2012年10月27日

Python 標準ロギングモジュール logging の使い方メモ

概要

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で探すと他にもいろいろなハンドラが存在している。
以下とか便利かもしれない。

存在しない Handler は上記を参考に自作してみると良いかもしれない。

まとめ

logging は障害対処時に非常に有効。多用することになるので、使い方に慣れておくと良い。

blog comments powered by Disqus