2016-02-10 16 views
12

私はPythonロギングモジュールを使用しており、インポートするサードパーティモジュールによって出力されるログメッセージを無効にしたいとします。例えば、私は次のようなものを使用しています:私はlogger.debug(「!私のメッセージ」)を行う際にPythonロギング - インポートされたモジュールからのロギングを無効にする

logger = logging.getLogger() 
logger.setLevel(level=logging.DEBUG) 
fh = logging.StreamHandler() 
fh_formatter = logging.Formatter('%(asctime)s %(levelname)s %(lineno)d:%(filename)s(%(process)d) - %(message)s') 
fh.setFormatter(fh_formatter) 
logger.addHandler(fh) 

これは私のデバッグメッセージを出力しますが、それはまた、任意のデバッグメッセージを出力します私がインポートするモジュール(リクエストや他の多くのものなど)

興味のあるモジュールからのログメッセージだけを見たいのですが、これはロギングモジュールをこれにすることは可能ですか?

理想的には、「ModuleX、ModuleY」からのメッセージを印刷し、他のすべてを無視するようにロガーに指示することができます。

私は、次のを見て、しかし、インポート機能へのすべての呼び出しの前に、私は有効/ログを無効にする必要がありますする必要はありません: logging - how to ignore imported module logs?

答えて

14

は問題が引数なしgetLoggerを呼び出すとルートを返すということですレベルをlogging.DEBUGに設定すると、そのロガーを使用する他のモジュールのレベルも設定されます。

ではなく、で簡単に解決できます。これはただの引数として名前を渡すためには、例えば、あなたのモジュールの名前:

logger = logging.getLogger('my_module_name') 
# as before 

が、これは新しいロガーが作成されますので、それが不注意で他のモジュールのログレベルを変更する文句を言いません。


明らかに、後者はルートロガーのdebugメソッドを呼び出す便利な関数であるため、代わりにlogging.debuglogger.debugを使用する必要があります。

これはAdvanced Logging Tutorialに記載されています。また、どのモジュールがログメッセージをトリガしたかを簡単に知ることができます。

4

@Bakuriuは非常に上品に機能を説明しています。逆に、getLogger()メソッドを使用して、不要なロガーを取得して再構成/無効化することができます。

また、logging.fileConfig()メソッドには、disable_existing_loggersというパラメータがあり、以前に定義されたロガー(インポートされたモジュール)は無効になります。

7

python loggingパッケージを使用する場合は、それを使用するすべてのモジュールでロガーを定義するのが一般的です。

logger = logging.getLogger(__name__) 

requestsを含む多くの一般的なpythonパッケージがこれを行います。パッケージがこの規則を使用する場合、ロガー名はパッケージと同じ名前(またはそのロガーの子になります)であるため、ロギングを有効または無効にするのは簡単です。他のロガーと同じファイルにログすることさえできます。

logger = logging.getLogger(__name__) 
logger.setLevel(logging.DEBUG) 

requests_logger = logging.getLogger('requests') 
requests_logger.setLevel(logging.DEBUG) 

handler = logging.StreamHandler() 
handler.setLevel(logging.DEBUG) 
logger.addHandler(handler) 
requests_logger.addHandler(handler) 
+0

ロガーを 'logging.basicConfig(...) 'という公式の基本チュートリアルのように設定しようとすると、すべてのロガーが' logging.lastResort'に出力されるようになることに注意してください。ハンドラが指定されていない場合、または設定したハンドラに指定されている場合)。とにかくすべてのログメッセージを取得し続けるでしょう。 – user136036

0

これはまだ(と外部ファイルをロードせずに)ルートロガーを使用しながら、そのようなインポートモジュールによって作成されたもののようなすべての既存のロガーを無効にします。

logging.config.dictConfig({ 
    'version': 1, 
    'disable_existing_loggers': True, 
}) 

最初にログに記録したくないモジュールをすべてインポートする必要があります。それ以外の場合は、「既存のロガー」とはみなされません。これらのモジュールからすべてのロガーが無効になります。これにより、重要な間違いを逃してしまうかもしれません!

コンフィグレーションに関連するオプションを使用した詳細な例については、https://gist.github.com/st4lk/6287746を参照してください。hereは、coloredlogライブラリを持つコンフィグレーションにYAMLを使用している(部分的に動作する)サンプルです。

+0

あなたの質問は何ですか? – user1767754

+0

これは 'request'のために働きますが、' BackgroundScheduler.BackgroundScheduler() 'を呼び出すときに、' APScheduler'のように、インポートされたモジュールが後で呼び出すクラスの中でロガーを作成するときには動作しません。ソリューションについてはこちらをご覧ください:https://stackoverflow.com/a/48891485/2441026 – user136036

関連する問題