はじめに
システムやプログラムを稼働・実行させている際にそのシステムやプログラムの状態の履歴の記録であるログを出力することが一般的です。特に異常時やエラー時等にログ内容から原因を究明して、改善・改良をすることがあることから、非常に重要な機能と言えます。
Pythonにおいてもログをコマンドラインに表示したり、ログファイル(.log)として出力することができます。本記事では、loggingライブラリを用いてPythonプログラムのログを表示、出力する方法を簡単に紹介します。
- はじめに
- 1. loggingによるログ内容の説明ページ
- 2. loggingによるログ出力
- 3. ログレベルを指定してログ出力
- 4. ログのメッセージフォーマットを指定
- 5. ログ記録時間のフォーマット
- 6. ログファイルの出力
- 7. logging.exceptionによるエラー内容の表示
- おわりに
1. loggingによるログ内容の説明ページ
本記事ではloggingライブラリを用いてログ表示・出力を行います。ログ内容の説明ページを下記に示します。詳細などは下記のリンクに記載されていますので、お時間がある方はぜひご覧ください。
2. loggingによるログ出力
loggingでは、DEBUG、INFO、WARNING,、ERROR、CRITICALの順の5段階レベルで出力することができます。ログレベルを指定しなければ、デフォルトのレベルは 「WARNING」になり、WARNING以上のログを出力します。
まずは簡単な例で確認してみましょう。最初はログレベルを指定せずにログの出力を試みてみます。下記に例を記載します。
上記を実行すると、下記のようなログがコマンドラインに表示されます。ご覧の通り、ログレベルを指定していないので、WARNING以上のログを出力となっています。
3. ログレベルを指定してログ出力
次に、ログレベルを指定してログ出力を行います。ここではレベルを下げて、INFOレベルを指定して出力してみます。ログ仕様を指定するに際には、logging.basicConfig()を用います。logging.basicConfig()の引数levelにレベルを指定します。下記に例を示します。
上記の実行結果が下記になります。ご覧のようにINFOのログまで出力しています。こちらはご自身の開発仕様に合わせて変更してみてください。
4. ログのメッセージフォーマットを指定
次に、ログのメッセージフォーマットを指定してログ出力を行います。メッセージフォーマットであるLogRecord 属性の詳細はこちらに記載されています。
代表的なものを抜粋して下表に示します。
属性名 | フォーマット | 説明 |
---|---|---|
asctime | %(asctime)s | ログが記録された時刻 |
pathname | %(pathname)s | loggingの呼び出しが発せられたファイルの絶対パス |
module | %(module)s | モジュール (filename の名前部分) |
ファイル名 | %(filename)s | 実行プログラムの絶対パスのファイル名部分 |
funcName | %(funcName)s | loggingの呼び出しを含む関数の名前 |
levelname | %(levelname)s | メッセージのログレベル |
lineno | %(lineno)d | loggingの呼び出しが発せられたソース行番号 |
message | %(message)s | ログメッセージ |
それでは、メッセージフォーマットを指定してログ出力を行ってみたいと思います。まずは、「ログ記録時間」、「ログレベル」、「ログメッセージ」の3種類の情報を出力してみましょう。下記にそのプログラムを示します。
上記のプログラムを実行すると、下記のように「ログ記録時間」、「ログレベル」、「ログメッセージ」の3種類の情報を含むログが表示されます。
さらに、要素を増やして表示させてみましょう。「ログ記録時間」、「ログレベル」、「ログメッセージ」、「モジュール」、「loggingの呼び出しを含む関数の名前」、「loggingの呼び出しが発せられたソース行番号」の6種類の情報を出力します。下記にそのプログラムを示します。
上記のプログラムを実行すると、「ログ記録時間」、「ログレベル」、「ログメッセージ」、「モジュール」、「loggingの呼び出しを含む関数の名前」、「loggingの呼び出しが発せられたソース行番号」の6種類の情報が出力されます。さらに関数(cal)内で実行されたloggingについてはその関数内で実行されたことが確認できます。また、 %(lineno)dによりloggingの行数が表示されて、どこのログなのかが把握しやすくなりました。
5. ログ記録時間のフォーマット
上記で「ログ記録時間」を表示していましが、このログ記録時間について表示形式を変更することが可能です。その際には、datefmtをlogging.basicConfig()の引数に指定することで実現可能です。フォーマット使用はtime.strftime()の仕様と同一です。
time --- 時刻データへのアクセスと変換 — Python 3.11.4 ドキュメント
それでは、ログ記録時間の表示形式を変更していきます。ここでは「%Y/%m/%d %H:%M:%S」の形式を指定し、その仕様で表示します。下記に例を示します。
上記のプログラムを実行すると、下記のような結果となります。時間の表示形式が「2023/07/08 15:10:43」のように変更されたことが確認できると思います。
6. ログファイルの出力
さて、ここまで表示内容について説明をしていきましたが、その内容をログファイルとして出力していきたいと思います。ログファイルを出力するには、logging.basicConfig()の引数filepathに出力先のパスを指定してあげることです。ここでは、プログラムと同一のディレクトリに出力するために、「logfile_test.log」のようにログファイルのベースネームのみ記載します。
このプログラムを実行すると、コマンドラインには何も表示されずにログファイルが出力されます。そのログファイルの中にログが記載されていることが確認できるかと思います。
7. logging.exceptionによるエラー内容の表示
例えば以下のようにtry-except文で例外処理やエラーが発生する場合、特段その内容が表示されなくて、何が原因で例外処理・エラーになったのか不明なケースがあると思います。
本記事で示したlogging.error()でも下記のようにエラー内容が表示されない状況です。
このようにエラーが発生した際にどのようなエラーかが不明で、原因を特定するのが難しいです。そんな時、活躍するのがlogging.exception()です。logging.exceptionでは例外情報がメッセージ内容に追加されます。それでは、logging.exceptionを使ってその仕様を確認してみます。上記と同じtry-except文でプログラムを実行してみます。
実行した結果が下記になります。ご覧の通り、loggingのメッセージに加えてエラー内容が表示されています。これで原因究明をしやすくなりますね。
おわりに
本記事では、loggingライブラリを用いてPythonプログラムのログを表示、出力する方法を簡単に紹介しました。ログの表示仕様などはご自身の開発に内容に合わせて調整してみてください。そしてログ内容から開発促進、システムのイレギュラー対応などにご活用いただければ幸いです。