Elasticsearchを埋め込みストアとして使用したLangChain4j

LangChain4j (LangChain for Java) には埋め込みストアとして Elasticsearch があります。これを使用して、プレーン Java で RAG アプリケーションを構築する方法を説明します。

Elasticsearch を実際に体験してみましょう。サンプルノートブックを詳しく調べたり、Elastic の無料クラウドトライアルを開始したり、今すぐローカルマシンで Elastic を試したりできます。


前回の投稿では、LangChain4j とは何か、またどのように使用するかについて説明しました。

  • LLMとChatLanguageModelを実装して議論する ChatMemory
  • チャット履歴をメモリに保持して、LLMとの以前の議論の文脈を思い出す

このブログ投稿では、次の方法について説明します。

  • テキスト例からベクトル埋め込みを作成する
  • ベクトル埋め込みをElasticsearch埋め込みストアに保存する
  • 類似ベクトルを検索

埋め込みを作成する

埋め込みを作成するには、使用するEmbeddingModelを定義する必要があります。たとえば、前回の投稿で使用したのと同じミストラル モデルを使用できます。それは ollama で実行されていました:

モデルはテキストからベクトルを生成できます。ここで、モデルによって生成された次元の数を確認できます。

テキストからベクトルを生成するには、以下を使用します。

または、テキスト、価格、発売日などに基づいてフィルタリングできるようにメタデータも提供したい場合は、 Metadata.from()使用できます。たとえば、ここではゲーム名をメタデータ フィールドとして追加しています。

このコードを実行する場合は、 Step5EmbedddingsTest.javaクラスをチェックアウトしてください。

ベクトルを保存するためにElasticsearchを追加する

LangChain4j はメモリ内の埋め込みストアを提供します。これは簡単なテストを実行するのに便利です:

しかし、明らかに、このデータストアはすべてをメモリに保存し、サーバーに無限のメモリがないため、これよりもはるかに大きなデータセットでは機能しません。そのため、代わりに、定義上「弾性」があり、データに合わせてスケールアップおよびスケールアウトできる Elasticsearch に埋め込みを保存することができます。そのためには、Elasticsearch をプロジェクトに追加しましょう。

お気づきのとおり、Elasticsearch TestContainers モジュールもプロジェクトに追加したので、テストから Elasticsearch インスタンスを起動できます。

Elasticsearch を埋め込みストアとして使用するには、LangChain4j のインメモリ データストアから Elasticsearch データストアに切り替えるだけです。

これにより、Elasticsearch のdefaultインデックスにベクトルが保存されます。インデックス名をより意味のあるものに変更することもできます。

このコードを実行する場合は、 Step6ElasticsearchEmbedddingsTest.javaクラスをチェックアウトしてください。

類似ベクトルを検索

類似のベクトルを検索するには、まず、以前使用したのと同じモデルを使用して、質問をベクトル表現に変換する必要があります。すでにそれを行ったので、もう一度これを行うのは難しくありません。この場合、メタデータは必要ないことに注意してください。

質問をこのように表現して検索リクエストを作成し、埋め込みストアに最初の上位ベクトルを見つけるように依頼することができます。

これで、結果を反復処理して、メタデータから取得したゲーム名やスコアなどの情報を出力できます。

予想どおり、最初のヒットは「Out Run」になります。

このコードを実行する場合は、 Step7SearchForVectorsTest.javaクラスをチェックアウトしてください。

舞台裏

Elasticsearch Embedding ストアのデフォルト構成では、バックグラウンドで近似 kNN クエリが使用されます。

ただし、埋め込みストアにデフォルトの構成 ( ElasticsearchConfigurationKnn ) とは別の構成 ( ElasticsearchConfigurationScript ) を提供することでこれを変更できます。

ElasticsearchConfigurationScript実装は、script_score cosineSimilarity関数 を使用して、バックグラウンドで クエリ を実行します。

基本的に、電話をかけるときは:

これにより、次のコードが呼び出されます。

この場合、結果は「順序」の点では変化せず、スコアのみが調整されます。これは、 cosineSimilarity呼び出しでは近似値を使用せず、一致するベクトルごとにコサインを計算するためです。

このコードを実行する場合は、 Step7SearchForVectorsTest.javaクラスをチェックアウトしてください。

まとめ

テキストから埋め込みを簡単に生成する方法と、2 つの異なるアプローチを使用して Elasticsearch で最も近い近傍を保存および検索する方法について説明しました。

  • デフォルトのElasticsearchConfigurationKnnオプションを使用して、近似高速knnクエリを使用する
  • 正確だが遅いscript_scoreクエリをElasticsearchConfigurationScriptオプションとともに使用する

次のステップでは、ここで学んだことを基に、完全な RAG アプリケーションを構築します。

関連記事

最先端の検索体験を構築する準備はできましたか?

十分に高度な検索は 1 人の努力だけでは実現できません。Elasticsearch は、データ サイエンティスト、ML オペレーター、エンジニアなど、あなたと同じように検索に情熱を傾ける多くの人々によって支えられています。ぜひつながり、協力して、希望する結果が得られる魔法の検索エクスペリエンスを構築しましょう。

はじめましょう