Python ランタイム環境

App Engine では、Python プログラミング言語を使用してウェブ アプリケーションを作成できます。また、プロのデベロッパーが世界レベルのウェブ アプリケーションの作成に使用する数多くの Python 用ライブラリ、ツール、フレームワークを利用できます。作成した Python アプリケーションは、Google のスケーラブルなインフラストラクチャ上で動作し、大規模な永続的ストレージとサービスを利用します。

はじめに

App Engine では、あらかじめ用意されている Python インタープリタを使用して、Python アプリケーション コードを安全な「サンドボックス」環境で実行します。アプリは、この環境と通信することで、ウェブ リクエストの受信、作業の実行、レスポンスの送信を行います。

Python ウェブ アプリケーションは、WSGI プロトコルを使用して App Engine ウェブサーバーと情報を交換します。そのため、アプリケーションは、WSGI 互換のさまざまなウェブ アプリケーション フレームワークを利用できます。App Engine には、webapp2 というシンプルなウェブ アプリケーション フレームワークが含まれているため、簡単に開発を開始できます。大規模なアプリケーションの場合には、Django など、実績のあるサードパーティ製フレームワークを App Engine と連携させることができます。

インタープリタは、作成したアプリケーションに含めた Python モジュールや、Python 標準ライブラリなど、あらゆる Python コードを実行できます。ただし、インタープリタはピュアな Python 環境であるため、C コードで作成された Python モジュールを読み込むことはできません。

安全なサンドボックス環境は、サービスとセキュリティ上の理由から、作成したアプリケーションを隔離します。サンドボックス環境では、アプリケーションは、他のアプリケーションのパフォーマンスとスケーラビリティに影響しない処理しか実行できないようになります。たとえば、ローカル ファイル システムにデータを書き込んだり、任意にネットワークに接続したりすることはできません。代わりに、App Engine が提供するスケーラブルなサービスを利用して、データの保存やインターネット経由の通信を行います。サンドボックス制限内では動作しない Python モジュールを標準ライブラリからインポートしようとすると、Python インタープリタは例外を生成します。

App Engine プラットフォームには、コードから呼び出せる多数のサービスが用意されています。また、アプリケーションでは、指定の間隔で実行されるタスクのスケジュールを構成することもできます。

Python スタートガイドでは、Python と App Engine を使用したウェブ アプリケーションの開発についてわかりやすく解説しています。

Python ランタイムを選択する

app.yaml 構成ファイルに Python ランタイム環境を指定します。アプリケーションを App Engine にデプロイするときに、この環境が使用されます。たとえば、Python バージョン 2.7 を使用する場合には、次の行を app.yaml ファイルに追加します。

runtime: python27
api_version: 1
threadsafe: true
...

1 つ目の要素 runtime で、Python ランタイム環境を選択します。

2 番目の要素 api_version で、使用する Python ランタイム環境のバージョンを選択します。現時点で、App Engine Python 環境のバージョンは 1 の 1 つだけです。App Engine チームで環境に行う変更が既存のコードと互換性がない場合、新しいバージョン ID でリリースします。api_version 設定を変更してアプリをアップロードするまで、選択したバージョンを使用できます。

app.yaml ファイルの詳細と App Engine にアプリをデプロイする方法については、app.yaml リファレンスPython 2.7 への移行Python アプリのデプロイをご覧ください。

サンドボックス

App Engine が複数のアプリケーションへのリクエストを複数のウェブサーバーに分散できるようにして、アプリケーションが相互に干渉しないようにするために、アプリケーションは制限された「サンドボックス」環境で実行されます。この環境では、アプリケーションはコードの実行、Cloud Datastore データストア内でのデータの保存とクエリ、App Engine メール、URL フェッチ、ユーザーのサービスの使用、ユーザーのウェブ リクエストの確認とレスポンスの準備が可能です。

App Engine アプリケーションでは、次のことはできません。

  • ファイルシステムへの書き込み。アプリケーションは、データを永続的に保存するために、Cloud Datastore を使用する必要があります。ファイルシステムからの読み取りは可能です。また、アプリケーションでアップロードされたアプリケーション ファイルはすべて利用可能です。

  • 遅いレスポンス。アプリケーションへのウェブ リクエストは、数秒以内に処理される必要があります。レスポンスまでに非常時に長い時間がかかるプロセスは、ウェブサーバーの過負荷を防ぐために終了します。

  • その他の種類のシステムコールの実行。

Python でサンドボックス化する

Python 2.7 ランタイムを使用している場合、.pyc ファイルをアップロードして使用できますが、同じファイルの .py.pyc をアップロードすることはできません。.py または .pyc ファイル(あるいはその組み合わせ)を含む zip ファイルをアップロードできます。.pyc ファイルをアップロードする場合には、次の点に注意してください。

  • CGI スクリプトの場合、.pyc ファイルをアップロードしても、スクリプト ハンドラ.py ファイル拡張子を使用する必要があります。
  • デフォルトでは、デプロイで .pyc ファイルがスキップされます。新しい値で .pyc ファイルがスキップされないように、app.yaml ファイルの skip_files 要素をオーバーライドする必要があります。
  • .pyc ファイルを作成するには、Python 2.7 を使用する必要があります。開発用のマシンで Python の異なるバージョン(Python 2.6 など)を使用する場合には、バージョン 2.7 を取得して互換性のある .pyc ファイルを作成する必要があります。

ピュア Python

Python ランタイム環境のコードはすべてピュア Python である必要があり、C 拡張やコンパイルが必要な他のコードを含めることはできません。

この環境には Python 標準ライブラリが含まれています。ただし、一部のモジュールは、コア関数が App Engine でサポートされないため、無効になっています(ネットワーク接続やファイル システムへの書き込みなど)。また、os モジュールは使用できますが、サポートされていない機能は無効になっています。サポートされていないモジュールをインポートしようとした場合や、サポートされていない機能を使用しようとした場合は、例外が発生します。

標準ライブラリの一部のモジュールは、App Engine で動作するように置換、カスタマイズされています。対象となるモジュールは、2 つの Python ランタイムで異なります(下記参照)。

Python バージョン 2.7 のカスタム ライブラリ

Python バージョン 2.7 ランタイムでは、次のモジュールが置換またはカスタマイズされています。

  • tempfile は無効になっています。ただし、TemporaryFile には StringIO のエイリアスが設定されます。

  • logging は使用可能です。使用することを強くおすすめします。ロギングをご覧ください。

Python 標準ライブラリと App Engine ライブラリ以外に、Python バージョン 2.7 ランタイムにはサードパーティ ライブラリも含まれています。

サードパーティ ライブラリを追加する

アプリケーションに Python のサードパーティ ライブラリを追加するには、アプリケーション ディレクトリにコードを配置します。アプリケーション ディレクトリのライブラリのディレクトリにシンボリック リンクを作成すると、そのリンクが参照されて、App Engine にデプロイするアプリケーションにライブラリが含まれるようになります。

Python モジュールのインクルード パスには、アプリケーションのルート ディレクトリ(app.yaml ファイルを含むディレクトリ)が含まれます。アプリケーションのルート ディレクトリに作成した Python モジュールは、ルートからのパスでアクセスできます。Python がこれらのサブディレクトリをパッケージとして認識できるように、必要な __init__.py ファイルをサブディレクトリに作成することを忘れないでください。また、ライブラリで C 拡張が不要になるようにしてください。

スレッド

Python バージョン 2.7 では、thread または threading モジュールを使用してスレッドを作成できます。リクエストが終了すると、ランタイムがスレッドを結合します。リクエストの終了後にスレッドを実行することはできません。

バックグラウンド スレッド

手動または基本のスケーリング インスタンスで実行するコードは、バックグラウンド スレッドを開始できます。このスレッドは、スレッドを生成したリクエストよりも長く存続できます。これにより、インスタンスは任意の周期またはスケジュールによってタスクを実行できるようなるほか、リクエストがユーザーに返された後でもバックグラウンドで作業を続行できるようになります。

バックグラウンド スレッドの os.environ とロギング エントリは、生成元スレッドのそれらの値とは無関係です。

App Engine 用 SDK から google.appengine.api.background_thread モジュールをインポートする必要があります。

from google.appengine.api import background_thread

BackgroundThread クラスは、通常の Python threading.Threadclass に似ていますが、スレッドを生成したリクエストよりも長く存続できます。バックグラウンド スレッドを作成し、開始する関数 start_new_background_thread() もあります。

# sample function to run in a background thread
def change_val(arg):
    global val
    val = arg

if auto:
    # Start the new thread in one command
    background_thread.start_new_background_thread(change_val, ['Cat'])
else:
    # create a new thread and start it
    t = background_thread.BackgroundThread(
        target=change_val, args=['Cat'])
    t.start()
App Engine API で作成される同時実行バックグラウンド スレッドの最大数はインスタンスごとに 10 個です(この制限は App Engine API に関係しない通常の Java スレッドには適用されません)。

ツール

App Engine 用 SDK には、アプリケーションのテスト、アプリケーション ファイルのアップロード、Cloud Datastore インデックスの管理、ログデータのダウンロード、Cloud Datastore に対する大量データのアップロードを行うためのツールが用意されています。

開発用サーバーを使用すると、ローカル コンピュータ上でアプリケーションを実行して、アプリケーションをテストできます。サーバーは Cloud Datastore サービスとサンドボックス制限をシミュレートします。また、開発サーバーでは、テスト中にアプリが実行するクエリに基づいて、Cloud Datastore インデックスの構成を生成することもできます。

gcloud ツールにより、App Engine で動作しているアプリケーションに対するすべてのコマンドライン操作が処理されます。コードをデプロイする前に新しいインデックスを作成できるように、gcloud app deploy を使用してアプリケーションを App Engine にアップロードするか、Cloud Datastore インデックス構成のような個々の構成ファイルを更新します。また、アプリのログデータを表示して、独自のツールでアプリのパフォーマンスを分析することもできます。

同時実行とレイテンシ

トラフィックに対処するために必要なインスタンスの数に特に大きく影響するのはアプリケーションのレイテンシです。リクエストを短時間のうちに処理できるサービスであれば、1 つのインスタンスで多くのリクエストを処理できます。

シングルスレッドのインスタンスでは、同時に 1 件のリクエストしか処理できません。そのため、レイテンシと、インスタンスで処理できる 1 秒あたりのリクエスト数の間には直接的な相関関係があります。たとえば、10 ミリ秒のレイテンシでは、1 つのインスタンスで 1 秒間に 100 件のリクエストを処理します。

マルチスレッドのインスタンスでは、多数のリクエストの同時処理が可能です。そのため、CPU 使用量と 1 秒あたりのリクエスト処理数の間に直接の相関関係があります。

Python バージョン 2.7 アプリは、同時リクエストをサポートしているため、1 つのインスタンスで他のリクエストが完了するまで待機している間に、新しいリクエストを処理できます。同時実行性を使用すると、アプリが必要とするインスタンスの数が大幅に少なくなりますが、アプリケーションをマルチスレッド対応として設計する必要があります。

たとえば、B4 インスタンス(約 2.4 GHz)がリクエスト 1 件につき 10 M サイクルを使用する場合、1 つのインスタンスでの 1 秒あたりのリクエスト処理数は 240 件になります。リクエスト 1 件につき 100 M サイクルを使用する場合は、1 つのインスタンスでの 1 秒あたりのリクエスト処理数は 24 件になります。このような数字は理想的な条件を想定したものですが、インスタンスの処理能力という点ではかなり現実的な数字です。

このページは役立ちましたか?評価をお願いいたします。

フィードバックを送信...

Python の App Engine スタンダード環境