Dissiper les idées reçues sur la vitesse d’insertion des données dans Milvus
De nombreux utilisateurs qui s’appuient sur LangChain ou LlamaIndex pour leurs étapes d’API pratiques et plus courtes pourraient penser que « l’insertion de données dans Milvus est lente ». Cependant, cette perception provient souvent d’un survol des étapes détaillées du processus.
Les étapes cachées
Lors de l’utilisation de LangChain ou de LlamaIndex, ces bibliothèques convertissent les données non structurées (comme les textes, les images ou les sons) en vecteurs à l’aide de modèles d’embedding. Elles insèrent ensuite ces vecteurs dans Milvus Lite. Les bibliothèques simplifient ce processus complexe en gérant pour vous plusieurs étapes en coulisses.
Cette abstraction peut créer l’illusion que le processus d’insertion des données prend beaucoup de temps.
Le gouffre temporel : la génération d’embeddings
Le temps moyen passé à générer des embeddings à partir de données non structurées est nettement plus long que le temps nécessaire pour insérer des données dans Milvus. La lenteur perçue est souvent due au processus gourmand en calcul de transformation des données en représentations vectorielles, plutôt qu’à l’étape d’insertion des données.
Pour illustrer la différence entre les temps de génération d’embeddings et d’insertion de données, je montrerai un exemple dans ce blog où le temps moyen d’embedding est d’environ 5 secondes. En revanche, le temps moyen d’insertion dans la base de données vectorielle Milvus n’est que d’environ un dixième de seconde. Le code complet est sur mon GitHub.
En d’autres termes, environ 97 % du temps d’« insertion Milvus » observé dans LangChain ou LlamaIndex est consacré à la génération d’embeddings, tandis qu’environ 3 % est consacré à l’étape réelle d’insertion dans la base de données.
J’ai montré dans un blog précédent comment se connecter à Milvus Lite en utilisant soit LlamaIndex, soit LangChain.
Dans les sections suivantes, je couvrirai :
Exemple de code LlamaIndex pour insérer des données dans Milvus
Exemple de code LangChain pour insérer des données dans Milvus
Exemple de code de l’API Pymilvus pour insérer des données dans Milvus
Exemple de code LlamaIndex pour insérer des données dans Milvus
Voici un exemple de code dans LlamaIndex.
from llama_index.core import (
ServiceContext,
StorageContext,
VectorStoreIndex,
)
from llama_index.embeddings.huggingface import HuggingFaceEmbedding
from llama_index.vector_stores.milvus import MilvusVectorStore
import time
# Define the embedding model.
service_context = ServiceContext.from_defaults(
# LlamaIndex local: translates to the same location as default HF cache.
embed_model="local:BAAI/bge-large-en-v1.5",
)
# Create a Milvus collection from the documents and embeddings.
EMBEDDING_DIM = 1024
vectorstore = MilvusVectorStore(
uri="./milvus_llamaindex.db",
dim=EMBEDDING_DIM,
# Override LlamaIndex default values for Milvus.
consistency_level="Eventually",
drop_old=True,
index_params = {
"metric_type": "COSINE",
"index_type": "AUTOINDEX",
"params": {},}
)
storage_context = StorageContext.from_defaults(
vector_store=vectorstore
)
llamaindex = VectorStoreIndex.from_documents(
lli_docs[:1],
storage_context=storage_context,
service_context=service_context
)
Exemple de code LangChain pour insérer des données dans Milvus
Voici un exemple de code dans LangChain.
from langchain_milvus import Milvus
from langchain_huggingface import HuggingFaceEmbeddings
from langchain.text_splitter import RecursiveCharacterTextSplitter
import time
# Define the embedding model.
model_name = "BAAI/bge-large-en-v1.5"
model_kwargs = {'device': 'cpu'}
encode_kwargs = {'normalize_embeddings': True}
embed_model = HuggingFaceEmbeddings(
model_name=model_name,
model_kwargs=model_kwargs,
encode_kwargs=encode_kwargs
)
EMBEDDING_DIM = embed_model.dict()['client'].get_sentence_embedding_dimension()
# Define the chunking strategy.
text_splitter = RecursiveCharacterTextSplitter(chunk_size=512, chunk_overlap=51)
# Create a Milvus collection from the documents with chunking and embeddings.
start_time = time.time()
docs = text_splitter.split_documents(docs)
vectorstore = Milvus.from_documents(
documents=docs,
embedding=embed_model,
connection_args={"uri": "./milvus_demo.db"},
# Override LangChain default values for Milvus.
consistency_level="Eventually",
drop_old=True,
index_params = {
"metric_type": "COSINE",
"index_type": "AUTOINDEX",
"params": {},}
)
Exemple de code d’API Pymilvus pour insérer des données dans Milvus
En utilisant directement les appels d’API Pymilvus, montrons ce qui se passe réellement en coulisses derrière ces codages LangChain et LlamaIndex courts et pratiques.
Les exemples ci-dessus utilisaient les pages de documentation Milvus téléchargées directement depuis Internet. Pour montrer la différence entre les temps d’embedding et les temps d’insertion, j’utiliserai ci-dessous un modèle d’embedding multimodal open source pour 1) embedder à la fois des images et des textes et 2) insérer les vecteurs denses dans Milvus.
import pymilvus
import requests
from io import BytesIO
# Run this in small batches to avoid memory issues.
BATCH_SIZE = 10
# Batch embed text and images and insert data into Milvus.
batch_embedding_times = []
batch_insert_times = []
for i in range(0, 300, BATCH_SIZE):
batch_images = []
batch_texts = []
batch_urls = []
for j in range(BATCH_SIZE):
if i + j < len(image_texts):
text = image_texts[i + j]
url = image_urls[i + j]
with Image.open(f"./images/{url}.jpg") as img:
batch_images.append(img.copy())
batch_texts.append(text)
batch_urls.append(url)
# STEP 1. EMBEDDING INFERENCE FOR TEXT AND IMAGES.
start_time = time.time()
image_embeddings, text_embeddings = embedding_model(
batch_images=batch_images,
batch_texts=batch_texts)
end_time = time.time()
# print(f"Embedding time for batch size {len(batch_images)}: ", end="")
# print(f"{np.round(end_time - start_time, 2)} seconds")
batch_embedding_times.append(end_time - start_time)
# STEP 2. INSERT CHUNK LIST INTO MILVUS OR ZILLIZ.
chunk_dict_list = []
# Create chunk dict_list.
for chunk, img_url, img_embed, text_embed in zip(
batch_texts,
batch_urls,
image_embeddings, text_embeddings):
chunk_dict = {
'chunk': chunk,
'image_filepath': img_url,
'text_vector': text_embed,
'image_vector': img_embed
}
chunk_dict_list.append(chunk_dict)
start_time = time.time()
try:
col.insert(data=chunk_dict_list)
except:
print(f"Insert error: {img_url}")
end_time = time.time()
# print(f"Insert time for {len(chunk_dict_list)} vectors: ", end="")
# print(f"{np.round(end_time - start_time, 4)} seconds")
batch_insert_times.append(end_time - start_time)
col.flush()
# Calculate the average embedding time.
average_time = np.mean(batch_embedding_times)
print(f"Average embedding time: {round(average_time,2)} seconds")
# Calculate the average insert time.
average_time = np.mean(batch_insert_times)
print(f"Average insert time: {round(average_time,2)} seconds")
Voici la sortie des temps d’embedding par lot.
Voici la sortie des temps d’insertion des données par lot dans Milvus.
Le temps moyen d’embedding était d’environ 5 secondes, et le temps moyen d’insertion dans la base de données vectorielle Milvus était d’environ un dixième de seconde. Cela signifie qu’environ 97 % du temps total était consacré à la génération des embeddings, tandis qu’environ 3 % était consacré à l’insertion dans la base de données.
Comme vous pouvez le voir, l’étape d’embedding est celle qui prend le plus de temps !
Ressources et lectures complémentaires
Continuer à lire

Why Context Engineering Is Becoming the Full Stack of AI Agents
Discover how context engineering unifies prompts, RAG, and tools to build smarter, production-ready AI agents powered by Milvus.

What Exactly Are AI Agents? Why OpenAI and LangChain Are Fighting Over Their Definition?
AI agents are software programs powered by AI that can perceive their environment, make decisions, and take actions to achieve a goal—often autonomously.

Legal Document Analysis: Harnessing Zilliz Cloud's Semantic Search and RAG for Legal Insights
Enhance legal document analysis with Zilliz Cloud’s Semantic Search and RAG. Improve accuracy, efficiency, and scalability for contracts, case law, and compliance.



