このページでは、App Engine アプリで使用可能なログと、ログエントリの作成、関連付け、表示を行う方法について説明します。
App Engine では次の 2 種類のログを収集します。
リクエストログ: アプリに送信されたリクエストのログ。デフォルトでは、App Engine は、アプリが受信した HTTP リクエストごとにログエントリを自動的に出力します。
アプリログ: サポートされているフレームワークまたはファイルに書き込んだログエントリに基づいて App Engine アプリが出力するログエントリ。
App Engine は、リクエストログとアプリログの両方を Cloud Logging エージェントに自動的に送信します。
アプリログを書き込む
App Engine はアプリに送信されたリクエストのログを自動的に出力します。ユーザーがリクエストログを作成する必要はありません。このセクションでは、アプリログを書き込む方法について説明します。
App Engine アプリからアプリログを書き込むときに、次の方法でログが書き込まれていれば、Cloud Logging が自動的にログを取得します。
Cloud Logging との統合
App Engine アプリを Cloud Logging と統合できます。この方法では Cloud Logging が提供するすべての機能を使用できます。Google 固有のコードを数行追加するだけで済みます。
Python アプリケーションから Cloud Logging にログを書き込むには、標準の Python ロギング ハンドラを使用するか、Python 用の Cloud Logging API クライアント ライブラリを直接使用します。標準の Python ロギング ハンドラを使用する場合は、Cloud Logging ハンドラを Python ルートハンドラに接続する必要があります。詳細については、Python 用に Cloud Logging を設定するをご覧ください。
構造化ログを stdout
と stderr
に書き込む
デフォルトでは、App Engine は Cloud Logging クライアント ライブラリを使用してログを送信します。ただし、このメソッドは構造化ロギングをサポートしていません。構造化ログを書き込むには、stdout/stderr
を使用する必要があります。また、テキスト文字列を stdout
と stderr
に送信することもできます。デフォルトでは、ログのペイロードはログエントリの textPayload
フィールドに保存されたテキスト文字列です。文字列は、ログ エクスプローラ、コマンドライン、Cloud Logging API にメッセージとして表示され、メッセージを発行した App Engine のサービスとバージョンに関連付けられます。
ログからより多くの情報を取得するには、ログ エクスプローラで重大度レベルを使用して、これらの文字列をフィルタします。文字列をフィルタするには、文字列を構造化データとしてフォーマットする必要があります。これを行うには、シリアル化された JSON を 1 行形式でログに書き込みます。App Engine は、このシリアル化された JSON 行を取得して解析し、ログエントリの textPayload
ではなく jsonPayload
フィールドに配置します。
次のスニペットは、このような構造化ログの書き込みを示しています。
App Engine スタンダード環境では、構造化ログを stdout
と stderr
に書き込んでも、Cloud Logging API での 1 分あたりのログ取り込みリクエスト数にカウントされません。
メッセージ内の特別な JSON フィールド
特殊フィールドのドキュメントで説明されているように、構造化ログを JSON ディクショナリとして提供すると、いくつかの特殊フィールドが jsonPayload
から削除され、生成された LogEntry の対応フィールドに書き込まれます。
たとえば、JSON に severity
プロパティが含まれている場合、jsonPayload
から削除され、代わりにログエントリの severity
として表示されます。message
プロパティが存在する場合は、ログエントリのメイン表示テキストとして使用されます。
リクエストログとアプリログを関連付ける
デフォルトでは、第 2 世代ランタイムのログは関連付けられていません。これらのランタイムでは、Cloud クライアント ライブラリを使用する必要があります。これらのライブラリはネストをサポートしていないため、ログを関連付ける必要があります。
Python ロギング モジュールを使用する
Python ロギング モジュールによって記録されたアプリログにリクエストを関連付けるには、Cloud Logging クライアント ライブラリを設定します。
アプリケーションの起動時に client.setup_logging()
メソッドを実行すると、logging.info()
や logging.error()
などの Python logging
モジュールによって書き込まれたアプリログに trace
フィールドと HTTP リクエストの詳細が追加されます。これらのログは logs/python
に転送されます。
また、App Engine はこの trace
フィールドを関連するリクエストログに追加します。これにより、関連するログエントリをログ エクスプローラで表示できます。
stdout
と stderr
を使用する
エントリを JSON オブジェクトとしてフォーマットし、特定のメタデータを提供すると、フィルタリングだけでなく、リクエストログとの関連付けも有効にできます。リクエストログのエントリとアプリログのエントリを関連付けるには、リクエストのトレース ID が必要です。手順に沿ってログ メッセージを関連付けます。
X-Cloud-Trace-Context
リクエスト ヘッダーからトレース ID を抽出します。- 構造化ログエントリで、ID を
logging.googleapis.com/trace
という名前のフィールドに書き込みます。X-Cloud-Trace-Context
ヘッダーの詳細については、リクエストを強制的にトレースするをご覧ください。
相関ログを表示するには、ログ エクスプローラで相関ログエントリを表示するをご覧ください。
ログを表示する
アプリログとリクエストログを表示する方法はいくつかあります。
- Google Cloud コンソールの Cloud Logging からログ エクスプローラを使用する。
- Google Cloud CLI で gcloud を使用してログを表示する
- さまざまな方法でプログラムによってログを読み取る
ログ エクスプローラを使用する
ログ エクスプローラを使用して、アプリログとリクエストログを表示できます。
Google Cloud コンソールの [ログ エクスプローラ] に移動します。
ページの上部にある既存の Google Cloud プロジェクトを選択します。
[リソースの種類] で [GAE アプリケーション] を選択します。
ログ エクスプローラでは、App Engine サービスとバージョン、その他の条件でフィルタリングできます。ログで特定のエントリを検索することもできます。詳細については、ログ エクスプローラの使用をご覧ください。
単純なテキスト エントリを標準出力に送信する場合は、ログビューアを使用して重要度でアプリエントリをフィルタリングすることはできません。また、特定のリクエストに対応するアプリログを表示することもできません。ログ エクスプローラでは、テキストやタイムスタンプなど、他のタイプのフィルタを使用することもできます。
ログ エクスプローラで相関ログエントリを表示する
ログ エクスプローラで、親ログエントリに関連付けられた子ログエントリを表示するには、ログエントリを開きます。
たとえば、App Engine リクエストのログエントリとアプリケーション ログエントリを表示するには、次のようにします。
Google Cloud コンソールのナビゲーション パネルで、[ロギング] を選択してから、[ログ エクスプローラ] を選択します。
[リソースの種類] で [GAE アプリケーション] を選択します。
リクエストログを表示して関連付けるには、[ログ名] で [request_log] を選択します。また、リクエストログで関連付けるには、[関連付け] をクリックして [request_log] を選択します。
[クエリ結果] ペインで、ログエントリを開くには、[開く] をクリックします。エントリを開くと、各リクエストログに関連付けられたアプリログが表示されます。
ログのフィルタを作成すると、各リクエストログに対応するアプリログが子ログとして表示されます。ログ エクスプローラは、アプリケーションが google-cloud-logging
ライブラリを使用していると仮定して、アプリログの trace
フィールドと特定のリクエストログを関連付けます。
次の図は、trace
フィールドでグループ化されたアプリログを示しています。
Google Cloud CLI を使用する
App Engine のログをコマンドラインから表示するには、次のコマンドを使用します。
gcloud app logs tail
詳細については、gcloud app logs tail をご覧ください。
プログラムでログを読み取る
プログラムでログを読み取るには、次のいずれかの方法を使用します。
- Pub/Sub へのログシンクと、Pub/Sub から pull するスクリプトを使用する。
- 使用しているプログラミング言語のクライアント ライブラリから Cloud Logging API を呼び出す。
- Cloud Logging API REST エンドポイントを直接呼び出す。
料金、割り当て、ログの保持ポリシー
リクエストログとアプリログの両方に適用される料金については、Cloud Logging の料金をご覧ください。
ログの保持ポリシーとログエントリの最大サイズについては、割り当てと上限をご覧ください。ログを長期間保存する場合は、Cloud Storage にログをエクスポートできます。ログをさらに処理するために、BigQuery や Pub/Sub へエクスポートすることもできます。
ログリソース使用状況の管理
アプリのコードからログエントリの書き込み量を調整することで、アプリログからロギング アクティビティの量を制御できます。リクエストログは自動的に作成されるため、アプリに関連付けられたリクエスト ログエントリの数を管理するには、Cloud Logging のログ除外機能を使用します。
既知の問題
第 2 世代のランタイムのロギングに関する問題は次のとおりです。
アプリログのエントリが、リクエストログに関連付けられない場合がある。これは、アプリがリクエストを初めて受信した場合および、App Engine がアプリログにステータス メッセージを書き込む場合に発生します。詳細については、https://issuetracker.google.com/issues/138365527 をご覧ください。
ログシンクから Cloud Storage にログを転送した場合、Cloud Storage の転送先にはリクエストログのみが格納されます。App Engine は、複数のフォルダにアプリのログを書き込みます。
BigQuery は、リクエストログの
@type
フィールドが原因でログを取り込めません。BigQuery ではフィールド名に@type
を使用できないため、自動スキーマ検出が中断されます。この問題を解決するには、スキーマを手動で定義し、リクエストログから@type
フィールドを削除する必要があります。ロギング REST API を使用すると、バックグラウンド スレッドが Cloud Logging にログを書き込みます。メインスレッドがアクティブでない場合、インスタンスは CPU 時間を取得しないため、バックグラウンド スレッドが停止します。ログ処理時間が遅延します。ある時点でインスタンスが削除され、送信されていないログがすべて失われます。ログが失われないようにするには、次のいずれかのオプションを使用します。
- gRPC を使用するように Cloud Logging SDK を構成します。gRPC を使用すると、ログはすぐに Cloud Logging に送信されます。ただし、これは必要な CPU の上限を引き上げる可能性があります。
stdout/stderr
を使用して、Cloud Logging にログメッセージを送信します。このパイプラインは App Engine インスタンスの外部にあるため、スロットルされることはありません。
次のステップ
- Cloud Logging でログを表示してエラーのデバッグを行う方法と、Cloud Trace を使用してアプリのレイテンシを把握する方法については、レイテンシのモニタリングとアラートをご覧ください。