ユーザー定義関数の概要¶
ユーザー定義関数(UDFs)を記述して、Snowflakeが提供する組み込みのシステム定義関数では利用できない操作を実行するようにシステムを拡張できます。UDF を作成すると、何度でも再利用できます。
UDF は、Snowflakeを拡張する1つの方法にすぎません。その他については、次をご参照ください。
注釈
UDF はストアドプロシージャに似ていますが、この2つは重要な点で異なります。詳細については、 ストアドプロシージャとユーザー定義関数のどちらを記述するかの選択 をご参照ください。
このトピックの内容:
ユーザー定義関数(UDF)とは¶
ユーザー定義関数(UDF)は、ユーザーが定義する関数であるため、 SQL から呼び出すことができます。 組み込み関数 と同様に、 SQL から呼び出すことができます。UDF のロジックは通常、 SQL にはない機能やうまくいかない機能を使用して SQL を拡張または拡張します。UDF は、コード内の複数の場所から繰り返し呼び出すことができるように、機能をカプセル化する方法も提供します。
UDF のロジック(そのハンドラー)を、 サポートされている言語 のいずれかで記述します。ハンドラーを作成したら、 CREATE FUNCTION コマンドで UDF を作成し、 SELECT ステートメントで UDF を呼び出す ことができます。
スカラー関数と表関数¶
単一の値(スカラー UDF) または表形式の値(ユーザー定義のテーブル関数、または UDTF)を返す UDF を記述できます。
スカラー 関数(UDF)は、入力行ごとに1つの出力行を返します。返される行は、単一の列/値で構成されます。
表 関数(UDTF)は、入力行ごとに表形式の値を返します。UDTF のハンドラーでは、Snowflakeに必要なインターフェイスに準拠するメソッドを記述します。これらのメソッドは次を実行します。
パーティション内の各行を処理する(必須)。
パーティションごとに1回ハンドラーを初期する(オプション)。
各パーティションの処理を終了する(オプション)。
メソッドの名前は、ハンドラー言語によって異なります。サポートされている言語のリストについては、 サポートされている言語 をご参照ください。
考慮事項¶
クエリが UDF を呼び出してステージングされたファイルにアクセスする場合に、 SQL ステートメントが UDF またはUDTF の いずれか を呼び出すビューもクエリすると、ビューにある関数がステージングされたファイルにアクセスするかどうかにかかわらず、操作に失敗してユーザーエラーが発生します。
UDTFs 複数のファイルを並行して処理できます。ただし、 UDFs は現在、ファイルをシリアルに処理しています。回避策として、 GROUP BY 句を使用してサブクエリの行をグループ化します。例については、 UDTF を使用して CSV を処理する をご参照ください。
現在、クエリで参照されているステージングされたファイルが、クエリの実行中に変更または削除された場合、関数の呼び出しはエラーを発生して失敗します。
始めましょう¶
SQL で記述されたハンドラーを使用して UDTF を記述するチュートリアルについては、 クイックスタート: ユーザー定義 SQL 関数入門 をご参照ください。
UDF の例¶
次の例のコードは、Pythonで記述されたハンドラーを使用して addone
という名前の UDF を作成します。ハンドラー関数は addone_py
です。この UDF は int
を返します。
CREATE OR REPLACE FUNCTION addone(i int)
RETURNS INT
LANGUAGE PYTHON
RUNTIME_VERSION = '3.8'
HANDLER = 'addone_py'
as
$$
def addone_py(i):
return i+1
$$;
次の例のコードは、 addone
UDF を実行します。
SELECT addone(3);
サポートされている言語¶
関数のハンドラー(そのロジック)は、いくつかのプログラミング言語のいずれかで記述します。各言語では、言語とそのランタイム環境の制約内でデータを操作できます。ハンドラー言語に関係なく、 SQL を使用して同じ方法でプロシージャー自体を作成し、ハンドラーとハンドラー言語を指定します。
次の言語のいずれかでハンドラーを記述できます。
言語 |
開発者ガイド |
---|---|
Java |
|
JavaScript |
|
Python |
|
Scala |
|
SQL |
言語の選択¶
UDF のハンドラー(そのロジック)は、いくつかのプログラミング言語のいずれかで記述します。各言語では、言語とそのランタイム環境の制約内でデータを操作できます。
次の場合は、特定の言語を選択できます。
その言語のコードがすでにある。
たとえば、ハンドラーとして機能するJavaメソッドがすでにあり、メソッドのオブジェクトが.jarファイルにある場合は、.jarをステージにコピーし、ハンドラーをクラスおよびメソッドとして指定してから、Javaを言語として指定します。
選択する言語には、他の言語にはない機能がある。
選択する言語には、必要な処理を実行するために役立つライブラリがある。
言語を選択するときは、次も考慮してください。
サポートされているハンドラーの場所。 すべての言語がステージ上のハンドラーの参照をサポートしているわけではありません(ハンドラーコードはインラインにする必要があります)。詳細については、 ハンドラーコードのインラインまたはステージ上での保持 をご参照ください。
ハンドラーが共有可能な UDF になるかどうか。 共有可能な UDF は、Snowflakeの Secure Data Sharing 機能で使用できます。
言語 |
ハンドラーの場所 |
共有可能 |
---|---|---|
Java |
インラインまたはステージング |
不可 [1] |
JavaScript |
インライン |
はい |
Python |
インラインまたはステージング |
不可 [2] |
Scala |
インラインまたはステージング |
不可 [3] |
SQL |
インライン |
はい |
開発者ガイド¶
ガイドラインと制約¶
- Snowflakeの制約:
Snowflakeの制約内で開発することにより、Snowflake環境内での安定性を確保できます。詳細については、 Snowflakeが課す制約内でのハンドラーの設計 をご参照ください。
- 命名:
他の関数との競合を避ける方法で関数に名前を付けるようにしてください。詳細については、 プロシージャおよび UDFs の命名とオーバーロード をご参照ください。
- 引数:
引数を指定し、どの引数がオプションであるかを示します。詳細については、 UDFs およびストアドプロシージャの引数の定義 をご参照ください。
- データ型マッピング:
ハンドラー言語ごとに、言語のデータ型と、引数および戻り値に使用される SQL 型との間に個別のマッピングのセットがあります。各言語のマッピングの詳細については、 SQL とハンドラー言語間のデータ型マッピング をご参照ください。
ハンドラーの記述¶
- ハンドラー言語:
ハンドラーの記述に関する言語固有のコンテンツについては、 サポートされている言語 をご参照ください。
- 外部ネットワークアクセス:
外部ネットワークアクセス で外部ネットワークロケーションにアクセスできます。Snowflakeの外部にある特定のネットワークロケーションへのセキュアアクセスを作成して、ハンドラーコード内からそのアクセスを使用することができます。
- ログおよびトレース:
ログメッセージやトレースイベントをキャプチャ し、後でクエリできるデータベースにデータを保存すると、コードのアクティビティを記録できます。
セキュリティ¶
UDF または UDTF を使用して特定の SQL アクションを実行するために必要な権限をオブジェクトに対して付与できます。詳細については、 Granting Privileges for User-Defined Functions をご参照ください
関数は、ストアドプロシージャと特定のセキュリティ上の問題を共有しています。詳細については、次をご参照ください。
UDFs とプロシージャのセキュリティプラクティス で説明されているベストプラクティスに従うと、プロシージャのハンドラーコードを安全に実行することができます。
機密情報は、アクセスしてはならないユーザーから隠されていることを確認してください。詳細については、 セキュア UDFs とストアドプロシージャの使用による機密情報の保護 をご参照ください
ハンドラーコードの展開¶
関数を作成するとき、関数のロジックを実装するハンドラーを、CREATE FUNCTION ステートメントとインラインのコードとして、またはパッケージ化されてステージにコピーされたコンパイル済みコードなど、ステートメントの外部のコードとして指定できます。
詳細については、 ハンドラーコードのインラインまたはステージ上での保持 をご参照ください。
関数の作成と呼び出し¶
ユーザー定義関数を作成して呼び出すには、 SQL を使用します。