Snowpark Container Services: サービスの操作

Snowpark Container Services を使用すると、コンテナー化されたアプリケーションを簡単に展開、管理、スケーリングできるようになります。アプリケーションを作成し、Snowflakeアカウントのリポジトリにアプリケーションイメージをアップロードしたら、アプリケーションコンテナーをサービスまたは ジョブ として実行できます。このトピックでは、サービスの操作方法について説明します。

サービスは長時間継続し、ウェブサービスのように自動的に終了することはありません。サービスを作成した後、Snowflakeは実行中のサービスを管理します。たとえば、何らかの理由でサービスコンテナーが停止した場合、Snowflakeはそのコンテナーを再起動し、サービスが中断されることなく実行されるようにします。サービスにより多くのコンピューティングパワーなどのリソースが必要な場合、Snowflakeは コンピューティングプール に追加のノードをプロビジョニングします。

基本的なサービス操作

Snowpark Container Servicesは、サービスの作成と管理に使用できる SQL コマンドのセットを提供します。これらには次が含まれます。 CREATE SERVICE、 ALTER SERVICE、 DROP SERVICE、 SHOW SERVICES、 および DESC[RIBE] SERVICE。

サービスの作成に最低限必要な情報は以下のとおりです。

  • サービス仕様: この 仕様 は、サービスの実行に必要な情報をSnowflakeに提供します。仕様は YAML ファイルです。CREATE SERVICE ステートメント内で仕様を直接定義するか、仕様をSnowflakeステージにアップロードし、 CREATE SERVICE ステートメント内でステージ情報を参照します。

    多くの場合、開発中はインライン仕様を選ぶでしょう。しかし、サービスを実稼働環境に展開する際には、懸念事項の分離という設計原則を適用し、仕様をステージにアップロードすることが望ましいといえます。

  • コンピューティングプール: Snowflakeは、指定された コンピューティングプール でサービスを実行します。

  • インライン仕様を使用してサービスを作成します。

    CREATE SERVICE echo_service
       IN COMPUTE POOL tutorial_compute_pool
       FROM SPECIFICATION $$
       spec:
         containers:
         - name: echo
           image: /tutorial_db/data_schema/tutorial_repository/my_echo_service_image:tutorial
           readinessProbe:
             port: 8000
             path: /healthcheck
         endpoints:
         - name: echoendpoint
           port: 8000
           public: true
       $$;
    
    Copy
  • ステージ情報を使用してサービスを作成します。

    CREATE SERVICE echo_service
      IN COMPUTE POOL tutorial_compute_pool
      FROM @tutorial_stage
      SPECIFICATION_FILE='echo_spec.yaml';
    
    Copy

サービスを作成した後、 ALTER SERVICE コマンドを使用してサービスを中断または再開することができます。

複数のサービスインスタンスを作成し、自動スケールを構成する

デフォルトでは、Snowflakeは指定したコンピューティングプールでサービスのインスタンスを1つ実行します。重いワークロードを管理するには、 MIN_INSTANCES と MAX_INSTANCES プロパティを設定して、複数のサービスインスタンスを実行できます。このプロパティは、サービスの最小インスタンス数から開始し、必要に応じてSnowflakeがスケールできる最大インスタンス数を指定します。

CREATE SERVICE echo_service
   IN COMPUTE POOL tutorial_compute_pool
   FROM @tutorial_stage
   SPECIFICATION_FILE='echo_spec.yaml'
   MIN_INSTANCES=2
   MAX_INSTANCES=4;
Copy

複数のサービスインスタンスが実行されている場合、Snowflakeは自動的にロードバランサーを提供し、受信するリクエストを分散します。

実行中のサービスインスタンス数を自動スケールするようにSnowflakeを構成するには、以下のステップに従います。

  1. サービス仕様ファイルで、サービスインスタンスに必要なメモリと CPU を指定します。詳細については、 container.resources フィールドをご参照ください。

    resources:
      requests:
       memory: <memory-reserved>
       cpu: <cpu-units>
    
    Copy
  2. CREATE SERVICE コマンドを実行する場合は、 MIN_INSTANCES と MAX_INSTANCES パラメーターを設定します。また、 ALTER SERVICE を使用してこれらの値を変更することもできます。

Snowflakeは、指定されたコンピューティングプール上に最小数のサービスインスタンスを作成することから開始し、その後、必要に応じてインスタンス数を自動的にスケールします。Snowflakeはしきい値の80%(CPU とメモリの双方で)を使用して、サービスインスタンス数をスケールアップまたはスケールダウンします。

指定されたコンピューティングプール上では、いつでも1つ以上のサービスインスタンスを実行できます。Snowflakeは、現在実行中のすべてのサービスインスタンスから使用状況データを集約して、コンピューティングプール内のリソース使用量(メモリまたは CPU)を継続的にモニターします。

リソース使用量の合計(すべてのサービスインスタンス)が80%を超えると、Snowflakeはコンピューティングプール内に追加のサービスインスタンスを展開します。集約されたリソースの使用量が80%を下回ると、Snowflakeは実行中のサービスインスタンスを削除してスケールダウンします。Snowflakeは5分間の安定化ウィンドウを使用して、頻繁なスケーリングを防止します。

以下のスケーリング動作に注意してください。

  • サービスインスタンスのスケーリングは、サービス用に構成された MIN_INSTANCES と MAX_INSTANCES パラメーターによって制約されます。

  • スケールアップが必要で、コンピューティングプールノードが別のサービスインスタンスを起動するために必要なリソース容量が不足している場合は、コンピューティングプールの自動スケールをトリガーできます。詳細については、 コンピューティングプールノードの自動スケーリング をご参照ください。

  • サービスの作成時に MAX_INSTANCES と MIN_INSTANCES パラメーターを指定しても、サービス仕様ファイルでサービスインスタンスのメモリと CPU 要件を指定しない場合は、自動スケーリングは実行されません。Snowflakeは MIN_INSTANCES プロパティで指定されたインスタンスの数で開始され、数は自動スケーリングされません。

サービスをリストする

さまざまな SHOW SERVICES コマンドを使用して、現在のサービスをリストすることができます。

  • SHOW SERVICES: 権限を持っている現在のデータベースとスキーマのサービスをリストします。

  • SHOW SERVICES IN ACCOUNT: サービスがどのデータベースやスキーマに属しているかに関係なく、Snowflakeアカウントのサービスをリストします。これは、アカウント内の複数のデータベースとスキーマにSnowflakeサービスが作成されている場合に便利です。他のコマンドと同様に、 SHOW SERVICES IN ACCOUNTS は権限によって制限され、使用しているロールが表示権限を持っているサービスのみを返します。

  • SHOW SERVICES IN SCHEMA: 指定されたスキーマのサービスをリストします。

特定のコンピューティングプールのサービスをリストアップするのは、2段階のプロセスです。

  1. SHOW SERVICES を実行し、サービスのリストを取得します。

  2. 特定のコンピューティングプールにあるサービスのために、前回のクエリ(RESULT_SCAN を使用)のリストをスキャンします。

以下のスクリプト例では、 SHOW SERVICES コマンドはまず、現在のデータベースとスキーマの中で、サービス名に特定の文字列を持つサービスをリストします。

次に、 SELECT クエリは、指定されたコンピューティングプール内のサービスのみを返すように結果セットをフィルターします。このクエリでは、前述の SHOW SERVICES コマンドの結果セットを取得するために RESULT_SCAN 関数を使用していることに注意してください。

SHOW SERVICES like '%tutorial%' in account;
SELECT *
    FROM TABLE(RESULT_SCAN(last_query_id()))
    WHERE "compute_pool" = 'TUTORIAL_COMPUTE_POOL';
Copy

サービスのモニタリング

サービスの詳細な実行時ステータスを取得するには、 SYSTEM$GET_SERVICE_STATUS を使用します。たとえば、この関数を呼び出すと、サービスがまだ実行中なのか、それともサービスの開始に失敗したのかを判断することができます。サービスの開始に失敗した場合、この関数は失敗の詳細を提供します。

この関数を呼び出す場合は、サービスの名前で渡します。

CALL SYSTEM$GET_SERVICE_STATUS('echo_service');
Copy

以下は出力例です。

  • 1つのインスタンスを実行し、1つのコンテナーを持つサービスのサンプル出力:

    [
       {
          "status":"READY",
          "message":"Running",
          "containerName":"echo",
          "instanceId":"0",
          "serviceName":"ECHO_SERVICE",
          "image":"<account>.registry.snowflakecomputing.com/tutorial_db/data_schema/tutorial_repository/my_echo_service_image:tutorial",
          "restartCount":0,
          "startTime":"2023-01-01T00:00:00Z"
       }
    ]
    
    Copy

    instanceId は、コンテナーが属するサービスインスタンス ID です。このサービスのインスタンスを2つ実行した場合、出力にはこのようなオブジェクトが2つ含まれ、各サービスインスタンスのコンテナーステータスが提供されます。この場合、インスタンス IDs は0と1です。

  • 1つのインスタンスを実行し、3つのコンテナーを持つサービスのサンプル出力:

    [
       {
          "status":"READY",
          "message":"Running",
          "containerName":"some-proxy",
          "instanceId":"0",
          "serviceName":"example_service",
          "image":"<account>.registry.snowflakecomputing.com/tutorial_db/data_schema/tutorial_repository/my_service_image_proxy:tutorial",
          "restartCount":0,
          "startTime":"2023-01-01T00:00:00Z"
       },
       {
          "status":"READY",
          "message":"Running",
          "containerName":"some-server",
          "instanceId":"0",
          "serviceName":"example_service",
          "image":"<account>.registry.snowflakecomputing.com/tutorial_db/data_schema/tutorial_repository/my_server:tutorial",
          "restartCount":0,
          "startTime":"2023-01-01T00:00:00Z"
       },
       {
          "status":"READY",
          "message":"Running",
          "containerName":"movies",
          "instanceId":"0",
          "serviceName":"example_service",
          "image":"<account>.registry.snowflakecomputing.com/tutorial_db/data_schema/tutorial_repository/my_movies:tutorial",
          "restartCount":0,
          "startTime":"2023-01-01T00:00:00Z"
       }
    ]
    
    Copy

    出力には、各コンテナーのステータス情報が含まれます。これらのコンテナーはすべて、インスタンス ID 0を持つ単一のサービスインスタンスに属しています。

SYSTEM$GET_SERVICE_STATUS は、オプションの timeout_secs 引数を取得します。 timeout_secs が指定されないか、値0で指定された場合、この関数はただちに現在のステータスを返します。 timeout_secs が指定された場合、Snowflakeは指定された時間内にサービスが終了状態(READY または FAILED)になるまで待ってからサービスステータスを返します。指定された時間内にサービスが終了状態に到達しなかった場合、Snowflakeは指定された時間間隔の終了時に現在の状態を返します。

指定するタイムアウトは、サービスの準備が整うと予想されるタイミングに基づく近似値であり、これは、Snowflakeが他のサービスを開始する前に、他のサービスやジョブが停止し、指定したコンピューティングプールのリソースが解放されるのを待っている場合などの状況を特定するのに役立ちます。次の SYSTEM$GET_SERVICE_STATUS 関数は10秒のタイムアウトを指定します。

call SYSTEM$GET_SERVICE_STATUS('echo_service', 10);
Copy

ローカルコンテナーログへのアクセス

Snowflakeは、アプリケーションコンテナー内のコードが標準出力や標準エラーに出力するものをすべて収集します。コードがサービスのデバッグに有用な情報を出力するようにしてください。

Snowflakeは、これらのコンテナーログにアクセスする2つの方法を提供します。

  • SYSTEM$GET_SERVICE_LOGS システム関数の使用: 特定のコンテナーからログにアクセスできます。コンテナーが終了した後も、しばらくはシステム関数を使用してログにアクセスできます。システム関数は、開発中やテスト中、サービスやジョブを最初に作成する場合に最も役に立ちます。詳細については、 SYSTEM$GET_SERVICE_LOGS をご参照ください。

  • イベントテーブルの使用: イベントテーブルを使用すると、すべてのサービスにわたる複数のコンテナーからログにアクセスできます。Snowflakeは、後でアクセスできるようにイベントテーブルにログを永続化します。イベントテーブルは、サービスやジョブのレトロスペクティブな分析に最適です。詳細については、 イベントテーブルの使用 をご参照ください。

SYSTEM$GET_SERVICE_LOGS の使用

ユーザーは、取得するサービス名、インスタンス ID、コンテナー名、またオプションで最新のログ行数を提供します。サービスインスタンスが1つしか実行されていない場合、サービスインスタンス ID は0になります。たとえば、次の GET_SERVICE_LOGS コマンドは、 echo_service という名前のサービスのインスタンス0に属する echo という名前のコンテナーのログから、後続の10行を取得します。

CALL SYSTEM$GET_SERVICE_LOGS('echo_service', '0', 'echo', 10);
Copy

サービス情報(インスタンス ID やコンテナー名など)を知らない場合は、まず GET_SERVICE_STATUS を実行して、各インスタンスで実行されているサービスインスタンスとコンテナーに関する情報を取得することができます。

出力例:

+--------------------------------------------------------------------------+
| SYSTEM$GET_SERVICE_LOGS                                                  |
|--------------------------------------------------------------------------|
| 10.16.6.163 - - [11/Apr/2023 21:44:03] "GET /healthcheck HTTP/1.1" 200 - |
| 10.16.6.163 - - [11/Apr/2023 21:44:08] "GET /healthcheck HTTP/1.1" 200 - |
| 10.16.6.163 - - [11/Apr/2023 21:44:13] "GET /healthcheck HTTP/1.1" 200 - |
| 10.16.6.163 - - [11/Apr/2023 21:44:18] "GET /healthcheck HTTP/1.1" 200 - |
+--------------------------------------------------------------------------+
1 Row(s) produced. Time Elapsed: 0.878s

SYSTEM$GET_SERVICE_LOGS 出力には以下の制限があります。

  • 標準出力と標準エラーのストリームを単純にマージするため、通常の出力とエラーメッセージの区別がつかなくなる。

  • 単一のサービスインスタンスで、特定のコンテナーのキャプチャデータを報告する。

  • 実行中のコンテナーのログのみを報告する。関数は、再起動された以前のコンテナーや、停止または削除されたサービスのコンテナーからログをフェッチすることはできない。

  • 関数は100 KB までのデータを返す。

イベントテーブルの使用

Snowflakeは、コンテナーからの標準出力と標準エラーをキャプチャし、アカウント用に設定されたイベントテーブルに記録することができます。詳細については、 ログおよびトレースの概要 をご参照ください。

たとえば、次の SELECT クエリは、過去1時間に記録されたSnowflakeサービスとジョブイベントを取得します。

SELECT TIMESTAMP, RESOURCE_ATTRIBUTES, RECORD_ATTRIBUTES, VALUE
FROM <current-event-table-for-your-account>
WHERE timestamp > dateadd(hour, -1, current_timestamp())
AND RESOURCE_ATTRIBUTES:"snow.executable.type" = 'SnowparkContainers'
ORDER BY timestamp DESC
LIMIT 10;
Copy

Snowflakeは、この例に示すように、イベントテーブルクエリの WHERE 句にタイムスタンプを含めることを推奨します。さまざまなSnowflakeコンポーネントによって生成される潜在的データ量のため、これは特に重要です。フィルターを適用すると、より小さなデータのサブセットを取得することができ、クエリのパフォーマンスが向上します。

サービス仕様ファイルの spec.logExportersフィールド を使用して、イベントテーブルに永続化するログのレベル(すべて、エラーのみ、なし)を制御します。

イベントテーブルには以下の列があり、Snowflakeがコンテナーから収集したログに関する有用な情報を提供します。

  • TIMESTAMP: Snowflakeがいつログを収集したかを示します。

  • RESOURCE_ATTRIBUTES: この列の各オブジェクトは、どのSnowflakeサービスとサービス内のコンテナーがログを生成したかを識別します。たとえば、サービスの実行時に指定されたサービス名、コンテナー名、コンピューティングプール名などの詳細を提供します。

    {
    "snow.containers.compute_pool.id": 549816068,
    "snow.containers.compute_pool.name": "TUTORIAL_COMPUTE_POOL",
    "snow.containers.container.name": "echo",
    "snow.containers.instance.name": "0",
    "snow.containers.restart.id": "cd0cf2",
    "snow.database.id": 549816076,
    "snow.database.name": "TUTORIAL_DB",
    "snow.executable.id": 980991015,
    "snow.executable.name": "ECHO_SERVICE",
    "snow.executable.type": "SnowparkContainers",
    "snow.schema.id": 549816076,
    "snow.schema.name": "DATA_SCHEMA"
    }
    
    Copy
  • RECORD_ATTRIBUTES: Snowflakeサービスの場合は、エラーソース(標準出力または標準エラー)を識別します。

    { "log.iostream": "stdout" }
    
    Copy
  • VALUE: 標準出力と標準エラーは行に分割され、各行はイベントテーブルに記録を生成します。

    "echo-service [2023-10-23 17:52:27,429] [DEBUG] Sending response: {'data': [[0, 'Joe said hello!']]}"
    

イベントテーブルの構成

詳細については、 ログおよびトレースの概要 をご参照ください。

サービスの使用

将来のサービス(まだ作成されていないサービス)の使用をロールに付与することができます。例:

GRANT USAGE ON FUTURE SERVICES IN [DATABASE <name> | SCHEMA <name>]TO ROLE <name>
Copy

サービスを作成した後、次の3つのサポートされている方法のいずれかを使用して、そのサービスと通信できます。

  • サービス関数: サービスに関連するサービス関数(UDF)を作成します。次に、 SQL クエリからサービスと通信するためにサービス関数を使用します。例については、 チュートリアル1 をご参照ください。

  • イングレス: Snowflake外部からサービスにアクセスするには、サービスによって公開されているパブリックエンドポイントを使用します。この場合は、Snowflakeがアクセス制御を管理します。例については、 チュートリアル1 をご参照ください。

  • サービス間通信: サービス間通信には、Snowflakeが割り当てたサービス DNS 名を使用します。例については、 チュートリアル3 をご参照ください。

以下のセクションで詳細を説明します。

サービス関数: SQL クエリからのサービスの使用

サービス関数とは、 CREATE FUNCTION を使用して作成するユーザー定義関数(UDF)のことです。しかし、 UDF のコードを直接記述する代わりに、 UDF をサービスに関連付けます。たとえば、 チュートリアル1 では、サービス仕様で定義された1つのエンドポイント(echoendoint)を公開する echo_service という名前のサービスを作成します。

spec:

  endpoints:
  - name: echoendpoint
    port: 8080
Copy

echoendpoint は、対応するポート(8080)を表す分かりやすいエンドポイント名です。このサービスエンドポイントと通信するには、次に示すように SERVICE と ENDPOINT パラメーターを指定してサービス関数を作成します。

CREATE FUNCTION my_echo_udf (text varchar)
   RETURNS varchar
   SERVICE=echo_service
   ENDPOINT=echoendpoint
   AS '/echo';
Copy

AS パラメーターは、サービスコードへの HTTP パスを提供します。このパス値はサービスコードから取得します(例: チュートリアル1 のservice.pyを参照)。

@app.post("/echo")
def echo():
...
Copy

サービス関数を呼び出すと、Snowflakeは関連するサービスエンドポイントとパスにリクエストを誘導します。

注釈

サービス関数は、ジョブとではなく、サービスと通信するために使用されます。つまり、サービスのみ(ジョブではなく)をサービス関数に関連付けることができます。

サービスの複数のインスタンスを実行する場合は、オプションの MAX_BATCH_ROWS パラメーターを指定してサービス関数を作成し、 バッチサイズ (Snowflakeがサービスにバッチで送信する最大行数)を制限することができます。たとえば、 MAX_BATCH_ROWS が10で、 my_echo_udf サービス関数を100入力行で呼び出したとします。Snowflakeは入力行をバッチに分割し、各バッチは最大10行を持ち、リクエスト本文にバッチ行を持つ一連のリクエストをサービスに送信します。処理に多くの時間がかかる場合は、バッチサイズを設定すると役に立ちます。行を利用可能なサーバー全体に分散することも役に立ちます。

サービス関数を変更するには、 ALTER FUNCTION を使用します。次の ALTER FUNCTION コマンドは、関連付けるサービスエンドポイントとバッチサイズを変更します。

ALTER FUNCTION my_echo_udf(VARCHAR)
   SET SERVICE=other_service
   ENDPOINT=otherendpoint
   MAX_BATCH_ROWS=100
Copy

データ交換形式

サービス関数とコンテナー間のデータ交換では、Snowflakeは外部関数が使用するのと同じ形式に従います(データ形式 を参照)。たとえば、テーブル(input_table)にデータ行が格納されているとします。

"Alex", "2014-01-01 16:00:00"
"Steve", "2015-01-01 16:00:00"

このデータをサービスに送信するには、これらの行をパラメーターとして渡してサービス関数を呼び出します。

SELECT service_func(col1, col2) FROM input_table;
Copy

Snowflakeは、一連のリクエストをリクエスト本文のデータ行のバッチと合わせて次の形式でコンテナーに送信します。

{
   "data":[
      [
         0,
         "Alex",
         "2014-01-01 16:00:00"
      ],
      [
         1,
         "Steve",
         "2015-01-01 16:00:00"
      ],
      …
      [
         <row_index>,
         "<column1>",
         "<column2>"
      ],
   ]
}
Copy

そして、コンテナーは次の形式で出力を返します。

{
   "data":[
      [0, "a"],
      [1, "b"],
      …
      [ row_index,  output_column1]
   ]
}
Copy

上記の出力例では、行(「a」、「b」)を持つ1列のテーブルを想定しています。

複数のサービスインスタンスが稼働している場合は、 MAX_BATCH_ROWS パラメーターを使用してサービス関数を作成し、利用可能なすべてのサーバーに入力行を分散して処理することができます。

サービス関数の作成および管理に必要な権限

サービス関数を作成して管理するには、ロールに以下の権限が必要です。

  • サービス関数を作成するには: 現在のロールは、参照されるサービスに対する USAGE 権限を持っている必要があります。

  • サービス関数を変更するには: サービス関数を変更し、別のサービスと関連付けることができます。現在のロールには、新しいサービスに対する USAGE 権限が必要です。

  • サービス関数を使用するには: 現在のロールには、サービス関数に対する USAGE 権限が必要であり、サービス関数所有者ロールには、関連するサービスに対する USAGE 権限が必要です。

次のスクリプト例では、サービス関数の権限を付与する方法を示します。

USE ROLE service_owner;
GRANT USAGE ON service service_db.my_schema.my_service TO ROLE func_owner;

USE ROLE func_owner;
CREATE OR REPLACE test_udf(v VARCHAR)
  RETURNS VARCHAR
  SERVICE=service_db.my_schema.my_service
  ENDPOINT=endpointname1
  AS '/run';

SELECT test_udf(col1) FROM some_table;

ALTER FUNCTION test_udf(VARCHAR) SET
  SERVICE = service_db.other_schema.other_service
  ENDPOINT=anotherendpoint;

GRANT USAGE ON FUNCTION test_udf(varchar) TO ROLE func_user;
USE ROLE func_user;
SELECT my_test_udf('abcd');
Copy

イングレス: Snowflake外部からのサービスの使用

サービスは、1つまたは複数のエンドポイントをパブリックとして公開して、ユーザーがパブリックウェブからサービスを使用できるようにします。

注釈

パブリックプライベートプレビューでは、Snowflakeアカウントの ACCOUNTADMIN により、以下のコマンドを実行する必要があります。

CREATE SECURITY INTEGRATION SNOWSERVICES_INGRESS_OAUTH
TYPE=oauth
OAUTH_CLIENT=snowservices_ingress
ENABLED=true;
Copy

サービス仕様ファイルでエンドポイントをパブリックとしてマークします。

spec
  ...
  endpoints
  - name: <endpoint name>
    port: <port number>
    public: true
Copy

サービス仕様の詳細については、 仕様リファレンス をご参照ください。

公開エンドポイントアクセスおよび認証

Snowpark Container Servicesは、パブリックエンドポイントへのリクエストを認証するためにSnowflake OAuth を必要とします。たとえば、ユーザー名とパスワードを使用してサインインする必要があります。背後では、サインインするとSnowflakeから OAuth トークンが生成されます。そして、 OAuth トークンを使用してサービスエンドポイントにリクエストが送信されます。

注釈

  • Snowpark ContainersはSnowflake OAuth を使用してイングレスを有効にするため、ユーザーの既定のロールは、 ACCOUNTADMIN、 SECURITYADMIN、 ORGADMIN などの権限ロールのいずれにすることもできません。詳細については、 統合の使用から特定のロールをブロックする をご参照ください。

  • サービスによって公開された公開エンドポイントには、誰もがアクセスできるわけではありません。サービスに対する USAGE 権限のあるロールを持つ同じSnowflakeアカウントのユーザーのみが、サービスのパブリックエンドポイントにアクセスできます。

パブリックエンドポイントには、ブラウザーまたはプログラムを使用してアクセスできます。

  • ブラウザーの使用によるパブリックエンドポイントのアクセス: ブラウザーを使用してパブリックエンドポイントにアクセスすると、ユーザー認証のために自動的にリダイレクトされます。 チュートリアル1 を探索して、この体験を試すことができます。

  • プログラムによるパブリックエンドポイントのアクセス: 以下のPythonのサンプルコードでは、まず Python用Snowflakeコネクタ を使用して、IDを表すセッショントークンを生成します。その後、コードはセッショントークンを使用してパブリックエンドポイントにログインします。

    import snowflake.connector
    import requests
    
    ctx = snowflake.connector.connect(
       user="<username>",# username
       password="<password>", # insert password here
       account="<orgname>-<acct-name>",
       session_parameters={
          'PYTHON_CONNECTOR_QUERY_RESULT_FORMAT': 'json'
       })
    
    # Obtain a session token.
    token_data = ctx._rest._token_request('ISSUE')
    token_extract = token_data['data']['sessionToken']
    
    # Create a request to the ingress endpoint with authz.
    token = f'\"{token_extract}\"'
    headers = {'Authorization': f'Snowflake Token={token}'}
    # Set this to the ingress endpoint URL for your service
    url = 'http://<ingress_url>'
    
    # Validate the connection.
    response = requests.get(f'{url}', headers=headers)
    print(response.text)
    
    # Insert your code to interact with the application here
    
    Copy

    コードで、

    • アカウント情報(<組織名>-<アカウント名>)が分からない場合は、チュートリアルの 共通セットアップ をご参照ください。

    • SHOW ENDPOINTS を使用すると、サービスが公開しているパブリックエンドポイントの ingress_url を取得できます。

イングレスリクエストのユーザー固有ヘッダー

Snowflakeは、イングレスエンドポイントのリクエストを受信すると、自動的に HTTP リクエストと共に以下のヘッダーをコンテナーに渡します。

Sf-Context-Current-User: <user_name>
Sf-Context-Current-User-Email: <email>
Copy

コンテナーコードにより、オプションでこれらのヘッダーを読み取り、呼び出し元が誰であるかを知ることができ、異なるユーザーに対してコンテキスト固有のカスタマイズを適用することができます。

サービス間通信

サービスは、Snowflakeが各サービスに自動的に割り当てる DNS 名を使用して相互に通信できます。例については、 チュートリアル3 をご参照ください。

DNS 名形式は以下のとおりです。

<service-name>.<schema-name>.<db-name>.snowflakecomputing.internal

サービスの DNS 名を取得するには、 SHOW SERVICES (また はDESCRIBE SERVICE)を使用します。前述の DNS 名はフルネームです。同じスキーマで作成されたサービスでは、 <サービス名> を使用するだけで通信できます。同じデータベースにありながらスキーマが異なるサービスでは、 <サービス名>.<スキーマ名> のようにスキーマ名を指定する必要があります。

Snowflakeは、同じロールによって作成されたサービス間のネットワーク通信を許可し、異なるロールによって作成されたサービス間のネットワーク通信をブロックします。サービス同士が通信できないようにする場合(セキュリティなどの理由により)は、異なるSnowflakeロールを使用してこれらのサービスを作成します。

DNS 名には以下の制限があります。

  • データベース名、スキーマ名、サービス名は、有効な DNS ラベルにする必要があります。(https://www.ietf.org/rfc/rfc1035.html#section-2.3.1 もご参照ください)。それ以外の場合は、サービスの作成に失敗します。

  • Snowflakeは、名前(データベース、スキーマ、およびサービス名)のアンダースコア(_)を DNS 名ではダッシュ(-)に置き換えます。

  • Snowflakeはサービスの DNS 名を更新しないため、サービスを作成した後はデータベースやスキーマ名を変更しないでください。

  • DNS 名は、同じアカウントで実行されているサービス間のSnowflake内部での通信にのみ使用されます。インターネットからはアクセスできません。

サービスのコード更新

サービスを作成した後、 ALTER SERVICE を使用してサービスコードを更新します。まず、修正したアプリケーションコードをイメージリポジトリにアップロードし、インラインまたはSnowflakeステージの仕様ファイルへのパスを指定して、サービス仕様を提供する ALTER SERVICE を呼び出します。例:

  • 仕様をインラインで提供します(以下は仕様の一部を表示)。

    ALTER SERVICE echo_service
    FROM SPECIFICATION $$
    spec:
      
      
    $$;
    
    Copy
  • Snowflakeステージのファイルパスを指定します。

    ALTER SERVICE echo_service
    FROM @tutorial_stage
    SPECIFICATION_FILE='echo_spec.yaml';
    
    Copy

リクエストを受信すると、Snowflakeは新しいコードを使用してサービスを再展開します。

ALTER SERVICE は、常にリポジトリの最新バージョンのイメージを使用します。たとえば、「echo_service:latest」または「echo_service:sometag」という名前が付いた複数のバージョンのイメージをアップロードした場合、Snowflakeはアップロードされた最新のバージョンのイメージを使用します。

DESCRIBE SERVICE コマンドを使用すると、サービスが実行しているイメージのバージョンを見つけることができます。サービス所有者の場合、 DESCRIBE SERVICE 出力には、イメージダイジェスト(イメージの SHA256)を取得するサービス仕様が含まれます。例:

spec:
containers:
- name: "echo"
   image: "orgname-acctname.registry-dev.snowflakecomputing.com/tutorial_db/data_schema/tutorial_repository/my_echo_service_image:latest"
   sha256: "@sha256:8d912284f935ecf6c4753f42016777e09e3893eed61218b2960f782ef2b367af"
   env:
      SERVER_PORT: "8000"
      CHARACTER_NAME: "Bob"
   readinessProbe:
      port: 8000
      path: "/healthcheck"
endpoints:
- name: "echoendpoint"
   port: 8000
   public: true
Copy

注釈

サービスを中断して再開した場合、Snowflakeは同じイメージバージョンを展開しますが、これはサービスの更新操作ではありません。

権限

権限

使用状況

メモ

USAGE

サービスと通信します。サービス関数の作成、パブリックエンドポイントの使用、他のサービスからの接続に必要です。

MONITOR

サービスをモニターし、ランタイムのステータスを取得します。

OPERATE

サービスを中断または再開します。

OWNERSHIP

サービスを包括的に制御します。特定のオブジェクトに対して一度にこの権限を保持できるのは、1つのロールのみです。

ALL [ PRIVILEGES ]

OWNERSHIP を除く、サービスに対するすべての権限を付与します。