
Snowflake IntelligenceでCortex Searchサービスからドキュメントを取得する際に、ユーザーごとにフィルタリングするには
データ事業本部の鈴木です。
この記事ではCortex AgentsにCortex Searchサービスをツールとして登録した際に、回答をリクエストしたユーザーに合わせてRAGに使うドキュメントをフィルタリングする方法を確認します。
これにより、同一のベクトルDBからユーザーに合わせてドキュメントを取得し、AIアプリの回答生成をカスタマイズすることができます。
Cortex Searchサービスでは検索時に属性を指定してフィルタリングが可能なため、Cortex SearchサービスのAPIに直接リクエストを送る際は、クライアントアプリからユーザーの権限に合わせて動的にフィルター条件を変えるようなことも可能ですが、Cortex Agentsの場合は現状は固定の条件になるようです。データソース内でフィルタリングをしたい場合は属性を、データソースから分けたい場合は別々にCortex Searchサービスを作り、Cortex Agentsのエージェントはいずれにせよ別に作るのがよさそうです。
はじめに
Cortex Searchサービスを使うと、誰でも簡単にRAG用のベクトルストアと検索サービスを構築できます。
Cortex Searchサービスについては以下で紹介していました。
Cortex SearchサービスはネイティブのAIエージェント機能であるCortex Agentsからツールとして使用ができます。11月にCortex AgentsとSnowflake Intelligenceが一般提供を開始してから数ヶ月経ちました。それ以前はCortex SearchサービスをCOMPLETE関数と合わせてより直接的に使い、StreamlitアプリでRAGアプリを構築したりしていましたが、最近はCortex Agentsにツールとして登録して、Snowflake Intelligenceから使うという動線がメジャーになってきたのではないでしょうか。
Cortex Searchサービスでは検索時に属性を指定してフィルタリングが可能ですが、Cortex Agentsの場合は現状は固定の条件になるようです。今後のアップデートでまた変わっていくと思いますが、現時点で確認した内容をご紹介します。
Cortex SearchサービスのAPIを直接使える場合
まずはStreamlitアプリなどでクライアントアプリを実装するような、Cortex SearchサービスのAPIを直接使える場合を振り返ります。
この場合の実装例は、以下のガイドに紹介されています。
ガイドのrag_access_control_streamlit_ui.pyの以下の箇所に、Streamlitアプリを使用しているユーザーのロールによってCortex Searchサービスから返却するドキュメントをフィルタリングする実装がされています。
# Getting Started with Access Controls for RAGs (Cortex Search)より抜粋
if is_visitor and current_role and current_role != "UNKNOWN":
filter_condition = {"@eq": {"product_department": current_role}}
context_documents = cortex_search_service.search(
query,
columns=["CHUNK"],
filter=filter_condition,
scoring_profile=scoring_profile,
)
filter_applied = f"product_department @eq '{current_role}' (server-validated)"
Cortex Searchサービスでは以下のようにドキュメントがチャンクに分割されて格納されていますが、赤枠のカラムでフィルタリングしています。

Cortex Agentsから使う場合
では続いてCortex Agentsからツールとして使う場合を見ていきます。
1. ツールでの検索フィルターの設定
例えば以下のようにCortex Searchサービスをツールとして登録し、エージェントによる回答生成に使用することができます。

上の画像のエージェントはBICYCLEに関するドキュメントのみを使用するエージェントとして振る舞って欲しいため、BICYCLE_AGENTという名前にしています。
ツール内で属性によるフィルタを行うためには、以下のようにツールのSearch results filtersに属性列とフィルタリング条件を設定できました。

指定できる値は、ガイドを見る限りでは固定値のようでした。
なお、フィルタリング条件を設定しない場合は、Cortex Searchサービスにあるドキュメントをフィルタリングせず利用してくれます。
Snowflake Intelligence上でエージェントによって回答に差異が出せるか確認したかったので、SKI_AGENTも作成しておきました。

2. Snowflake Intelligenceでの回答生成
作成したエージェントに対して「Ski Bootzについて教えて。」と質問をしてみました。
まずはSKIのドキュメントを知らないBICYCLE_AGENTエージェントの回答です。分からない旨を回答してくれました。

続いて、SKIのドキュメントを使えるSKI_AGENTエージェントの回答です。質問に対して回答をしてくれていますね。

以上のように、フィルタリング条件を設定することで簡単に回答生成に使用するドキュメントについて、検索時のフィルタリング設定ができました。
設定方法の使い分け
ここまではCortex Searchサービスの検索結果をフィルタリングすることで、ユーザーごとにRAGに使うドキュメントを変える方法を紹介しました。
一方で、結果のフィルタリングではなく、そもそもCortex Searchサービス自体を別にするのもアリだと思います。
▼ Cortex Searchサービスの検索結果をフィルタリングするパターン

▼ Cortex Searchサービス自体を分けるパターン

特に明確な使い分けはありませんが、個人的には、機密度の違いなどでより確実に分けたいときはCortex Searchサービスも分ける方が安全と考えています。
Cortex Searchサービスを意図せず間違ったエージェントに設定してしまうことはありえるものの、属性カラムによるフィルタリングの方が複雑で、設定間違いが起こりやすいかなと思います。
単にエージェントの振る舞いを変えたいような場合には、属性列によるフィルタリングの方が便利に使えそうですね。
最後に
Snowflake IntelligenceでCortex Searchサービスからドキュメントを取得する際に、ユーザーごとにRAGで使うドキュメントを変える方法について、現時点での設定方法を見てみました。
今回ご紹介した方法はSnowflakeのロールに対するドキュメント取得のフィルタリング制御となります。
なお、ドキュメントがもともとSnowflake外のSaaSなどにある場合、「ユーザーによってそのSaaSの設定に合わせて権限制御したい」というような気持ちになりますが、SaaS側のドキュメントへのアクセス制御状況をリアルタイムにドキュメント検索結果のフィルタリング条件に反映しないといけないため、Snowflakeに限らず難しいと思います。
このような理由からも、フィルタリング条件はSnowflakeのロール設計と合わせて考えると設計しやすそうです。







