Python 2 用 Appstats

Python 2 SDK には、アプリケーションの RPC(リモート プロシージャ コール)のパフォーマンスを測定する Appstats ライブラリが含まれています。App Engine RPC は、アプリケーションと App Engine Service API の間で行われる往復のネットワーク呼び出しです。 たとえば、以下の API 呼び出しはすべて RPC 呼び出しです:

  • データストア呼び出し(ndb.get_multi()ndb.put_multi()ndb.gql()など)。
  • Memcache 呼び出し(memcache.get()memcache.get_multi()、など)。
  • URL Fetch 呼び出し(urlfetch.fetch()など)。
  • Mail 呼び出し(mail.send()など)。

スケーラブルなアプリケーションでは、さまざまな要因でパフォーマンスが低下することや予期しないコストがかかることがあるため、パフォーマンスの最適化やデバッグが難しくなる場合があります。このような問題をログやリクエスト時間の統計情報などの通常の情報源でデバッグするのは非常に困難です。アプリケーションのほとんどのリクエストは、リクエストを処理するためのネットワーク呼び出しの完了を待機することに大半の時間を費やしています。

アプリケーションの処理速度を確保するには、次の項目を確認する必要があります。

  • アプリケーションで不要な RPC 呼び出しが行われていないか。
  • 同一のデータを取得する場合、繰り返し RPC を呼び出すのではなく、データをキャッシュに格納する必要があるか。
  • 複数のリクエストを連続ではなく並行して実行したほうがアプリケーションのパフォーマンスが向上するかどうか。

Appstats ライブラリを使用すると、このような問題を解決できます。このライブラリは RPC 呼び出しを測定し、アプリケーションが RPC を効率的に使用しているかどうか確認します。また、特定のリクエストに対するすべての RPC 呼び出しを追跡し、呼び出しごとに時間とコストを報告します。

アプリケーションでの RPC の使用を最適化することにより、コストを削減できます。アプリリソースの管理をご覧ください。

動画デモを見る

設定

Appstats の利用を開始するにあたって、ダウンロードやインストールが必要なものはありません。以下の手順に沿ってアプリケーションを構成して再デプロイし、Appstats コンソールにアクセスするだけです。残りの処理は Appstats ライブラリが実行します。

1. イベント レコーダーのインストール

ウェブ リクエストに関する統計情報を記録するには、アプリケーションの各リクエスト ハンドラで Appstats を呼び出す必要があります。アプリケーションで使用しているフレームワークに応じて、次のいずれかを選択します。

  • WSGI リクエスト ハンドラ

    WSGI フレームワーク(webapp2 など)を含め、WSGI リクエスト ハンドラとともに Appstats を使用するには、WSGI アプリケーションを Appstats ミドルウェアでラップする必要があります。これを行う最も簡単な方法は、appengine_config.py を使ってすべての WSGI アプリケーションをラップする WSGI ミドルウェアの定義することです。

    それがまだない場合には、アプリケーションのルート ディレクトリに appengine_config.py という名前のファイルを作成します。このファイルに以下の関数を追加します。

    def webapp_add_wsgi_middleware(app):
        from google.appengine.ext.appstats import recording
        app = recording.appstats_wsgi_middleware(app)
        return app

    WSGI アプリケーションを呼び出す前に、ランタイムではこのファイルがインポートされ、webapp_add_wsgi_middleware 関数(見つかった場合)が呼び出されます。

    appengine_config.py の詳細については、下記のオプションの構成をご覧ください。

  • Django フレームワーク

    Appstats ミドルウェアを Django アプリケーションにインストールするには、settings.py ファイルを編集し、次の行を MIDDLEWARE_CLASSES の最初の項目として追加します。

        MIDDLEWARE_CLASSES = (
      'google.appengine.ext.appstats.recording.AppStatsDjangoMiddleware',
    
      # ...
    )
    

    Appstats ミドルウェアは 1 つ目の項目でなければなりません。これにより、プロファイラは他のミドルウェアを統計情報に含めることができます。

    Django ミドルウェアは必要に応じて、Appstats を呼び出してイベントを記録します。他のアプリケーション コードを変更する必要はありません。

2. コンソールパスの設定

Appstats のコンソールにアクセスするには、ウェブブラウザでアプリケーションの URL に移動します。この URL のパスは、以下に示す 2 つの方法のいずれかで設定する必要があります。

  • デフォルト URL

    Appstats をデフォルトのディレクトリ(/_ah/stats/)にマッピングするには、appstats ビルトインを app.yaml ファイルに追加します。

    runtime: python27
    api_version: 1
    threadsafe: yes
    
    builtins:
    - appstats: on
    
    handlers:
    - url: .*
      script: main.app
    
  • カスタム URL

    Appstats をデフォルト以外のディレクトリにマッピングする必要がある場合は、url ディレクティブを app.yaml で使用できます。

      - url: /stats.*
      script: google.appengine.ext.appstats.ui.app
      

3. オプションの構成

Appstats の動作を構成するには、コンテンツをアプリケーションのルート ディレクトリの appengine_config.py ファイルに追加します。構成オプションの完全実例については、SDK の google/appengine/ext/appstats/sample_appengine_config.py ファイルをご覧ください。

appengine_config.py については次の点にご注意ください。

  • リクエスト ハンドラで sys.path が変更される場合は、同じ内容の変更を appengine_config.pysys.path に加える必要があり、そうすると、Appstats ウェブ インターフェースですべてのファイルを表示できるようになります。

コストの表示

AppStats は、RPC について時間だけでなくコストも追跡できます。アプリケーションの処理速度が十分でも、コストが予想よりも高い場合には、予想以上にコストがかかっているオペレーションを探します。コストの追跡を有効にするには、appengine_config.py ファイルで appstats_CALC_RPC_COSTS = True を設定します。

4. 開発用サーバーからの Appstats のテスト

Appstats の設定は開発用サーバーでテストできます。上記のデフォルト URL を使用するようにコンソールパスを構成した場合、コンソールには http://localhost:8080/_ah/stats/ からアクセスできます。

5. デプロイ

Appstats の設定に問題がなければ、アプリケーションをデプロイします。上記のデフォルト URL を使用するようにコンソールパスを構成した場合、http://your_app_id.appspot.com/_ah/stats のコンソールにアクセスできます。

Appstats コンソールについて

Appstats コンソールには、RPC 呼び出しの概要、リクエストされた URL パス、最近のリクエストの履歴、個々のリクエストの詳細が表示されます。

  • [RPC Stats] テーブルには、アプリケーションで実行された RPC の種類別に統計情報が表示されます。プラスボタンを押すとエントリが展開され、RPC でリクエストされたパス別に詳細が表示されます。

    スクリーンショット

  • [Path Stats] テーブルには、アプリケーションに送信されたそれぞれのパスリクエストの統計情報が表示されます。プラスボタンをクリックするとエントリが展開され、リクエストされたパスの詳細が RPC 別に表示されます。

    スクリーンショット

    API コスト追跡機能を有効にしている場合には、コストも表示されます。

  • [Requests History] テーブルには、個々のリクエストに関連するデータが表示されます。プラスボタンを押すとエントリが展開され、RPC 別に詳細が表示されます。リクエストのリンクをクリックすると、個々の RPC のタイミングを含むリクエストのタイムラインが表示されます。

    スクリーンショット

  • RPC タイムラインのグラフには、特定の RPC 呼び出しが実行された時間とリクエストの処理にかかった時間が表示されます。[RPC Total] バーには、RPC 呼び出しの待機時間の合計が表示されます。[Grand Total] バーには、リクエストの処理時間の合計が表示されます。下のタイムラインからわかるように、大半の時間は RPC 呼び出しに使用されています。これは珍しいことではありません。他のタブには、リクエストに関する追加情報が表示されます。パフォーマンスを分析するときに、アプリケーションのレスポンス時間に対する RPC 呼び出しの影響を把握することは重要です。

    スクリーンショット

  • Interactive Playground では、デベロッパーがウェブフォームに任意の Python コードを入力し、アプリの環境内で実行できます。

    Interactive Playground を使用するには、Appstats に移動して該当するリンクをクリックします。1 つのテキスト領域で構成されるフォームが表示されます。テキスト領域に任意の Python コードを入力し、フォームを送信して実行します。標準出力に出力された結果がテキスト領域の横に表示され、コードで生成された RPC 呼び出しのタイムライン分析が表示されます。

    Interactive Playground は、有効にするか無効にするかを切り替え可能です。SDK ではデフォルトで有効になり、本番環境ではデフォルトで無効になります。それを有効にするには、appengine_config.py ファイルに次の行を追加します。

    <pre suppresswarning="yes" class="prettyprint">
    appstats_SHELL_OK = True
    </pre>
    

仕組み

Appstats は、API フックを使用して、App Engine サービスの API の基礎となるリモート プロシージャ コールのフレームワークに追加されます。リクエスト ハンドラの実行中に行われたすべての API 呼び出しについて統計情報を記録し、__appstats__ の名前空間を使用して、そのデータを memcache に格納します。Appstats では、最新の 1,000 件のリクエストに関する統計情報を保持します。データには、概要レコード(それぞれ約 200 バイト)と詳細レコード(それぞれ最大 100 KB)が含まれます。詳細レコードに格納される詳細情報の量は制御できます(オプションの構成と構成ファイルの例をご覧ください)。

API フックによって、リクエスト ハンドラにオーバーヘッドがかかります。Appstats は、「情報」レベルのメッセージをログに追加して、Appstats ライブラリ自体で消費されているリソースの量をレポートします。ログには次のような行が出力されます。

<pre suppresswarning="yes" class="prettyprint">
INFO 2009-08-25 12:04:07,277 recording.py:290] Saved; key: __appstats__:046800, part: 160 bytes, full: 25278 bytes, overhead: 0.019 + 0.018; link: http://your_app_id.[REGION_ID].r.appspot.com/stats/detail?time=1234567890123
</pre>

この行では、更新された memcache キー、概要レコード(part)と詳細レコード(full)のサイズ、この情報の記録にかかった時間(秒)が報告されます。ログ行には、このイベントのデータが表示される Appstats 管理インターフェースへのリンクも含まれます。