本文将向您展示如何构建一个实时RAG(Retrieval-Augmented Generation)管道,以索引Google Drive中的文件,并将其存储到Redis向量存储中。此管道支持增量更新,意味着每次重新运行管道时,只会更新已更改的文档,而不会重新索引所有文档。
设置
首先,我们需要安装必要的软件包并启动Redis Docker镜像。
%pip install llama-index-storage-docstore-redis
%pip install llama-index-vector-stores-redis
%pip install llama-index-embeddings-huggingface
%pip install llama-index-readers-google
# 如果创建一个新的容器
!docker run -d --name redis-stack -p 6379:6379 -p 8001:8001 redis/redis-stack:latest
# 如果启动一个现有的容器
# !docker start -a redis-stack
定义摄取管道
在这里,我们定义摄取管道。给定一组文档,我们将运行句子分割和嵌入转换,然后将它们加载到Redis文档存储和向量存储中。
import os
os.environ["OPENAI_API_KEY"] = "sk-..."
from llama_index.embeddings.huggingface import HuggingFaceEmbedding
from llama_index.core.ingestion import (
DocstoreStrategy,
IngestionPipeline,
IngestionCache,
)
from llama_index.core.ingestion.cache import RedisCache
from llama_index.storage.docstore.redis import RedisDocumentStore
from llama_index.core.node_parser import SentenceSplitter
from llama_index.vector_stores.redis import RedisVectorStore
vector_store = RedisVectorStore(
index_name="redis_vector_store",
index_prefix="vector_store",
redis_url="redis://localhost:6379",
)
cache = IngestionCache(
cache=RedisCache.from_host_and_port("localhost", 6379),
collection="redis_cache",
)
# 可选:如果存在,清除向量存储
if vector_store._index_exists():
vector_store.delete_index()
embed_model = HuggingFaceEmbedding(model_name="BAAI/bge-small-en-v1.5")
pipeline = IngestionPipeline(
transformations=[
SentenceSplitter(),
embed_model,
],
docstore=RedisDocumentStore.from_host_and_port(
"localhost", 6379, namespace="document_store"
),
vector_store=vector_store,
cache=cache,
docstore_strategy=DocstoreStrategy.UPSERTS,
)
定义我们的向量存储索引
我们定义索引以包装底层的向量存储。
from llama_index.core import VectorStoreIndex
index = VectorStoreIndex.from_vector_store(
pipeline.vector_store, embed_model=embed_model
)
加载初始数据
这里我们从LlamaHub加载Google Drive文件中的数据。
from llama_index.readers.google import GoogleDriveReader
loader = GoogleDriveReader()
def load_data(folder_id: str):
docs = loader.load_data(folder_id=folder_id)
for doc in docs:
doc.id_ = doc.metadata["file_name"]
return docs
docs = load_data(folder_id="1RFhr3-KmOZCR5rtp4dlOMNl3LKe1kOA5")
nodes = pipeline.run(documents=docs)
print(f"Ingested {len(nodes)} Nodes")
初始数据上的问答
query_engine = index.as_query_engine()
response = query_engine.query("What are the sub-types of question answering?")
print(str(response))
修改和重新加载数据
修改已摄取的数据并重新运行摄取管道。
docs = load_data(folder_id="1RFhr3-KmOZCR5rtp4dlOMNl3LKe1kOA5")
nodes = pipeline.run(documents=docs)
print(f"Ingested {len(nodes)} Nodes")
新数据上的问答
query_engine = index.as_query_engine()
response = query_engine.query("What are the sub-types of question answering?")
print(str(response))
可能遇到的错误
- 无法连接到Redis:请确保Redis服务已启动并正在运行。
- Google Drive API限额:确保您已正确设置服务账户,并且API调用未超过限额。
- 缺少必要的软件包:安装所有必要的软件包并检查是否有拼写错误。
如果你觉得这篇文章对你有帮助,请点赞,关注我的博客,谢谢!
参考资料: