AI知识库

53AI知识库

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


浅谈人工智能之基于ollama本地大模型结合本地知识库搭建智能客服
发布日期:2024-11-04 19:03:14 浏览次数: 1785 来源:肉肉爸爸的技术探秘


摘要

随着人工智能技术的飞速发展,基于大型语言模型(LLMs)的智能客服系统逐渐成为提升企业服务质量和效率的关键工具。然而,对于注重数据隐私和安全的企业而言,使用云服务可能会引发数据泄露的风险。因此,构建基于Ollama的本地大模型,并结合自建知识库的智能客服系统,成为了一种理想的选择。本文档旨在提供一个详尽的指南,介绍如何利用Ollama搭建一个高效、安全且定制化的本地智能客服系统。

1. 引言

1.1 Ollama简介

Ollama是一个开源项目,它使得在本地部署和运行大型语言模型变得简单易行。通过Ollama,用户可以绕过云服务,直接在本地服务器或设备上运行包括Llama系列在内的多种预训练模型,从而保障数据的隐私性和可控性。
关于ollama的安装,可以参考之前的文章:根据操作系统进行选择部署
浅谈人工智能之Windows:基于ollama进行本地化大模型部署
浅谈人工智能之Linux:基于ollama进行本地化大模型部署

1.2 本地知识库的重要性

本地知识库是指存储于企业内部服务器上的、专门用于智能客服系统的数据集合。它包含了公司的产品信息、常见问题解答、客户服务政策等,是智能客服系统精准回答用户提问的基础。相较于云端知识库,本地知识库能够更好地控制数据访问权限,防止敏感信息外泄。

2. 系统架构概述

2.1 技术栈

● Ollama:本地模型运行环境。
● LangChain:LangChain是一项革新性的技术应用,它专注于优化和提炼信息的核心价值。通过先进的自然语言处理算法,LangChain能够对文本进行深度分析,巧妙地剥离冗余部分,而精心保留最为关键的信息要素。这一过程不仅提升了信息的密度与质量,还确保了内容传达的精准度与效率,同时忠实地维护了原文的风格、语气及逻辑框架。其结果是一种更为精炼、有力且易于消化的信息表达形式,尤其适用于学术交流、专业报告及知识总结等领域,展现了技术与人文科学的完美融合,为读者带来既深刻又优雅的阅读体验。
● Embedding:嵌入技术是机器学习和自然语言处理领域中的一项核心技术,主要用于将高维稀疏数据(如文本、图像特征等)转换为低维稠密向量,这样的向量能够捕捉原始数据的语义信息和模式。这一转换过程使得数据在向量空间中具备了计算相似度的能力,从而便于在诸如推荐系统、语义搜索、机器翻译等多种应用中使用。

2.2 工作流程

  1. 模型训练:对知识库模型进行简单训练。

  2. 用户提问:通过前端界面提交问题。

  3. 请求处理:API Gateway接收并解析请求。

  4. 知识检索:查询本地知识库获取相关信息。

  5. 模型推理:Ollama根据输入的问题和知识库信息生成回复。

  6. 结果返回:回复通过API Gateway返回前端展示给用户。

3. 应用实例

3.1 模型下载

我们这里用到的模型使用:bce-embedding-vase_v1
下载路径(国内请使用这个环境):
BCE模型下载
如果大家跟外网是互通的,则可以通过git命令进行下载,如果是不互通的,则需要通过其他方式进行下载,我这边由于网络不通是在页签“Files and versions”界面安装他的目录一个个下载到本地

本地目录结构,模型存放地址:D:\vec\bce-embedding-vase_v1

3.2 构建本地知识库

  1. 选择文档内容:假设我有一个常见的FAQ文档需要生成知识库,知识库的内容如下:

问题1:git克隆失败-文件名太长答案1:查看错误信息中是否包含关键字:Filename too long问题2:git克隆失败-access_token失效答案2:查看错误信息中是否包含关键字:Authentication failed for、 Access denied、invalid_token。解决方法:重新生成一个有效的access_toekn问题3:git克隆失败-网络超时答案3:查看错误信息中是否包含关键字:Connection timed out、Unknown error、Could not resolve host等。可能是执行机与yfgitlab网络不通或者网络波动导致,执行机dns配置有问题,不能访问yfgitlab的域名问题4:git克隆失败-CI站点上配置的工程信息异常答案4:查看错误信息中是否包含关键字:FETCH_HEAD error: Sparse checkout leaves no entry on working directory。可能原因:1)、工程信息中填写的脚本路径斜杠反了,比如不正确的写法:TEST\Stability\ITC,正确的写法:TEST/Stability/ITC;2)多个脚本路径用英文分号拼接,不能使用其他符号,比如TEST/PI/SD,TEST/PI/COMMON使用逗号拼接的是异常的问题5:git克隆失败-‘git’ 不是内部或外部命令,也不是可运行的程序答案5:1、检查下执行机上是否安装了git;2、可能链接jenkins的时候没有安装git,链接成功后才安装的git,联系工厂客服删除节点,用户重新部署执行机。问题6:git克隆失败-分支名中带有.号答案6:查看错误信息中是否包含关键字:Invalid argument Cloning into 。换一个没有.号的分支名问题7:git克隆失败-git链接不是以.git结尾答案7:查看错误信息中是否包含关键字:没有找到项目名称(xxx)对应的项目id。需要填写完整的git地址问题8:git克隆失败-out of memory答案8:查看错误信息中是否包含关键字:out of memory、No space left on device。用户需要检查下执行机硬盘空间
  1. 向量数据库生成代码

# coding=utf-8from langchain_community.document_loaders import TextLoaderfrom langchain.text_splitter import RecursiveCharacterTextSplitterfrom langchain_community.embeddings importHuggingFaceEmbeddingsfrom langchain_community.vectorstores import Chromafrom langchain_community.llms import Ollamafrom langchain.chains import RetrievalQA

# 导入文本loader = TextLoader(r"D:\vec\document\test.txt")# 将文本转成 Document 对象data = loader.load()print(f'documents:{len(data)}')
# 初始化加载器text_splitter = RecursiveCharacterTextSplitter(chunk_size=100, chunk_overlap=0)# 切割加载的 documentsplit_docs = text_splitter.split_documents(data)print("split_docs size:",len(split_docs))
model_name = r"D:\vec\bce-embedding-vase_v1"model_kwargs = {'device': 'cpu'}encode_kwargs = {'normalize_embeddings': False}embeddings = HuggingFaceEmbeddings(model_name=model_name,model_kwargs=model_kwargs,encode_kwargs=encode_kwargs)
# 保存向量数据库部分# 初始化数据库db = Chroma.from_documents(split_docs, embeddings, persist_directory=r"D:\vec\vecdb")# 持久化db.persist()# 对数据进行加载db = Chroma(persist_directory=r"D:\vec\vecdb", embedding_function=embeddings)
question = "out of memory"# 测试寻找四个相似的样本similarDocs = db.similarity_search(question,k=4)

3.3 集成Ollama与知识库

代码如下

# coding=utf-8from langchain_community.document_loaders import TextLoaderfrom langchain.text_splitter import RecursiveCharacterTextSplitterfrom langchain_community.embeddings importHuggingFaceEmbeddingsfrom langchain_community.vectorstores import Chromafrom langchain_community.llms import Ollamafrom langchain.chains import RetrievalQA
retriever = db.as_retriever()qa = RetrievalQA.from_chain_type(llm=Ollama(base_url='http://XX.XX.XX.XXX:9999',model="Qwen2-7b:latest"),retriever=retriever)query = "我在做持续集成的时候,发现在git克隆的时候出现out of memory"print(qa.run(query))

3.4 开发前后端

● 为了方便大家阅读,我把后端训练的代码和接口代码写到一起,大家只要拿下面这份代码启动以后就可以进行模型训练和接口调用的功能。

from flask import Flask, request, jsonifyfrom flask_cors import CORS
# 上面的代码保持不变from langchain_community.document_loaders import TextLoaderfrom langchain_huggingface import HuggingFaceEmbeddingsfrom langchain.text_splitter import RecursiveCharacterTextSplitterfrom langchain_community.vectorstores import Chromafrom langchain_community.llms import Ollamafrom langchain.chains import RetrievalQA
# 导入文本loader = TextLoader(r"D:\vec\document\test.txt")data = loader.load()print(f'documents:{len(data)}')
text_splitter = RecursiveCharacterTextSplitter(chunk_size=100, chunk_overlap=0)split_docs = text_splitter.split_documents(data)print("split_docs size:", len(split_docs))
model_name = r"D:\vec\bce-embedding-vase_v1"model_kwargs = {'device': 'cpu'}encode_kwargs = {'normalize_embeddings': False}embeddings = HuggingFaceEmbeddings(model_name=model_name,model_kwargs=model_kwargs,encode_kwargs=encode_kwargs)
db = Chroma.from_documents(split_docs, embeddings, persist_directory=r"D:\vec\vecdb")db.persist()
db = Chroma(persist_directory=r"D:\vec\vecdb", embedding_function=embeddings)
retriever = db.as_retriever()qa = RetrievalQA.from_chain_type(llm=Ollama(base_url='http://xx.xx.xxx.xxx:9999', model="Qwen2-7b:latest"), retriever=retriever)
# 创建FastAPI应用app =Flask(__name__)CORS(app)
@app.route('/query', methods=['POST'])async def query_endpoint():# 使用qa.run处理请求中的查询data = request.get_json()messages = data.get('query')result = qa.run(messages)return jsonify({"response": result})

if __name__ == '__main__':app.run(debug=True)

● 前端交互代码如下

<!DOCTYPE html><html lang="en"><head><meta charset="UTF-8"><title>Chat Interface with Markdown</title><style>#chatHistory {height: 800px;overflow-y: scroll;border: 1px solid #ccc;padding: 10px;}#userInput {width: 100%;box-sizing: border-box;margin-bottom: 10px;}</style><!-- 引入marked库 --><script src="https://cdnjs.cloudflare.com/ajax/libs/marked/4.2.12/marked.min.js"></script></head><body><div id="chatHistory"></div><input type="text" id="userInput" placeholder="请输入你的问题..."><button onclick="sendMessage()">发送</button>
<script>function sendMessage() {const userInput = document.getElementById('userInput');const chatHistory = document.getElementById('chatHistory');
// 获取用户输入并清空输入框const userMessage = userInput.value;userInput.value = '';
// 构建请求体const data = {"query": userMessage };
// 发送POST请求到后端接口fetch('http://127.0.0.1:5000/query', {method: 'POST',headers: {'Content-Type': 'application/json'},body: JSON.stringify(data)}).then(response => response.json()).then(data => {// 假设后端返回的数据格式为 { "response": "回答内容" }const botResponse = data.response;
// 在聊天历史中添加用户的问题chatHistory.innerHTML += `<p><strong>你:</strong> ${userMessage}</p>`;
// 将Markdown转换为HTML并添加机器人的回答if (botResponse) {const htmlResponse = marked.parse(botResponse);chatHistory.innerHTML += `<p><strong>机器人:</strong> ${htmlResponse}</p>`;} else {console.error("没有从后端接收到有效的回答");}
// 滚动到底部以便查看最新消息chatHistory.scrollTop = chatHistory.scrollHeight;}).catch(error => {console.error('Error:', error);// 可以在这里添加错误信息的展示逻辑chatHistory.innerHTML += `<p><strong>错误:</strong> 发生了一个错误,请稍后再试。</p>`;});}</script></body></html>

3.5 测试

我们在前端输入框中输入我们的问题,比如:分支名中带有.号,我们可以得到如下结果

4. 安全与维护

● 数据加密:确保知识库中的敏感数据加密存储。
● 访问控制:实施严格的访问权限管理。
● 定期更新:跟踪Ollama及其依赖的更新,定期维护升级系统。

5. 结论

通过上述步骤,企业不仅能够构建一个高度定制化、响应迅速的智能客服系统,还能在确保数据安全的前提下,充分利用大型语言模型的强大能力。Ollama与本地知识库的结合,为追求数据隐私和业务自主权的企业提供了一个可行且高效的解决方案。随着技术的不断成熟,本地部署的智能客服系统将更加普及,为企业数字化转型增添动力。


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

产品:大模型应用平台+智能体定制开发+落地咨询服务

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

联系我们

售前咨询
186 6662 7370
预约演示
185 8882 0121

微信扫码

与创始人交个朋友

回到顶部

 
扫码咨询