概要
logging を利用してみる。
ドキュメント
モジュールの使い方は、公式ドキュメント「logging — Logging facility for Python」に概要が書いてある。 また「Logging HOWTO」が具体的な使い方に関して書いてある。
使い方
以下が一番簡単な例。
#!/usr/bin/env python
# -*- coding: utf-8 -*-
import logging
def main():
logging.warning('わーにんぐ')
logging.info('いんふぉ')
if __name__ == '__main__':
main()
実行すると以下のようになる。これはデフォルトレベルが「WARNING」以上だから。
WARNING:root:わーにんぐ
ログのレベルは以下のようになる。
レベル | 関数 | 数値 | 概要 |
---|---|---|---|
CRITICAL | logging.critical() | 50 | 停止してしまうような致命的な問題用 |
ERROR | logging.error() | 40 | 重大な問題用 |
WARNING | logging.warning() | 30 | 実行機能で問題が発生した場合用 |
INFO | logging.info() | 20 | 動作情報表示用 |
DEBUG | logging.debug() | 10 | 詳細な情報表示用 |
NOTSET | 0 | 全てを出力。基本的に設定用の値 |
ファイルへの出力
エラーをファイルに出したい場合があるが以下のようにする。
#!/usr/bin/env python
# -*- coding: utf-8 -*-
import logging
def main():
logging.basicConfig(filename='example.log', level=logging.DEBUG)
logging.debug('でばっぐ')
logging.info('いんふぉ')
logging.warning('わーにんぐ')
if __name__ == '__main__':
main()
「sample.log」ファイルに以下のように出力される。
DEBUG:root:でばっぐ
INFO:root:いんふぉ
WARNING:root:わーにんぐ
ログ出力形式の指定
ログの出力形式はいろいろ変更できる。
#!/usr/bin/env python
# -*- coding: utf-8 -*-
import logging
def main():
logging.basicConfig(format='%(asctime)s:%(levelname)s:%(message)s',
level=logging.DEBUG)
logging.debug('でばっぐ')
logging.info('いんふぉ')
logging.warning('わーにんぐ')
if __name__ == '__main__':
main()
以下のように出力される。
2012-10-01 11:21:46,999:DEBUG:でばっぐ
2012-10-01 11:21:46,999:INFO:いんふぉ
2012-10-01 11:21:47,000:WARNING:わーにんぐ
使えるフォーマットは「LogRecord attributes」に一覧がある。主な物は以下。
フォーマット | 概要 |
---|---|
%(asctime)s | 実行時刻 |
%(filename)s | ファイル名 |
%(funcName)s | 関数名 |
%(levelname)s | DEBUG、INFO等のレベル名 |
%(lineno)d | 行番号 |
%(name)s | 呼びだしたログの定義名 |
%(module)s | モジュール名 |
%(message)s | ログメッセージ |
%(process)d | プロセスID |
%(thread)d | スレッドID |
設定ファイルの利用
フォーマットやログレベルの設定は、通常は設定ファイルを書いて利用する。設定ファイルのファイル名な何でも良い。ここでは以下の内容で「logging.conf」として作成する。
以下の例だと、コンソールとファイルに「DEBUG」レベルでログを出力する。
[loggers]
keys=root, logExample
[handlers]
keys=consoleHandler, fileHandler
[formatters]
keys=logFormatter
[logger_root]
level=DEBUG
handlers=consoleHandler
[logger_logExample]
level=DEBUG
handlers=consoleHandler, fileHandler
qualname=logExample
propagate=0
[handler_consoleHandler]
class=StreamHandler
level=DEBUG
formatter=logFormatter
args=(sys.stdout,)
[handler_fileHandler]
class=handlers.RotatingFileHandler
level=DEBUG
formatter=logFormatter
args=('example.log',)
[formatter_logFormatter]
format=%(asctime)s - %(name)s - %(levelname)s - %(message)s
datefmt=
利用するソースは以下。
#!/usr/bin/env python
# -*- coding: utf-8 -*-
import logging
import logging.config
def main():
logging.config.fileConfig('logging.conf')
logger = logging.getLogger('logExample')
logger.debug('でばっぐ')
logger.info('いんふぉ')
logger.warning('わーにんぐ')
if __name__ == '__main__':
main()
Handlerの利用
上記のサンプルだと「RotatingFileHandler」を利用している。これはファイルが一定量になると回転するハンドラ。
標準のハンドラでも十分な場合もあるが、PyPIで探すと他にもいろいろなハンドラが存在している。
以下とか便利かもしれない。
- log4mongo:mongoDB にログを出力
- python-redis-log:Redis にログを出力
- td-logger:Treasure Dataにログを出力
- fluent-logger:Fluentdにログを出力
存在しない Handler は上記を参考に自作してみると良いかもしれない。
まとめ
logging は障害対処時に非常に有効。多用することになるので、使い方に慣れておくと良い。