トップ / 基礎知識
自分のPythonコードは、結局どこで動いているのか。クライアント・Snowflake・UDFという3つの実行場所を切り分けて説明します。
このページは、あなたの手元のマシン(ノートPCなど)からSnowflakeに接続してPythonスクリプトを実行する、最も基本的な使い方を前提にしています。そのうえで、Snowparkのコードを読むとき「Pythonなのだから手元のマシンで動く」と思ってしまいがちですが、実際には3種類の場所に処理が分かれています。
1. クライアント側:あなたが書いたPythonのスクリプト自体(DataFrameの変換メソッドを呼ぶ部分) 2. Snowflake側(SQLエンジン):フィルタ・結合・集計など、実際のデータ処理 3. Snowflake側(UDFのサンドボックス):あなたが書いたPython関数の中身が、条件によってはこちらで動く
この3つを区別せずに「Pythonはクライアントで動く」「SQLはSnowflakeで動く」とだけ覚えると、UDFを使った瞬間に混乱します。順番に見ていきます(ストアドプロシージャとして登録した場合はこの前提が変わります。後述の節を参照)。
select・filter・joinのような変換メソッドを呼ぶPythonの文自体は、あなたの手元のマシンからSnowflakeに接続して実行している限り、クライアント側で動きます。
ただし、このPythonコードが実際に行っていることは、データの処理ではありません。「この列を選ぶ」「この条件で絞り込む」という指示を、内部的な論理プラン(実行計画)として積み上げているだけです。Snowflake公式ドキュメントも「DataFrameは、データを取得するために評価される必要のあるクエリのようなものである」と説明しており、変換メソッドは「SQL文の組み立て方を指定するだけで、Snowflakeデータベースからデータを取得しない」と明記しています。
# ここまでの4行は、すべてクライアント側のPythonが実行される。
# しかし「実行される」のは論理プランの組み立てであって、
# テーブルの中身が読まれたり、フィルタが適用されたりは一切していない。
df2 = df.select("customer_id", "amount")
df3 = df2.filter(col("amount") > 100)
df4 = df3.join(other_df, "customer_id")
print("ここまで到達。まだSnowflakeには何も送っていない。")
# ここで初めてSQLが組み立てられ、Snowflakeへ送信・実行される。
result = df4.collect()
collect()・count()・show()・save_as_table()のようなアクションメソッドを呼んだ瞬間、それまで積み上げた論理プランがSQL文に変換され、Snowflakeの仮想ウェアハウスへ送信されて実行されます。テーブルの読み取り・結合・絞り込みといった実際のデータ処理はすべてここで行われ、処理結果だけがクライアントへ返ってきます。
ここが最も誤解されやすい点です。Pythonで書いたUDF(ユーザー定義関数)は、定義自体はクライアント側で書きますが、実行されるのはSnowflake側です。Snowflake公式ドキュメントは「UDFを呼び出すと、Snowparkはあなたの関数をデータのある場所=サーバー側で実行する」と明記しています。UDFの中でPythonの通常のライブラリを使っていても、それはSnowflakeのウェアハウス内で動いており、あなたの手元のマシンでは実行されていません。
変換をまとめてSQLへ変換してからSnowflakeへ送ることで、Snowflakeのクエリオプティマイザが変換全体を見渡して最適化できます。UDFの実行場所をSnowflake側に寄せているのも同じ理由で、データをクライアントへ転送せずに済み、ペタバイト規模のデータでも同じコードで処理できます。
ここまでの説明は「あなたの手元のマシンから接続して実行する」場合の話です。同じPythonコードをストアドプロシージャ(SPROC)として登録し、Snowflake側で呼び出す形にすると、前提が変わります。Snowflake公式ドキュメントは、Pythonのストアドプロシージャについて「Snowflakeの中でデータパイプラインを構築・実行でき、Snowflakeのウェアハウスがコンピュート基盤になる」「ウェアハウス上でAnacondaパッケージのインストールが行われる」と説明しています。つまり、SPROCとして登録したコードは、そのPython関数の中身自体がクライアントではなくSnowflakeのウェアハウス上で実行されます。
このとき、SPROCの中でselect・filterのようなDataFrame変換メソッドを呼んでも、それらはもう「あなたの手元のマシン」で動いているのではありません。「クライアント側」という言葉が指す場所自体が、SPROCの内側では変わるという点に注意してください。UDF・UDTF・SPROCの使い分け自体はこちらのページで解説しています。
selectやfilterを何行書いても、Snowflakeへは何も送られていません。「実行が速い」のではなく「まだ何も実行していない」だけ、というケースがよくあります。処理時間を計測するときは、必ずアクションメソッドを呼んだ地点で計測します。print()の出力はそのまま出てきません(Snowflakeのクエリ履歴やログから確認する必要があります)。「手元でデバッグできない」のはバグではなく、実行場所が違うことの当然の帰結です。公式ドキュメントの記載にもとづく解説です(実行検証はしていません)。確認日:2026-08-27