ベクトル検索インデックスを作成してクエリを実行する方法
この記事では、 Mosaic AI Vector Search を使用してベクトル検索インデックスを作成およびクエリする方法について説明します。
ベクトル検索UI、Python SDK 、またはREST API を使用して、ベクトル検索エンドポイントやベクトル検索インデックスなどの コンポーネントを作成および管理できます。
必要条件
- Unity Catalog対応ワークスペースであること。
- サーバレス コンピュートが有効化されていること。手順については、 サーバレス コンピュートへの接続を参照してください。
- ソース テーブルでは、チェンジデータフィードが有効になっている必要があります。 手順については、DatabricksでのDelta Lakeチェンジデータフィードの使用を参照してください。
- ベクトル検索インデックスを作成するには、インデックスが作成されるカタログスキーマに対する CREATE TABLE 権限が必要です。
- 別のユーザーが所有するインデックスをクエリするには、追加の特権が必要です。 ベクトル検索エンドポイントのクエリを参照してください。
ベクトル検索エンドポイントを作成および管理するためのアクセス許可は、アクセス制御リストを使用して構成されます。 ベクトル検索エンドポイント ACLを参照してください。
インストール
ベクトル検索 SDK を使用するには、ノートブックにインストールする必要があります。 次のコードを使用して、パッケージをインストールします。
%pip install databricks-vectorsearch
dbutils.library.restartPython()
次に、次のコマンドを使用して VectorSearchClient
をインポートします。
from databricks.vector_search.client import VectorSearchClient
認証
データ保護と認証を参照してください。
ベクトル検索エンドポイントを作成する
ベクトル検索エンドポイントは、Databricks UI、Python SDK、または API を使用して作成できます。
UI を使用したベクトル検索エンドポイントの作成
UI を使用してベクトル検索エンドポイントを作成するには、次の手順に従います。
-
左のサイドバーで、[ コンピュート ]をクリックします。
-
「 ベクトル検索 」タブをクリックし、「 作成 」をクリックします。
-
エンドポイントの作成フォーム が開きます。このエンドポイントの名前を入力します。
-
確認 をクリックします。
Python SDK を使用してベクトル検索エンドポイントを作成する
次の例では、 create_endpoint() SDK 関数を使用して ベクトル検索 エンドポイントを作成します。
# The following line automatically generates a PAT Token for authentication
client = VectorSearchClient()
# The following line uses the service principal token for authentication
# client = VectorSearchClient(service_principal_client_id=<CLIENT_ID>,service_principal_client_secret=<CLIENT_SECRET>)
client.create_endpoint(
name="vector_search_endpoint_name",
endpoint_type="STANDARD"
)
REST API を使用してベクトル検索エンドポイントを作成する
REST API リファレンスドキュメントを参照してください: POST /api/2.0/vector-search/endpoints。
(オプション)埋め込みモデルを提供するエンドポイントを作成して構成する
エンベディングをDatabricksに計算させることを選択した場合は、事前に構成された基盤モデル API エンドポイントを使用するか、モデルサービング エンドポイントを作成して、選択したエンベディングモデルを提供できます。 手順については、トークン単位の従量課金 基盤モデル API または エンドポイント基盤モデルをサービングするエンドポイントの作成を参照してください。ノートブックの例については、 エンベディングモデルを呼び出すためのノートブックの例を参照してください。
エンべディングエンドポイントを構成する場合、Databricks では、デフォルトの選択である Scale to zero を削除することをお勧めします。 エンドポイントの提供にはウォームアップに数分かかる場合があり、スケールダウンされたエンドポイントを持つインデックスに対する最初のクエリがタイムアウトする可能性があります。
エンべディングエンドポイントがデータセットに対して適切に構成されていない場合、ベクトル検索インデックスの初期化がタイムアウトになる可能性があります。 CPU エンドポイントは、小規模なデータセットとテストにのみ使用してください。 大規模なデータセットの場合は、最適なパフォーマンスを得るために GPU エンドポイントを使用します。
ベクトル検索インデックスを作成する
ベクトル検索インデックスは、UI、Python SDK、または REST API を使用して作成できます。 UI は最も簡単なアプローチです。
インデックスには、次の 2 つのタイプがあります。
- Delta Sync Index は、ソース Delta テーブルと自動的に同期し、Delta テーブル内の基になるデータが変更されると、インデックスを自動的かつ増分的に更新します。
- Direct Vector Access Index は、ベクトルとメタデータの直接読み取りと書き込みをサポートします。 ユーザーは、REST API または Python SDK を使用してこのテーブルを更新する必要があります。 このタイプのインデックスは、UI を使用して作成することはできません。 REST API または SDK を使用する必要があります。
列名 _id
は予約されています。ソース・テーブルに _id
という名前のカラムがある場合は、ベクトル検索インデックスを作成する前に名前を変更します。
UI を使用したインデックスの作成
-
左のサイドバーで[ カタログ ] をクリックして、カタログエクスプローラーUIを開きます。
-
使用する Delta テーブルに移動します。
-
右上の 作成 ボタンをクリックし、ドロップダウンメニューから ベクトル検索インデックス を選択します。
-
ダイアログのセレクタを使用して、インデックスを設定します。
名前 : Unity Catalog のオンライン テーブルに使用する名前。 名前には
<catalog>.<schema>.<name>
、. 英数字とアンダースコアのみ使用できます。主キー : 主キーとして使用する列。
エンドポイント : 使用するベクトル検索エンドポイントを選択します。
同期する列 : ベクトル インデックスと同期する列を選択します。 このフィールドを空白のままにすると、ソース テーブルのすべての列がインデックスと同期されます。 主キー列と埋め込みソース列または埋め込みベクトル列は常に同期されます。
エンべディングソース : Databricks でDeltaテーブル内のテキスト列のエンべディングをコンピュートするか ( エンベディングの計算 )、 Deltaテーブルに事前計算されたエンべディングが含まれるかどうか ( 既存のエンべディング列を使用 ) を示します。
- エンベディングの計算 を選択した場合は、埋め込みコンピュートの列と、埋め込みモデルを提供するエンドポイントを選択します。テキスト列のみがサポートされています。
- 既存のエンべディング列を使用 を選択した場合は、事前計算されたエンべディングとエンべディングディメンションを含む列を選択します。 事前計算されたエンべディング列の形式は
array[float]
である必要があります。
計算されたエンベディングの同期 : この設定を切り替えて、生成されたエンベディングを Unity Catalog テーブルに保存します。 詳細については、「 生成されたエンベディングテーブルの保存」を参照してください。
同期モード : 連続 は、インデックスを数秒の待機時間と同期させます。 ただし、コンピュート クラスターは連続同期ストリーミング パイプラインを実行するためのプロビジョニングであるため、コストが高くなります。 連続 と トリガー の両方で、更新は増分であり、最後の同期以降に変更されたデータのみが処理されます。
トリガー モードでは、Python SDK または REST API を使用して同期を開始します。Delta Sync インデックスの更新を参照してください。
-
インデックスの構成が完了したら、[ 作成 ] をクリックします。
Python SDK を使用してインデックスを作成する
次の例では、Databricks によるエンべディングコンピュートを使用してDelta同期インデックスを作成します。
client = VectorSearchClient()
index = client.create_delta_sync_index(
endpoint_name="vector_search_demo_endpoint",
source_table_name="vector_search_demo.vector_search.en_wiki",
index_name="vector_search_demo.vector_search.en_wiki_index",
pipeline_type="TRIGGERED",
primary_key="id",
embedding_source_column="text",
embedding_model_endpoint_name="e5-small-v2"
)
次の例では、自己管理型のエンベディングを使用して Delta Sync Index を作成します。 この例では、オプションのパラメーター columns_to_sync
を使用して、インデックスで使用する列のサブセットのみを選択する方法も示しています。
client = VectorSearchClient()
index = client.create_delta_sync_index(
endpoint_name="vector_search_demo_endpoint",
source_table_name="vector_search_demo.vector_search.en_wiki",
index_name="vector_search_demo.vector_search.en_wiki_index",
pipeline_type="TRIGGERED",
primary_key="id",
embedding_dimension=1024,
embedding_vector_column="text_vector"
)
デフォルトでは、ソーステーブルのすべてのカラムがインデックスと同期されます。 列のサブセットのみを同期するには、 columns_to_sync
を使用します。 プライマリ・キーとエンベディングカラムは、常にインデックスに含まれます。
プライマリキーとエンベディングカラム のみを 同期するには、次のように columns_to_sync
で指定する必要があります。
index = client.create_delta_sync_index(
...
columns_to_sync=["id", "text_vector"] # to sync only the primary key and the embedding column
)
追加の列を同期するには、次のように指定します。 プライマリ・キーとエンベディングカラムは、常に同期されるため、含める必要はありません。
index = client.create_delta_sync_index(
...
columns_to_sync=["revisionId", "text"] # to sync the `revisionId` and `text` columns in addition to the primary key and embedding column.
)
次の例では、Direct Vector Access Index を作成します。
client = VectorSearchClient()
index = client.create_direct_access_index(
endpoint_name="storage_endpoint",
index_name=f"{catalog_name}.{schema_name}.{index_name}",
primary_key="id",
embedding_dimension=1024,
embedding_vector_column="text_vector",
schema={
"id": "int",
"field2": "string",
"field3": "float",
"text_vector": "array<float>"}
)
REST API を使用したインデックスの作成
REST API リファレンス ドキュメント ( POST /api/2.0/vector-search/indexes) を参照してください。
生成されたエンベディングテーブルを保存
Databricks がエンべディングを生成する場合、生成されたエンべディングを Unity Catalog のテーブルに保存できます。 このテーブルは、ベクトル索引と同じスキーマで作成され、ベクトル索引ページからリンクされます。
テーブルの名前は、ベクトル検索インデックスの名前に _writeback_table
を付加したものです。 名前は編集できません。
このテーブルは、Unity Catalog の他のテーブルと同様にアクセスしてクエリを実行できます。 ただし、テーブルは手動で更新することを意図していないため、削除または変更しないでください。 インデックスが削除されると、テーブルは自動的に削除されます。
ベクトル検索インデックスの更新
Delta Sync インデックスの更新
連続 同期モードで作成されたインデックスは、ソース Delta テーブルが変更されると自動的に更新されます。 トリガー同期 モードを使用している場合は、Python SDK または REST API を使用して同期を開始します。
- Python SDK
- REST API
index.sync()
REST API リファレンスドキュメントを参照してください: POST /api/2.0/vector-search/indexes/{index_name}/sync。
Direct Vector Access インデックスの更新
Python SDK または REST API を使用して、Direct Vector Access Index のデータを挿入、更新、または削除できます。
- Python SDK
- REST API
index.upsert([{"id": 1,
"field2": "value2",
"field3": 3.0,
"text_vector": [1.0, 2.0, 3.0]
},
{"id": 2,
"field2": "value2",
"field3": 3.0,
"text_vector": [1.1, 2.1, 3.0]
}
])
REST API リファレンス ドキュメント ( POST /api/2.0/vector-search/indexes) を参照してください。
本番運用アプリケーションの場合、 Databricks は personal access token の代わりに serviceプリンシパル を使用することをお勧めします。 パフォーマンスは、クエリごとに最大 100 ミリ秒向上できます。
次のコード例は、サービスプリンシパルを使用してインデックスを更新する方法を示しています。
export SP_CLIENT_ID=...
export SP_CLIENT_SECRET=...
export INDEX_NAME=...
export WORKSPACE_URL=https://...
export WORKSPACE_ID=...
# Set authorization details to generate OAuth token
export AUTHORIZATION_DETAILS='{"type":"unity_catalog_permission","securable_type":"table","securable_object_name":"'"$INDEX_NAME"'","operation": "WriteVectorIndex"}'
# Generate OAuth token
export TOKEN=$(curl -X POST --url $WORKSPACE_URL/oidc/v1/token -u "$SP_CLIENT_ID:$SP_CLIENT_SECRET" --data 'grant_type=client_credentials' --data 'scope=all-apis' --data-urlencode 'authorization_details=['"$AUTHORIZATION_DETAILS"']' | jq .access_token | tr -d '"')
# Get index URL
export INDEX_URL=$(curl -X GET -H 'Content-Type: application/json' -H "Authorization: Bearer $TOKEN" --url $WORKSPACE_URL/api/2.0/vector-search/indexes/$INDEX_NAME | jq -r '.status.index_url' | tr -d '"')
# Upsert data into vector search index.
curl -X POST -H 'Content-Type: application/json' -H "Authorization: Bearer $TOKEN" --url https://$INDEX_URL/upsert-data --data '{"inputs_json": "[...]"}'
# Delete data from vector search index
curl -X DELETE -H 'Content-Type: application/json' -H "Authorization: Bearer $TOKEN" --url https://$INDEX_URL/delete-data --data '{"primary_keys": [...]}'
次のコード例は、パーソナル アクセス トークン (PAT) を使用してインデックスを更新する方法を示しています。
export TOKEN=...
export INDEX_NAME=...
export WORKSPACE_URL=https://...
# Upsert data into vector search index.
curl -X POST -H 'Content-Type: application/json' -H "Authorization: Bearer $TOKEN" --url $WORKSPACE_URL/api/2.0/vector-search/indexes/$INDEX_NAME/upsert-data --data '{"inputs_json": "..."}'
# Delete data from vector search index
curl -X DELETE -H 'Content-Type: application/json' -H "Authorization: Bearer $TOKEN" --url $WORKSPACE_URL/api/2.0/vector-search/indexes/$INDEX_NAME/delete-data --data '{"primary_keys": [...]}'
ベクトル検索エンドポイントのクエリ
ベクトル検索エンドポイントのクエリは、Python SDK、REST API、または SQL vector_search()
AI 関数を使用してのみ実行できます。
エンドポイントをクエリするユーザーがベクトル検索インデックスの所有者でない場合、そのユーザーには次の UC 権限が必要です。
- ベクトル検索インデックスを含むカタログ上のUSE CATALOG。
- ベクトル検索インデックスを含むスキーマに対して USE SCHEMA。
- ベクトル検索インデックスに対するSELECT権限。
デフォルトのクエリタイプは ann
(近似最近隣内) です。ハイブリッドキーワード類似性検索を実行するには、パラメーター query_type
を hybrid
に設定します。ハイブリッド検索では、すべてのテキスト メタデータ列が含まれ、最大 200 件の結果が返されます。
- Python SDK
- REST API
- SQL
# Delta Sync Index with embeddings computed by Databricks
results = index.similarity_search(
query_text="Greek myths",
columns=["id", "text"],
num_results=2
)
# Delta Sync Index using hybrid search, with embeddings computed by Databricks
results3 = index.similarity_search(
query_text="Greek myths",
columns=["id", "text"],
num_results=2,
query_type="hybrid"
)
# Delta Sync Index with pre-calculated embeddings
results2 = index.similarity_search(
query_vector=[0.2, 0.33, 0.19, 0.52],
columns=["id", "text"],
num_results=2
)
REST API リファレンス ドキュメントを参照してください: POST /api/2.0/vector-search/indexes/{index_name}/query。
本番運用アプリケーションの場合、 Databricks は personal access token の代わりに serviceプリンシパル を使用することをお勧めします。 サービスプリンシパルを使用すると、セキュリティとアクセス管理の向上に加えて、クエリごとに最大 100 ミリ秒のパフォーマンスを向上させることができます。
次のコード例は、サービスプリンシパルを使用してインデックスをクエリする方法を示しています。
export SP_CLIENT_ID=...
export SP_CLIENT_SECRET=...
export INDEX_NAME=...
export WORKSPACE_URL=https://...
export WORKSPACE_ID=...
# Set authorization details to generate OAuth token
export AUTHORIZATION_DETAILS='{"type":"unity_catalog_permission","securable_type":"table","securable_object_name":"'"$INDEX_NAME"'","operation": "ReadVectorIndex"}'
# If you are using an route_optimized embedding model endpoint (TODO: link), then you need to have additional authorization details to invoke the serving endpoint
# export EMBEDDING_MODEL_SERVING_ENDPOINT_ID=...
# export AUTHORIZATION_DETAILS="$AUTHORIZATION_DETAILS"',{"type":"workspace_permission","object_type":"serving-endpoints","object_path":"/serving-endpoints/'"$EMBEDDING_MODEL_SERVING_ENDPOINT_ID"'","actions": ["query_inference_endpoint"]}'
# Generate OAuth token
export TOKEN=$(curl -X POST --url $WORKSPACE_URL/oidc/v1/token -u "$SP_CLIENT_ID:$SP_CLIENT_SECRET" --data 'grant_type=client_credentials' --data 'scope=all-apis' --data-urlencode 'authorization_details=['"$AUTHORIZATION_DETAILS"']' | jq .access_token | tr -d '"')
# Get index URL
export INDEX_URL=$(curl -X GET -H 'Content-Type: application/json' -H "Authorization: Bearer $TOKEN" --url $WORKSPACE_URL/api/2.0/vector-search/indexes/$INDEX_NAME | jq -r '.status.index_url' | tr -d '"')
# Query vector search index.
curl -X GET -H 'Content-Type: application/json' -H "Authorization: Bearer $TOKEN" --url https://$INDEX_URL/query --data '{"num_results": 3, "query_vector": [...], "columns": [...], "debug_level": 1}'
# Query vector search index.
curl -X GET -H 'Content-Type: application/json' -H "Authorization: Bearer $TOKEN" --url https://$INDEX_URL/query --data '{"num_results": 3, "query_text": "...", "columns": [...], "debug_level": 1}'
次のコード例は、パーソナル アクセス トークン (PAT) を使用してインデックスをクエリする方法を示しています。
export TOKEN=...
export INDEX_NAME=...
export WORKSPACE_URL=https://...
# Query vector search index with `query_vector`
curl -X GET -H 'Content-Type: application/json' -H "Authorization: Bearer $TOKEN" --url $WORKSPACE_URL/api/2.0/vector-search/indexes/$INDEX_NAME/query --data '{"num_results": 3, "query_vector": [...], "columns": [...], "debug_level": 1}'
# Query vector search index with `query_text`
curl -X GET -H 'Content-Type: application/json' -H "Authorization: Bearer $TOKEN" --url $WORKSPACE_URL/api/2.0/vector-search/indexes/$INDEX_NAME/query --data '{"num_results": 3, "query_text": "...", "columns": [...], "debug_level": 1}'
vector_search()
AI 関数はパブリック プレビュー段階です。
この AI 関数を使用するには、 vector_search
関数を参照してください。
クエリでフィルターを使用する
クエリでは、Delta テーブル内の任意の列に基づいてフィルターを定義できます。 similarity_search
は、指定したフィルターに一致する行のみを返します。 次のフィルターがサポートされています。
フィルター演算子 | 挙動 | 例 |
---|---|---|
| フィルターを無効にします。 キーの末尾は「NOT」である必要があります。 たとえば、値が "red" の "color NOT" は、色が赤でないドキュメントと一致します。 |
|
| フィールド値がフィルター値より小さいかどうかを確認します。 キーの末尾は「<」でなければなりません。 たとえば、値が 200 の "price <" は、価格が 200 未満のドキュメントと一致します。 |
|
| フィールド値がフィルター値以下であるかどうかを確認します。 キーの末尾は「<=」である必要があります。 たとえば、値が 200 の "price <=" は、価格が 200 以下のドキュメントと一致します。 |
|
| フィールド値がフィルター値より大きいかどうかを確認します。 キーの末尾は「>」である必要があります。 たとえば、値が 200 の "price >" は、価格が 200 より大きいドキュメントと一致します。 |
|
| フィールド値がフィルター値以上かどうかを確認します。 キーの末尾は「>=」である必要があります。 たとえば、値が 200 の "price >=" は、価格が 200 以上のドキュメントと一致します。 |
|
| フィールド値がフィルター値のいずれかと一致するかどうかを確認します。 キーには、複数のサブキーを区切る |
|
| 文字列内の空白で区切られたトークンを照合します。以下のコード例を参照してください。 |
|
フィルタ演算子が指定されていません | フィルターは完全一致をチェックします。 複数の値を指定すると、いずれかの値に一致します。 |
|
次のコード例を参照してください。
- Python SDK
- REST API
- LIKE
# Match rows where `title` exactly matches `Athena` or `Ares`
results = index.similarity_search(
query_text="Greek myths",
columns=["id", "text"],
filters={"title": ["Ares", "Athena"]},
num_results=2
)
# Match rows where `title` or `id` exactly matches `Athena` or `Ares`
results = index.similarity_search(
query_text="Greek myths",
columns=["id", "text"],
filters={"title OR id": ["Ares", "Athena"]},
num_results=2
)
# Match only rows where `title` is not `Hercules`
results = index.similarity_search(
query_text="Greek myths",
columns=["id", "text"],
filters={"title NOT": "Hercules"},
num_results=2
)
LIKE
例
{"column LIKE": "apple"}
: 文字列 "apple" と "apple pear" は一致しますが、"pineapple" と "pear" は一致しません。部分文字列 "apple" が含まれていても "pineapple" には一致しないことに注意してください---、"apple pear" のように空白で区切られたトークンと完全に一致するものを探します。
{"column NOT LIKE": "apple"}
その逆を行います。「pineapple」と「pear」は一致しますが、「apple」または「apple pear」は一致しません。
ノートブックの例
このセクションの例では、ベクトル検索Python SDK の使用方法を示します。
LangChain の例
LangChainパッケージとの統合と同様にMosaic AI Vector Searchを使用するには、LangChainでMosaic AI Vector Searchを使用する方法 を参照してください。
次のノートブックは、類似性検索結果を LangChain ドキュメントに変換する方法を示しています。
Python SDK ノートブックを使用したベクトル検索
埋め込みモデルを呼び出すためのノートブックの例
次のノートブックは、埋め込み生成用に Mosaic AI Model Serving エンドポイントを構成する方法を示しています。