Milvusテキスト埋め込み機能とLangChainの連携

Open In Colab GitHub Repository

このガイドでは、Milvus 2.6のテキスト埋め込み機能(Data In Data Out)をLangChainと連携させる方法を説明します。この機能により、Milvusサーバは生のテキストを自動的にベクトル埋め込みに変換し、クライアント側のコードを簡素化し、APIキー管理を一元化することができます。

Milvusは世界で最も先進的なオープンソースのベクトルデータベースで、埋め込み類似検索とAIアプリケーションをサポートするために特別に構築されています。LangChainは、大規模言語モデル(LLM)を利用したアプリケーション開発のためのフレームワークです。Milvusのテキスト埋め込み機能を統合することで、LangChainアプリケーションにおいて、よりシンプルで効率的なベクトル検索ソリューションを実現することができます。

前提条件

このチュートリアルを実行する前に、以下の依存関係がインストールされていることを確認してください:

! pip install --upgrade langchain-milvus langchain-core langchain-openai

Google Colabをお使いの場合、インストールした依存関係を有効にするために、ランタイムを再起動する必要があります(画面上部の "Runtime "メニューをクリックし、ドロップダウンメニューから "Restart session "を選択してください)。

Milvusサーバーの設定

重要:テキスト埋め込み機能(Data In Data Out)はMilvus Serverでのみ使用可能です。Milvus Liteはこの機能をサポートしていません。Docker/KubernetesでデプロイされたMilvusサーバを使用する必要があります。

テキスト埋め込み機能を利用する前に、Milvusサーバに埋め込みサービスプロバイダ用のクレデンシャルを設定する必要があります。

credentialの下にキーを宣言します:

APIキーは1つでも複数でも構いません。

# milvus.yaml

credential:
  apikey_dev:
    apikey: <YOUR_OPENAI_API_KEY>

どのキーをOpenAIの呼び出しに使うかをMilvusに伝える。

同じファイルで、OpenAIプロバイダが使用したいラベルを指定します。

function:
  textEmbedding:
    providers:
      openai:
        credential: apikey_dev
        # url: https://api.openai.com/v1/embeddings   # (optional) custom url

その他の設定方法については、Milvus Embedding Functionのドキュメントを参照してください。

Milvusサービスの起動

Milvusサーバが起動しており、エンベッディング機能が有効になっていることを確認します。DockerまたはKubernetesを使用してMilvusサーバをデプロイすることができます。Milvus Liteはテキストエンベッド機能をサポートしていません

エンベッディングについてクライアントサイドとサーバサイド

使い方の前に、まず2つのエンベッディングアプローチの違いを理解しましょう。

LangChainのEmbeddings クラスを使った埋め込み(クライアントサイド)

従来のLangChainアプローチでは、Embeddings クラスを使ってクライアントサイドでエンベッディングを生成します。アプリケーションはこのクラスのembed_query メソッドを使ってエンベッディングAPIを呼び出し、生成されたベクトルをmilvusに格納します。

from langchain_openai import OpenAIEmbeddings
from langchain_milvus import Milvus

# Generate embedding on client side
embeddings = OpenAIEmbeddings()
vector = embeddings.embed_query("Hello, world!")
# [0.123, -0.456, ...] A vector of floats

vector_store = Milvus(
    embedding_function=embeddings,
    connection_args={"uri": "http://localhost:19530"},
    collection_name="traditional_approach_collection",
)

シーケンス図

特徴

  • クライアントが直接エンベッディングAPIを呼び出す
  • クライアント側でAPIキーの管理が必要
  • データの流れテキスト → クライアント → 埋め込みAPI → ベクトル → milvus

Milvusテキスト埋め込み機能(サーバ側データインデータアウト)

Milvus2.6のテキスト埋め込み機能(Data In Data Out)は、Milvusサーバーが生のテキストを自動的にベクトル埋め込みに変換する機能です。クライアントはテキストを入力するだけで、Milvusが自動的に埋め込みを生成します。

シーケンス図

特徴

  • Milvusサーバが埋め込みAPIを呼び出す
  • APIキーはサーバ側で一元管理
  • データの流れテキスト → Milvus → エンベッディングAPI → ベクター(Milvusに格納)

2つの方式の比較

特徴LangChain埋め込み(クライアント側)Milvusテキスト埋め込み機能(サーバサイド)
処理場所クライアントアプリケーションMilvusサーバー
APIコールクライアントが直接埋め込みAPIを呼び出すMilvusサーバーがエンベッディングAPIを呼び出す
APIキーの管理クライアント側での管理が必要サーバ側で一元管理、よりセキュア
コードの複雑さクライアント側でAPIキーとコールを管理する必要があるMilvusのコンフィギュレーションで一度だけ設定する必要がある。
使用例- 埋め込み処理をクライアント側で制御したい
- 埋め込み結果をクライアント側でキャッシュしたい
- 複数のエンベッディングモデルの切り替えに対応したい
- クライアント側コードの簡素化
- サーバー側でAPIキーを一元管理したい
- 大量のドキュメントを一括処理したい
- クライアント側での外部APIとのやり取りを減らしたい
- BM25のようなMilvusのビルトイン機能と組み合わせたい
Milvusのバージョン要件全てのバージョン(Milvus Liteを含む)Milvus Liteには対応しておりません。

このチュートリアルでは、Milvus 2.6から導入された新機能であり、クライアントサイドのコードを大幅に簡素化し、セキュリティを向上させることができるMilvusサーバーサイドのテキスト埋め込み関数(Data In Data Out)メソッドを主に紹介します。

テキスト埋め込み関数の使用

例1: サーバ側の埋め込みのみ

これは最も単純な使用例で、埋め込みの生成を完全にMilvusサーバに依存します。クライアントは埋め込み関数を必要としません。

from langchain_milvus import Milvus
from langchain_milvus.function import TextEmbeddingBuiltInFunction
from langchain_core.documents import Document

# Create Text Embedding Function
text_embedding_func = TextEmbeddingBuiltInFunction(
    input_field_names="text",  # Input field name (field containing text)
    output_field_names="vector",  # Output field name (field storing vectors)
    dim=1536,  # Vector dimension (must specify)
    params={
        "provider": "openai",  # Service provider
        "model_name": "text-embedding-3-small",  # Model name
        "credential": "apikey_dev",    # Optional: use credential label configured in milvus.yaml
    },
)

# Create Milvus vector store
# Note: embedding_function=None, because embedding is done on server side
vector_store = Milvus(
    embedding_function=None,  # Do not use client-side embedding
    builtin_function=text_embedding_func,
    connection_args={"uri": "http://localhost:19530"},
    collection_name="my_collection",
    # consistency_level="Strong",    # Strong consistency level, default is "Session"
    auto_id=True,
    # drop_old=True,  # If you want to drop old collection and create a new one
)

connection_args の場合:

  • Milvus Serverを使用する必要があります:テキスト埋め込み機能はMilvus Serverのみで、Milvus Liteには対応していません。
  • http://localhost:19530 (ローカルDockerデプロイ) またはhttp://your-server:19530 (リモートサーバ) などのサーバURIを使用してください。
  • Zilliz Cloudを利用する場合は、Public Endpointをuri とし、token パラメータを設定してください。

ドキュメントを追加する場合、テキストを提供するだけでよく、事前にベクトルを計算する必要はありません。Milvusは自動的にOpenAI APIを呼び出して埋め込みを生成します。

# Add documents (only need to provide text, no need to pre-compute vectors)
documents = [
    Document(page_content="Milvus simplifies semantic search through embeddings."),
    Document(
        page_content="Vector embeddings convert text into searchable numeric data."
    ),
    Document(
        page_content="Semantic search helps users find relevant information quickly."
    ),
]

vector_store.add_documents(documents)
[462726375729313252, 462726375729313253, 462726375729313254]

検索時には、テキストクエリを直接使用することで、Milvusが自動的にクエリテキストを検索用のベクトルに変換します。

# Search (directly use text query)
results = vector_store.similarity_search(
    query="How does Milvus handle semantic search?", k=2
)

for doc in results:
    print(f"Content: {doc.page_content}")
    print(f"Metadata: {doc.metadata}\n")
WARNING: All log messages before absl::InitializeLog() is called are written to STDERR
I0000 00:00:1765186679.227345 12227536 fork_posix.cc:71] Other threads are currently calling into gRPC, skipping fork() handlers


Content: Milvus simplifies semantic search through embeddings.
Metadata: {'pk': 462726375729313252}

Content: Semantic search helps users find relevant information quickly.
Metadata: {'pk': 462726375729313254}

セマンティック検索(テキスト埋め込み)とキーワード検索(BM25)を組み合わせることで、より強力なハイブリッド検索が可能になります。セマンティック検索はクエリの意図を理解することに優れ、キーワード検索は完全一致に優れています。

from langchain_milvus import Milvus
from langchain_milvus.function import TextEmbeddingBuiltInFunction, BM25BuiltInFunction

# Text Embedding Function (semantic search)
text_embedding_func = TextEmbeddingBuiltInFunction(
    input_field_names="text",
    output_field_names="vector_dense",
    dim=1536,
    params={
        "provider": "openai",
        "model_name": "text-embedding-3-small",
    },
)

# BM25 Function (keyword search)
bm25_func = BM25BuiltInFunction(
    input_field_names="text",
    output_field_names="vector_sparse",
)

# Create Milvus vector store
vector_store = Milvus(
    embedding_function=None,
    builtin_function=[text_embedding_func, bm25_func],
    connection_args={"uri": "http://localhost:19530"},
    vector_field=["vector_dense", "vector_sparse"],
    collection_name="hybrid_search_collection",
    # consistency_level="Strong",    # Strong consistency level, default is "Session"
    auto_id=True,
    # drop_old=True,  # If you want to drop old collection and create a new one
)

# Add documents
documents = [
    Document(page_content="Machine learning and artificial intelligence"),
    Document(page_content="The cat sat on the mat"),
]

vector_store.add_documents(documents)
[462726375729313255, 462726375729313256]

WeightedRanker 、セマンティック検索とキーワード検索のウェイトをコントロールする。密なウェイトを高くすると、結果はより意味的類似性に偏り、疎なウェイトを高くすると、結果はよりキーワードマッチングに偏る。

# Hybrid search, use WeightedRanker to control weights
# 70% semantic search, 30% keyword search
results = vector_store.similarity_search(
    query="AI technology",
    k=2,
    ranker_type="weighted",
    ranker_params={"weights": [0.7, 0.3]},
)

# If you want to be more biased towards keyword matching, you can adjust weights
# 30% semantic search, 70% keyword search
results_keyword_focused = vector_store.similarity_search(
    query="cat mat",
    k=2,
    ranker_type="weighted",
    ranker_params={"weights": [0.3, 0.7]},
)
results
[Document(metadata={'pk': 462726375729313255}, page_content='Machine learning and artificial intelligence'),
 Document(metadata={'pk': 462726375729313256}, page_content='The cat sat on the mat')]
results_keyword_focused
[Document(metadata={'pk': 462726375729313256}, page_content='The cat sat on the mat'),
 Document(metadata={'pk': 462726375729313255}, page_content='Machine learning and artificial intelligence')]

まとめ

おめでとうございます!Milvusのテキスト埋め込み機能(Data In Data Out)をLangChainで利用する方法を学びました。埋め込み生成をサーバサイドに移すことで、クライアントサイドのコードを簡素化し、APIキーを一元管理し、ハイブリッド検索を簡単に実装することができます。テキスト埋め込み機能とBM25を組み合わせることで、milvusは強力なベクトル検索機能を提供します。