AI知识库 AI知识库

53AI知识库

学习大模型的前沿技术与行业应用场景


在笔记本电脑上,10行代码!实现本地大模型RAG智能问答(1)
发布日期:2024-04-23 07:21:17 浏览次数: 1864


但是,AnythingLLM目前支持的嵌入模型(Embedding Model)很有限。此前通过Ollama运行的嵌入模型nomic-embed-text,对于中文的支持不是特别好,因此导致对中文文档的检索和问答效果欠佳。


本文介绍使用LlamaIndex框架,只要通过10行代码,就可以实现更好地本地大模型知识库RAG智能问答,且具备更好的可扩展性。


1. 了解LlamaIndex


LlamaIndex是一个数据框架,专门为构建检索增强生成(RAG)系统而设计,基于企业数据构建生产级LLM应用


Source: https://www.llamaindex.ai/


LlamaIndex提供了实现RAG的一系列组件,包括:

  • 数据连接器(Data connectors),对接API、PDF、SQL等来源获取数据

  • 数据索引(Data indexes),对数据进行结构化,使其易于为LLM高效使用

  • 检索引擎(Query engines,用于知识增强输出的强大检索接口

  • 聊天引擎(Chat engines),用于与数据进行多轮消息交互的对话接口

  • 数据代理(Data agents),从简单的辅助功能到API集成等更多功能

  • 应用程序集成(Application integrations ),集成LangChain、Flask、Docker、ChatGPT等生态系统




Source:Build a chatbot with custom data sources, powered by LlamaIndex


上图展示LlamaIndex框架如何实现RAG,其过程包括两个阶段:


  • 索引阶段:这是LlamaIndex构建知识库的过程,首先提取数据并将其转换为文档(Documents),然后解析这些文档中的元数据(如文本、关系等)到节点(Nodes),并基于块(Chunks)创建可查询的索引。

  • 查询阶段:从知识库中检索相关上下文,并提供给大模型进行回答。在这一阶段,大模型可以获取和使用其原本训练数据中未包含的数据,从而增强回答的准确性。


2. 安装LlamaIndex和LLM组件


我们可以通过以下一条命令,安装LlamaIndex的主要组件。其中,包括常用的llama-index-core组件。


pip install llama_index


由于我们不使用OpenAI的API,而是通过Ollama使用本地部署的LLM,因此我们还需要安装相关组件。


pip install llama_index.llms.ollama


关于如何安装和使用Ollama,请参考我此前的文章:在笔记本电脑上,轻松使用Gemma模型》。


3. 选择嵌入模型


们这次选择一个对中文支持更好的嵌入模型,智源研究院发布的BAAI/bge-small-zh-v1.5


LlamaIndex通过与LangChain的集成,可以从HuggingFace下载和使用各种模型。所以,我们先安装LangChain,后面会用到其中的langchain_community组件。它提供与第三方如LlamaIndex的集成。


pip install langchain


由于运行时要从HuggingFace下载模型,请预先在电脑上设置HuggingFace的国内镜像地址hf-mirror.com。


export HF_ENDPOINT=https://hf-mirror.com


5. 知识库管理


为了演示方便,我们简化了知识库管理的功能。我们只需要把相应的PDF、DOCX文档放在指定的文件夹下。


比如,我创建一个文件夹,名称“data”。


我把之前写《大卫说流程》系列文章的DOCX文件,复制到data文件夹中。后面我可以根据这些文章中的内容,向大模型提问。你可以使用你自己电脑上的任何知识文档。


6. 十行代码实现RAG


现在,创建了一个文件app.py,编写如下10行Python代码,并确保把app.py 和“data“放在同一个目录下。


from llama_index.core import VectorStoreIndex, SimpleDirectoryReader, Settingsfrom llama_index.llms.ollama import Ollama
# 配置ollama的LLM模型,这里我们用gemma:7bSettings.llm = Ollama(model="gemma", request_timeout=600.0)
# 配置HuggingFaceEmbeddings嵌入模型,这里我们用BAAI/bge-small-zh-v1.5from langchain_community.embeddings import HuggingFaceEmbeddingsSettings.embed_model = HuggingFaceEmbeddings(model_name="BAAI/bge-small-zh-v1.5")
# 将data文件夹下的文档建立索引documents = SimpleDirectoryReader("data").load_data()index = VectorStoreIndex.from_documents(documents)
# 创建问答引擎,并提一个简单的问题query_engine = index.as_query_engine()response = query_engine.query("流程有哪三个特征?")print(response)


以上代码,我给出了注释。重点说一下LLM和嵌入模型的选择与配置。


1)LLM配置


LLM选用的是谷歌最新开源的gemma:7b模型。该模型效果较好,在我的笔记本电脑上推理的时间比较长,所以要把超时设置得比较大,600秒。


若使用更小的模型,例如gemma:2b,推理速度更快,但是我发现效果会差很多。你也可以尝试Ollama提供的qwen:7b、llama2:7b等模型。


2)嵌入模型配置


嵌入模型选用的是BAAI/bge-small-zh-v1.5。如果你用的是GPU服务器,而不是笔记本电脑,在性能足够支撑的情况下,推荐采用规模更大的模型,比如最新的BAAI/bge-m3。同样,LLM也推荐采用百亿参数以上的开源模型。


3)文档问答


在代码中可以看到,我针对《大卫说流程》系列文章中的这一篇《流程的内在逻辑与价值分析》,提了一个简单的问题:“流程有哪三个特征”。


如果大模型RAG运行良好的话,应能回答出”目标性、重复性、过程性“这三个特征。你需要针对你所选用的知识文档来提问。


现在,可以通过以下命令运行程序。


python app.py


由于运行时需要下载嵌入模型,对文档进行索引,在笔记本电脑上运行需要等待数分钟,请保持耐心:-)


你也可以在app.py开头添加如下代码,观察输出的日志信息。


import loggingimport sys# 增加日志信息logging.basicConfig(stream=sys.stdout, level=logging.DEBUG)logging.getLogger().addHandler(logging.StreamHandler(stream=sys.stdout))


等待片刻后,终端上会输出大模型给出的回答。

可以看出,大模型获取到了本地文档中的上下文信息,并给出了准确的回答!


7. 选用Moonshot API


在笔记本电脑上运行gemma:7b比较慢,我们可以尝试使用月之暗面的Moonshot API,更快地实现文档问答


这与直接使用kimi的不同点在于,我们无需将全部文档发给kimi。而是将数据全部保存在本地,仅仅把检索到的信息发给大模型来回答。这样更好地保护数据安全。


请将app.py代码中,原本使用Ollama的LLM的部分,更换为如下代码。


# 使用moonshot的apifrom langchain_openai import ChatOpenAIllm_langchain = ChatOpenAI(openai_api_base="https://api.moonshot.cn/v1/",     openai_api_key="input your key here",model_name="moonshot-v1-32k",)Settings.llm = llm_langchain


请提前在Moonshot开放平台(https://platform.moonshot.cn/)申请API key,输入在以上代码中。


运行app.py后的结果如下。


可以看到,针对文档中有明确答案的问题,本地运行的gemma:7b相比Moonshot API的回答生成,也毫不逊色。


8. 构建Web应用


LlamaIndex提供了API,以及Python和TypeScript开发包,可以与Flask、Streamlit、Chainlit等框架集成,从而很方便地创建类似ChatGPT的Web界面,进一步构建生产级的RAG系统。


作为示例,我们采用Streamlit,修改app.py并增加相关代码,构建一个简单的Web UI,方便进行多轮对话。以下是完整的示例代码,总共也才需要50行!


from llama_index.core import VectorStoreIndex, SimpleDirectoryReader, ServiceContext, Documentfrom llama_index.llms.ollama import Ollama
# 配置ollama的LLM模型,这里我们用gemma:7bllm = Ollama(model="gemma", request_timeout=600.0)
# 配置HuggingFaceEmbeddings嵌入模型,这里我们用BAAI/bge-small-zh-v1.5from langchain_community.embeddings import HuggingFaceEmbeddingsembed_model = HuggingFaceEmbeddings(model_name="BAAI/bge-small-zh-v1.5")
# 配置Streamlit Web应用import streamlit as st
st.set_page_config(page_title="本地大模型知识库RAG应用", page_icon="?", layout="centered", initial_sidebar_state="auto", menu_items=None)st.title("本地大模型知识库RAG应用")st.info("By 大卫", icon="?")
if "messages" not in st.session_state.keys(): # 初始化聊天历史记录st.session_state.messages = [{"role": "assistant", "content": "关于文档里的内容,请随便问"}]
@st.cache_resource(show_spinner=False)def load_data():with st.spinner(text="Loading and indexing the Streamlit docs – hang tight! This should take 1-2 minutes."):reader = SimpleDirectoryReader(input_dir="./data", recursive=True) # 将data文件夹下的文档建立索引docs = reader.load_data()service_context = ServiceContext.from_defaults(llm=llm,embed_model=embed_model) # 使用上面配置的模型index = VectorStoreIndex.from_documents(docs, service_context=service_context)return index
index = load_data()
if "chat_engine" not in st.session_state.keys(): # 初始化聊天引擎st.session_state.chat_engine = index.as_chat_engine(chat_mode="condense_question", verbose=True)
if prompt := st.chat_input("Your question"): # 提示用户输入问题,并将问题添加到消息历史记录st.session_state.messages.append({"role": "user", "content": prompt})
for message in st.session_state.messages: # 显示此前的问答记录with st.chat_message(message["role"]):st.write(message["content"])
if st.session_state.messages[-1]["role"] != "assistant": # 生成回答with st.chat_message("assistant"):with st.spinner("Thinking..."):response = st.session_state.chat_engine.chat(prompt)st.write(response.response)message = {"role": "assistant", "content": response.response}st.session_state.messages.append(message) # 将回答加入到消息历史记录


上述LlamaIndex与Streamlit的集成的相关代码,来源于这篇文章,供参考。

https://blog.streamlit.io/build-a-chatbot-with-custom-data-sources-powered-by-llamaindex/


通过以下命令运行代码后,浏览器将自动打开http://localhost:8501,即可使用这个Streamlit应用。


streamlit run app.py


同样,提问:“流程有哪三个特征?”。可以得到以下回复。你可以针对文档继续问其他问题。


9. 阶段总结


以上,我们基于LlamaIndex + Ollama + Streamlit,构建了一个完整可本地部署和运行的RAG智能问答系统。


未来,可以在这个技术栈上,进一步完善知识库的管理、优化前端界面,打造生产级的系统。


53AI,大模型落地应用首选服务商

定位:开箱即用的大模型落地应用平台

承诺:先做场景POC验证,看到效果再签署服务协议。零风险落地应用大模型,已交付160+中大型企业

年轻人!来一起搞AI吗?

如果你看见AI对商业世界的变革,欢迎来和我们一起探索~

岗位:销售经理

查看详情

岗位:项目经理

查看详情

岗位:产品经理

查看详情

岗位:测试工程师

查看详情

联系我们

售前咨询
186 6662 7370
产品演示
185 8882 0121

微信扫码

与创始人交个朋友

回到顶部

 
扫码咨询