如何快速部署PrivateGPT?打造企业私有化GPT

前言

对于很多企业或者个人来说,训练和部署自己私有的大模型,在本地运行,这将是未来的大趋势。

今天我们就来介绍如何以非常简单的方式来快速部署 PrivateGPT 应用程序。本文将会逐步指导您使用后端 API 和 Streamlit 前端应用程序部署您自己的 PrivateGPT 应用程序。令人惊喜的是,任何前端解决方案都可以轻松连接到 privateGPT 后端 API。

如果您是企业或以隐私为中心的数据组织,这对您来说很合适。PrivateGPT 通过优先考虑用户隐私和数据安全,使自己与其他聊天应用程序区分开来。

一、为什么需要PrivateGPT?

1.1、前提条件

1、您的数据很敏感

2、数据不得离开您的企业

3、隐私法规

4、不想发送个人敏感数据

PrivateGPT是一个具有完整数据控制的聊天GPT,当我们在面临以上这些情况:数据比较敏感不适合暴露在互联网或者共享出来,对于企业涉密且拥有知识产权的数据,一些一些地方对于数据隐私保护的要求,包括我们个人涉及隐私比较敏感的数据需要有这么一个APP支持在本地传输数据给我们的大模型,然后快速响应给我响应的结果,这种情况下PrivateGPT应用而生。

1.1、使用场景:

1、企业应用

2、拥有机密数据的组织

3、着重保护用户数据隐私,例如HIPAA法案

4、敏感的个人数据

在这些应用场景下,任何像ChatGPT这样的聊天应用都可以从PrivateGPT中受益,比较典型的场景是企业,企业拥有大量内部数据,不能对外公开,因为涉及知识产品的问题。

1.3、传统文本聊天类应用流程图

对于传统文档类GPT聊天应用的工作原理和流程图,基本上都是按照如上图的步骤:

1、首先获取任何文档数据(上传本地文件或者输入一个文档链接)

2、通过技术手段将文档内容提取出来,比如PDF文档提取文本,音频提取文本

3、由于LLMs对于输入和响应的字数有一定的限制,为了能同时接收或者处理更多的数据,我们需要对识别的文本内容进行切割、分块

4、然后将文本片段通过LangChain等一些辅助库通过调研模型接口将文本转换为向量或者数字

5、然后将这些向量保存在支持向量的数据库中,比如开源的Chroma和云数据库Supabase(前面有专门分享过)

6、然后通过前端查询请求进行文本搜索,首先自然也需要将输入的文本内容转换为向量

7、通过和向量数据库中存储的向量值进行余弦相似度计算,找到与检索文本相似度最高的Top N条记录。

1.4、接耦后的文本聊天类应用流程图

要理解系统背后的工作原理,我们可以把它接耦合将文档数据采集系统和数据检索系统视为两个独立的流程,其中对于文档数据采集系统,首先从文档中提取文本,然后将该文本分为小块,然后将其转换为数字或者使用Enbedding向量,然后将这些向量或数字保存在向量数据库中。

同样,对于数据检索系统,也遵循一种模式,即不获取文档,而是获取问题,然后使用类似的Enbedding模型将问题转换为向量,然后进行搜索,通过向量数据库进行余弦相似度计算,找到最近相邻的文本,然后将这些作为相关答案提供给我们的GPT API,以完成最终的答案响应。

对于PrivateGPT,我们采集上传的文档数据是保存在公司本地私有化服务器上的,然后在服务器上本地调用这些开源的大语言文本模型,用于存储向量的数据库也是本地的,因此没有任何数据会向外部发送,所以使用PrivateGPT,涉及到以上两个流程的请求和数据都在本地服务器或者电脑上,完全私有化。

我们在GitHub上可以看到目前PrivateGPT已经拥有22800颗了,说明PrivateGPT现在已经非常流行且受欢迎了,同时对于大语言模型的爆发,一些企业或者个人私有化应用场景的需求也明显爆发出来。

二、如何快速部署PrivateGPT?

接下来我们将介绍两种部署PrivateGPT的方法,一种是非常简单的方法,直接部署在Railway远程环境;第二种是在我们自己的本地服务器上部署。

PrivateGPT原生仓库目前只提供了CLI接口,只能在终端窗口中去使用它,部署完成后没有可以方便使用的UI界面,这里我们介绍一个基于原生PrivateGPT做了一定友好性封装的应用privateGPT-app,我们可以在GitHub上很方便的找到它,它通过使用FastAPI将与原生的GPT封装成了后端的API接口服务,前端基于Streamlit模板实现了一个方便交互的UI聊天界面。

三、Railway远程部署

Railway这种部署方式快速方便,比较适合我们希望快速体验一下产品demo的场景,如果需要完整稳定的使用其功能,建议还是选择在本地服务器上进行部署。

3.1、克隆privateGPT-app项目

在部署之前需要先将privateGPT-app项目fork一份到我们个人的GitHub仓库里来,后面需要用到。

3.2、部署privateGPT-app项目

1)点击【Deploy on Railway】按钮,即可快速跳转到你的Railway个人空间

2)接着我们点击右上角的【Deploy Now】开始部署PrivateGPT app,没授权默认第一次会跳转授权确认弹窗

3)我们点击Configure按钮,输入GitHub的密码进入GitHub的仓库授权页面

4)这里我们不用授权仓库所有项目,只需要授权我们刚才fork过来的privateGPT-app这个项目即可,这里选择它,点save保存即可。

5)在部署前我们需要做下简单的配置修改,例如这里的项目名称我修改为PrivateGPT-webapp,勾选上Private repository设置为私有仓库,其他的环境变量参数我们就按默认值保持不变。

6)接下来,Railway将开始执行一些脚本部署并构建应用程序,部署完成大概需要8-10分钟,完成后会提供应用访问链接,然后我们就可以访问运行了。

7)看到这个绿色的标志基本上代表我们的应用已经部署安装完成了,点击绿色的名称进入部署详细页面

8)然后点击这里的紫色的应用链接,就可以正式访问privateGPT-app了。

温馨提示:这里我们Railway使用的免费实例,本身提供的内存和CPU资源都是非常有限的,所以使用过程中可能会出现一些故障,如果你希望在公有云的环境中去部署应用正式作为生产去使用,建议还是选择付费实例。

Railway是按使用时长来收费的,新用户可以免费使用500小时,如果不打算使用付费服务,记得在到期前去关闭它。

9)当我们打开APP后,主页面如下图所示,接下来可以上传PDF文档,输入问题进行检索了。

四、本地服务器部署

4.1、环境要求:

4.2、安装Python

4.2.1、安装Python 3.11版本

如何在 CentOS 7 / RHEL 7 上安装 OpenSSL 1.1.x

如何在 CentOS 7 / RHEL 7 上安装 Python 3.11

4.2.2、创建Python虚拟环境

4.3、安装privateGPT-app

4.3.1、下载源码

从GitHub克隆privateGPT-app项目到服务器,进入项目privateGPT-app主目录中

git clone git@github.com:menloparklab/privateGPT-app.git
cd privateGPT-app/

4.3.2、配置环境变量

将环境变量从example.env复制到一个名为.env. 修改文件中的值.env以匹配所需的配置。

PERSIST_DIRECTORY:应用程序将保存数据的目录。
MODEL_TYPE:要使用的语言模型的类型(例如,“GPT4All”、“LlamaCpp”)。
MODEL_PATH: 语言模型文件的路径。
EMBEDDINGS_MODEL_NAME:要使用的嵌入模型的名称。
MODEL_N_CTX:模型生成期间要考虑的上下文数量。
API_BASE_URL:FastAPI 应用程序的基本 API url,通常部署到端口:8000。

4.3.3、下载LLM模型

下载模型后并将其放在models文件夹中

wget https://gpt4all.io/models/ggml-gpt4all-j-v1.3-groovy.bin

4.3.4、安装项目依赖

pip install -r requirements.txt 

这里因为安装的依赖较多,由于有些依赖的镜像源下载很慢,安装过程会需要一点时间,请耐心等待。由于每个人使用的环境不太一样,安装过程可能不一定会非常顺利,针对我在CentOS 7.6上出现的一些问题解决过程可以参考一下,遇到错误仔细分析解决即可,亦可借助于ChatGPT快速进行错误定位。

当你看到整个执行过程如下图所示,没有出现任何错误,完整结束的时候,恭喜你,安装成功了。

4.3.4、安装错误分析

1)、安装过程中某个包太大,由于网络原因导致超时中断

如果下载依赖的过程中,出现某些依赖下载超时(Read Timeout)失败的情况,可以试试配置以下pip镜像源。通过国内阿里的镜像源下载。建议多尝试几次,因为网络波动会导致失败。

pip install -r requirements.txt -i https://mirrors.aliyun.com/pypi/simple/ 

建议将pip install -r requirements.txt直接换成上面的命令,使用阿里云的镜像去下载,速度非常快,用默认的镜像速度基本上保持在50kb的速度,很容易超时失败。

2)编译llama-cpp-python模块失败:ERROR: Failed building wheel for llama-cpp-python

具体错误信息如下所示:

An error occurred while building with CMake.
        Command:
          /tmp/pip-build-env-71_8yzad/overlay/lib/python3.11/site-packages/cmake/data/bin/cmake --build . --target install --config Release --
        Install target:
          install
        Source directory:
          /tmp/pip-install-28q3m34k/llama-cpp-python_6954e336998c48ae82b7af6382c0f027
        Working directory:
          /tmp/pip-install-28q3m34k/llama-cpp-python_6954e336998c48ae82b7af6382c0f027/_skbuild/linux-x86_64-3.11/cmake-build
      Please check the install target is valid and see CMake's output for more information.

      [end of output]

  note: This error originates from a subprocess, and is likely not a problem with pip.
  ERROR: Failed building wheel for llama-cpp-python
Failed to build llama-cpp-python
ERROR: Could not build wheels for llama-cpp-python, which is required to install pyproject.toml-based projects 

解决方案:升级gcc-11即可解决,安装gcc-11需要先安装SCL 开发工具集(devtoolset-11 软件集)

yum list installed | grep devtoolset-11

如果看到 devtoolset-11 的条目,则表示已安装。否则,请安装它:(执行)

sudo yum install -y devtoolset-11
scl enable devtoolset-11 bash
scl enable devtoolset-11 -

如果还是无法使用 scl 命令,请尝试更新您的操作系统,并重新安装 devtoolset-11。

如果您已经安装了 devtoolset-11 开发工具集,那么您可以使用 scl enable devtoolset-11 bash 命令启用开发工具链。在启用后,您可以使用 gcc、g++ 和其他工具,而无需再单独安装这些软件包。

yum install centos-release-scl

yum install devtoolset-11-gcc*

通过 devtoolset-11-gcc* 包安装的 GCC 软件包只有在未启用 devtoolset-11 环境时才会被使用。因此,如果您打算使用 devtoolset-11 环境,请不要单独安装 devtoolset-11-gcc* 包。 

参考解决方案:https://github.com/abetlen/llama-cpp-python/issues/106

4.4、运行 FastAPI 后端

要运行 FastAPI 后端,请执行以下命令:

# 控制台启动,便于查看日志
gunicorn app:app -k uvicorn.workers.UvicornWorker --timeout 1500

#后台进程启动,正式部署
nohup gunicorn app:app -k uvicorn.workers.UvicornWorker --timeout 1500 --bind=0.0.0.0:14800 > privateGPT-backend.log 2>&1 &

此命令启动后端服务器并自动处理语言模型和嵌入模型的必要下载。该--timeout 500选项可确保为正确的模型下载留出足够的时间,看到如下界面表示已经成功启动,如启动有错误请参考后面的问题进行排查。

4.4.1、启动出错,提示语法错误:SyntaxError: invalid syntax

[2023-05-25 00:01:53 +0800] [54956] [INFO] Waiting for application startup.
  File "ingest.py", line 52
    def load_single_document(file_path: str) -> Document:
                                      ^
SyntaxError: invalid syntax
embeddings working
File already exists.
[2023-05-25 00:01:53 +0800] [54956] [INFO] Application startup complete. 

解决方案:原因是代码基于Python3.x实现,但可能执行的是默认的Python2.x解释器,导致出现语法兼容问题。很大概率是你不在虚拟环境中安装依赖或者重新编译完Python未更新到虚拟环境。

1)修改代码,将其语法兼容Python2.x

2)在使用gunicorn启动应用时,指定Python解释器为3.x版本

gunicorn app:app -k uvicorn.workers.UvicornWorker --timeout 1500 --bind=0.0.0.0:8000 --pythonpath=/opt/gptlabs/privateGPT/myenv/bin/python3.11

4.4.2、启动报错:ModuleNotFoundError: No module named '_sqlite3'

import nltk
  File "/opt/gptlabs/privateGPT/myenv/lib/python3.11/site-packages/nltk/__init__.py", line 153, in 
    from nltk.translate import *
  File "/opt/gptlabs/privateGPT/myenv/lib/python3.11/site-packages/nltk/translate/__init__.py", line 24, in 
    from nltk.translate.meteor_score import meteor_score as meteor
  File "/opt/gptlabs/privateGPT/myenv/lib/python3.11/site-packages/nltk/translate/meteor_score.py", line 13, in 
    from nltk.corpus import WordNetCorpusReader, wordnet
  File "/opt/gptlabs/privateGPT/myenv/lib/python3.11/site-packages/nltk/corpus/__init__.py", line 64, in 
    from nltk.corpus.reader import *
  File "/opt/gptlabs/privateGPT/myenv/lib/python3.11/site-packages/nltk/corpus/reader/__init__.py", line 106, in 
    from nltk.corpus.reader.panlex_lite import *
  File "/opt/gptlabs/privateGPT/myenv/lib/python3.11/site-packages/nltk/corpus/reader/panlex_lite.py", line 15, in 
    import sqlite3
  File "/usr/local/lib/python3.11/sqlite3/__init__.py", line 57, in 
    from sqlite3.dbapi2 import *
  File "/usr/local/lib/python3.11/sqlite3/dbapi2.py", line 27, in 
    from _sqlite3 import *
ModuleNotFoundError: No module named '_sqlite3' 

解决方案:由于 Python 编译时未包括对 SQLite3 的支持而导致的,不确定 Python 源码是否已编译为支持 SQLite3,可以使用以下命令来检查当前 Python 解释器中是否启用了 SQLite3 扩展:

python -c "import sqlite3; print(sqlite3.sqlite_version)"

如果输出了 SQLite3 库的版本号,则表示 Python 已经编译好了对 SQLite3 的支持。

如果这个命令引发了 ImportError 或其他错误,则表示 Python 可能未编译为支持 SQLite3。此时您需要重新编译 Python 并确保在编译选项中启用了对 SQLite3 的支持(例如 --enable-loadable-sqlite-extensions)。

注意: 请确保在重新编译并安装 Python 之前备份现有的 Python 安装 (如果您不是在虚拟环境中操作)。

tar -czvf python_backup.tar.gz /usr/local/bin/python3.11

如果您使用的是源代码或已经下载了 Python 源码,请按照以下步骤进入Python源码目录编译并安装 Python:

LDFLAGS="${LDFLAGS} -Wl,-rpath=/usr/local/openssl/lib" ./configure --with-openssl=/usr/local/openssl --prefix=/usr/local/python3.11 --enable-loadable-sqlite-extensions
make
make install

4.5、运行 Streamlit 应用程序

请更新API_BASE_URL为适当的 FastAPI 网址

要运行 Streamlit 应用程序,请使用以下命令:

# 控制台启动,便于查看日志
streamlit run streamlit_app.py --server.address 0.0.0.0 --logger.level=debug 

#后台进程启动,正式部署
nohup streamlit run streamlit_app.py --server.address 0.0.0.0 > privateGPT-frontend.log 2>&1 &

此命令启动 Streamlit 应用程序并将其连接到正在运行的后端服务器localhost。

4.6、访问PrivateGPT

前后端部署完成后,我们可以正式访问PrivateGPT了,浏览器直接输入前端Streamlit的端口接口,启动前端应用在控制台会打印出来,也可以在配置文件中设置端口号。

4.6.1、上传文档

点击[Browse files]选择本地文档上传,上传文件大小限制200M以内,支持的文件格式在5.1中有说明。

4.6.2、向量计算

只需点击[Embed]按钮即可,将文件进行分割并计算向量存储,PrivateGPT采用的Chroma向量数据库存储,默认在项目根目录下的db文件夹。

4.6.3、文本检索

只有文档正确上传并Embedding之后,才可以选择文档进行对话,如果下拉框没有刚才上传的文件,基本上load失败了,可以去查看日志,注意:这里文件名不能有空格。

五、重要注意事项

5.1、支持的文档扩展名

六、后端AP接口

6.1、根路由

curl -X GET http://localhost:8000/
import requests

response = requests.get("http://localhost:8000/")
print(response.json())

6.2、文档嵌入接口

curl -X POST -F "files=@file1.txt" -F "files=@file2.txt" -F "collection_name=my_collection" http://localhost:8000/embed
import requests

files = [("files", open("file1.txt", "rb")), ("files", open("file2.txt", "rb"))]
data = {"collection_name": "my_collection"}

response = requests.post("http://localhost:8000/embed", files=files, data=data)
print(response.json())

6.3、数据检索接口

curl -X POST -H "Content-Type: application/json" -d '{"query": "sample query", "collection_name": "my_collection"}' http://localhost:8000/retrieve
import requests

data = {"query": "sample query", "collection_name": "my_collection"}

response = requests.post("http://localhost:8000/retrieve", json=data)
print(response.json())

请注意,实际 URL ( http://localhost:8000/) 和请求负载应根据您的特定设置和要求进行调整。

展开阅读全文

页面更新:2024-02-02

标签:向量   终端   应用程序   模型   文本   命令   快速   文档   环境   项目   数据   企业

1 2 3 4 5

上滑加载更多 ↓
推荐阅读:
友情链接:
更多:

本站资料均由网友自行发布提供,仅用于学习交流。如有版权问题,请与我联系,QQ:4156828  

© CopyRight 2020-2024 All Rights Reserved. Powered By 71396.com 闽ICP备11008920号-4
闽公网安备35020302034903号

Top