基于Phoenix项目实现Milvus与LlamaIndex结合的搜索检索系统评估与优化
概述
在现代AI应用中,构建高效的文档问答系统是一个常见需求。本文将通过Arize AI的Phoenix项目,展示如何评估和优化基于Milvus向量数据库和LlamaIndex框架构建的搜索检索系统。
系统架构
该文档问答系统采用五层架构设计:
- 用户查询层:接收用户关于Arize产品的自然语言问题
- 嵌入层:使用OpenAI的text-embedding-ada-002模型将查询转换为向量表示
- 检索层:通过Milvus向量数据库执行相似度搜索,找出知识库中最相关的文档片段
- 响应生成层:使用gpt-3.5-turbo模型结合查询和检索结果生成回答
- 反馈层:收集用户对回答质量的反馈
Phoenix项目为这个系统提供了关键的可观测性能力,能够捕获和分析以下关键数据:
- 查询向量
- 检索到的上下文及其相似度分数
- 生成的最终响应
环境准备
依赖安装
系统需要以下关键组件:
- Phoenix:提供LLM应用的可观测性能力
- LlamaIndex:构建检索增强生成(RAG)应用的核心框架
- Milvus:高性能向量数据库
- OpenAI API:用于嵌入和响应生成
%pip install -Uq gcsfs "langchain>=0.0.334" "arize-phoenix[evals,llama-index,embeddings]" "openai>=1" 'httpx<0.28'
!pip install pymilvus==2.2.15
!pip install --upgrade --force-reinstall grpcio==1.56.0
数据准备
系统使用Arize产品文档作为知识库,这些文档已预先处理并存储在云端:
url = "http://storage.googleapis.com/arize-assets/xander/milvus-workshop/milvus_dataset.json"
with urllib.request.urlopen(url) as response:
buffer = response.read()
data = json.loads(buffer.decode("utf-8"))
rows = data["rows"]
Milvus向量数据库配置
Zilliz Cloud设置
- 创建Zilliz Cloud账户
- 建立组织和项目
- 添加标准集群(提供100美元免费额度)
- 获取公共端点和访问令牌
ENDPOINT = getpass(prompt="请输入Zilliz Cloud的公共端点: ")
TOKEN = getpass(prompt="请输入Zilliz Cloud的访问令牌: ")
向量存储初始化
vector_store = MilvusVectorStore(
uri=ENDPOINT,
token=TOKEN,
collection_name="colab_collection",
dim=1536, # text-embedding-ada-002的向量维度
embedding_field="embedding",
doc_id_field="doc_id",
overwrite=True,
)
知识库数据加载
将预处理好的文档数据转换为TextNode格式并存入Milvus:
nodes = []
for row in rows:
node = TextNode(
embedding=row["embedding"],
text=row["text"],
id_=row["id"],
relationships={NodeRelationship.SOURCE: RelatedNodeInfo(node_id=row["doc_id"])},
)
nodes.append(node)
vector_store.add(nodes)
问答系统实现
服务初始化
配置LlamaIndex的核心组件,包括LLM、嵌入模型和回调处理器:
callback_handler = OpenInferenceCallbackHandler()
service_context = ServiceContext.from_defaults(
llm=OpenAI(model_name="gpt-3.5-turbo", temperature=0),
embed_model=OpenAIEmbedding(model="text-embedding-ada-002"),
callback_manager=CallbackManager(handlers=[callback_handler]),
)
index = VectorStoreIndex.from_vector_store(vector_store, service_context=service_context)
query_engine = index.as_query_engine()
查询示例
queries = [
"如何获取Arize API密钥?",
"能否通过API创建监控器?",
"时间戳需要什么格式?",
"Arize平台的价格是多少?"
]
for query in queries:
response = query_engine.query(query)
print(f"问题: {query}")
print(f"回答: {response}")
print("-"*50)
数据分析与评估
数据加载与预处理
Phoenix使用OpenInference格式存储推理数据,主要包含以下字段:
- 查询ID和时间戳
- 查询文本和嵌入向量
- 生成的响应
- 检索到的文档ID和相似度分数
- 用户反馈(点赞/点踩)
- GPT-4生成的相关性评估
query_data_buffer = callback_handler.flush_query_data_buffer()
sample_query_df = as_dataframe(query_data_buffer)
嵌入空间对齐
由于查询和文档的嵌入分布不同,需要进行中心化处理:
database_centroid = database_df["text_vector"].mean()
database_df["text_vector"] = database_df["text_vector"].apply(lambda x: x - database_centroid)
query_centroid = query_df[":feature.[float].embedding:prompt"].mean()
query_df[":feature.[float].embedding:prompt"] = query_df[":feature.[float].embedding:prompt"].apply(lambda x: x - query_centroid)
LLM辅助评估
除了传统的余弦相似度和欧氏距离外,还可以使用GPT-4评估检索质量:
def evaluate_relevance(query, document):
prompt = f"""
判断以下文档是否与查询相关:
查询: {query}
文档: {document}
请回答'relevant'或'irrelevant'
"""
response = openai.ChatCompletion.create(
model="gpt-4",
messages=[{"role": "user", "content": prompt}],
temperature=0
)
return response.choices[0].message.content.lower()
系统优化方向
通过Phoenix的可观测性能力,可以识别以下优化机会:
- 文档覆盖缺口:发现用户常问但文档未覆盖的问题
- 低质量响应:识别用户反馈差的回答集群
- 检索失败:通过多种指标检测相关性低的检索结果
- 嵌入空间优化:分析查询和文档在嵌入空间的分布
结论
本文展示了如何利用Phoenix项目对基于Milvus和LlamaIndex构建的文档问答系统进行全面评估和优化。关键点包括:
- 完整的RAG系统实现流程
- 使用Zilliz Cloud托管Milvus向量数据库
- Phoenix提供的强大可观测性能力
- 多种评估方法的综合应用
这种架构和评估方法可以推广到各种企业知识管理场景,帮助团队构建更智能、更可靠的问答系统。
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考