• [开源for鲲鹏云] 在鲲鹏CPU和HCE系统下部署运行QAnything 2.0
    资源购买资源名称规格操作系统存储ECS鲲鹏内存优化型 km1.xlarge.8 4vCPUs 32GiBHuawei Cloud EulerOS 2.0 标准版 64位 ARM版系统盘:超高IO,100GiB基础软件安装Condamkdir -p ~/miniconda3 wget https://repo.anaconda.com/miniconda/Miniconda3-latest-Linux-aarch64.sh -O ~/miniconda3/miniconda.sh bash ~/miniconda3/miniconda.sh -b -u -p ~/miniconda3 rm -f ~/miniconda3/miniconda.sh source ~/miniconda3/bin/activate conda init --allPython & Pip官方默认安装的python版本为3.99,版本比较低,这里使用Conda创建一个3.10的虚拟环境。conda create -n QAnything python=3.10 conda activate QAnything # 设置 pip软件源 pip config set global.index-url https://repo.huaweicloud.com/repository/pypi/simple python -m pip install --upgrade pipDocker & Docker Compose官方默认安装的docker版本为18.09.0,版本比较低,很多新的特性无法使用,如docker-buildx等,建议升级到最新版本。因为官方并未提供Huawei Cloud EulerOS 2.0的repo支持,所以可以采取以下方式进行安装。如果之前安装过docker,要先删掉之后再安装依赖sudo dnf remove docker docker-ce-cli docker-selinux docker-engine下载repo文件wget -O /etc/yum.repos.d/docker-ce.repo https://mirrors.huaweicloud.com/docker-ce/linux/centos/docker-ce.repo sudo sed -i 's+download.docker.com+mirrors.huaweicloud.com/docker-ce+' /etc/yum.repos.d/docker-ce.repo sudo sed -i 's+$releasever+9.9+' /etc/yum.repos.d/docker-ce.repo安装新版本sudo dnf install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin设置开机启动sudo systemctl enable --now docker配置镜像加速器vi /etc/docker/daemon.json # 粘贴以下配置,保存退出,镜像地址可替换成自己在华为云申请的镜像加速器地址 { "registry-mirrors": [ "https://docker.1ms.run", "https://docker.xuanyuan.me"] } 重启dockersystemctl restart docker下载QAnything源码git clone https://github.com/netease-youdao/QAnything.git官方的docker镜像xixihahaliu01/qanything-linux:v1.5.1 是在X86的服务器下构建的,无法在ARM架构下运行,需要手动构建Docker镜像。构建QAnything镜像进入build_images,查看Dockerfile,可以得到以下几点信息Dockerfile文件要移动到父目录下才能构建需要准备models、nltk_data文件夹数据# 复制 requirements.txt 文件到容器中 COPY requirements.txt /tmp/requirements.txt # 复制 models 文件夹到 /root 目录 COPY models /root/models COPY nltk_data /root/nltk_data想知道model文件夹下要准备什么数据就要看这个文件复制到容器后是如何使用的,通过docker-compose-linux.yaml 可知,运行qanything-container-local容器时会执行/bin/bash -c "cd /workspace/QAnything && bash scripts/entrypoint.sh",打开script/entrypoint.sh,其中跟/root/models和/root/nltk_data有关的信息如下:# 创建软连接 if [ ! -L "/workspace/QAnything/qanything_kernel/dependent_server/embedding_server/embedding_model_configs_v0.0.1" ]; then # 如果不存在软连接 cd /workspace/QAnything/qanything_kernel/dependent_server/embedding_server && ln -s /root/models/linux_onnx/embedding_model_configs_v0.0.1 . fi if [ ! -L "/workspace/QAnything/qanything_kernel/dependent_server/rerank_server/rerank_model_configs_v0.0.1" ]; then # 如果不存在软连接 cd /workspace/QAnything/qanything_kernel/dependent_server/rerank_server && ln -s /root/models/linux_onnx/rerank_model_configs_v0.0.1 . fi if [ ! -L "/workspace/QAnything/qanything_kernel/dependent_server/ocr_server/ocr_models" ]; then # 如果不存在软连接 cd /workspace/QAnything/qanything_kernel/dependent_server/ocr_server && ln -s /root/models/ocr_models . # 创建软连接 fi if [ ! -L "/workspace/QAnything/qanything_kernel/dependent_server/pdf_parser_server/pdf_to_markdown/checkpoints" ]; then # 如果不存在软连接 cd /workspace/QAnything/qanything_kernel/dependent_server/pdf_parser_server/pdf_to_markdown/ && ln -s /root/models/pdf_models checkpoints # 创建软连接 fi if [ ! -L "/workspace/QAnything/nltk_data" ]; then # 如果不存在软连接 cd /workspace/QAnything/ && ln -s /root/nltk_data . # 创建软连接 fi从脚本内容结合官方README可知,models文件夹中要准备embedding、rerank、ocr、pdf四个模型,nltk_data下要准备nltk 数据model文件夹下要准备的数据下面下载模型数据都是在QAnything目录下执行安装modelscopepip install modelscopebce-embedding-base_v1modelscope download --model netease-youdao/bce-embedding-base_v1 --local_dir ./models/linux_onnx/embedding_model_configs_v0.0.1bce-reranker-base_v1modelscope download --model netease-youdao/bce-reranker-base_v1 --local_dir ./models/linux_onnx/rerank_model_configs_v0.0.1pdf_models和ocr_modelmodelscope download --model netease-youdao/QAnything-pdf-parser --local_dir ./models/pdf_modelspdf_models中已经包含了ocr,可以重用,这里要改下entrypoint.sh中ocr_models路径if [ ! -L "/workspace/QAnything/qanything_kernel/dependent_server/ocr_server/ocr_models" ]; then # 如果不存在软连接 cd /workspace/QAnything/qanything_kernel/dependent_server/ocr_server && ln -s /root/models/pdf_models/ocr ocr_models # 创建软连接 finltk_data文件夹下要准备的数据modelscope download --dataset CaiJichang/nltk_data --local_dir ./nltk_data构建之前需要对项目中的一些文件做些优化。Dockfile优化在QAnything目录下创建新的Dockerfilevi Dockerfile # 添加以下内容 # 使用官方 Python 3.10.14 镜像作为基础镜像 FROM python:3.10-slim # 替换APT源 RUN sed -i 's/http:\/\/deb.debian.org\//https:\/\/mirrors.huaweicloud.com\//g' /etc/apt/sources.list.d/debian.sources # 设置时区 ENV TZ=Asia/Shanghai RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone # 安装 RUN apt-get update && apt-get install -y \ vim \ wget \ htop \ build-essential \ procps \ && rm -rf /var/lib/apt/lists/\* # 创建TikToken缓存目录 RUN mkdir /opt/tiktoken_cache # 下载TikToken模型缓存 ARG TIKTOKEN_URL="https://openaipublic.blob.core.windows.net/encodings/cl100k_base.tiktoken" RUN wget -O /opt/tiktoken_cache/$(echo -n $TIKTOKEN_URL | sha1sum | head -c 40) "$TIKTOKEN_URL" # 设置环境变量指向TikToken缓存目录 ENV TIKTOKEN_CACHE_DIR=/opt/tiktoken_cache # 复制 requirements.txt 文件到容器中 COPY requirements.txt /tmp/requirements.txt RUN pip config set global.index-url https://repo.huaweicloud.com/repository/pypi/simple \ && python -m pip install --upgrade pip # 安装 Python 依赖(torch单独安装CPU版本) RUN pip install torch torchvision torchaudio --index-url https://download.pytorch.org/whl/cpu \ && pip install -r /tmp/requirements.txt # 复制 models 文件夹到 /root 目录 COPY models /root/models COPY nltk_data /root/nltk_data # 设置工作目录 WORKDIR /workspace # 清理 APT 缓存 RUN apt-get clean && rm -rf /var/lib/apt/lists/\* # 设置默认命令 CMD ["/bin/bash"] requirements.txt优化默认的依赖包中会安装CUDA依赖,本次我们是纯CPU部署,不需要这些。vi requirements.txt # 添加以下内容 onnxruntime==1.17.1 xgboost-cpu==3.0.0 concurrent-log-handler==0.9.25 boto3==1.34.79 sanic==23.6.0 sanic_ext==23.6.0 langchain-openai==0.3.7 langchain_elasticsearch==0.3.2 langchain-community==0.3.18 unstructured==0.12.4 unstructured[pptx]==0.12.4 unstructured[md]==0.12.4 opencv-python-headless==4.9.0.80 python-dotenv==1.0.1 mysql-connector-python==8.2.0 pymilvus==2.5.5 aiomysql==0.2.0 PyMuPDF==1.24.4 openpyxl==3.1.2 python-docx==1.1.0 newspaper4k==0.9.3.1 newspaper4k[zh]==0.9.3.1 duckduckgo-search==5.3.0b4 html2text==2024.2.26 mistune==3.0.2 flair==0.13.0 nltk==3.8.1 pandas==2.1.1 scikit-learn==1.3.2 chardet==5.2.0 scipy==1.10.1 fastchat==0.1.0 wikipedia==1.4.0 Wikipedia-API==0.6.0 rouge-score==0.1.2 toml==0.10.2 tqdm==4.66.1 anthropic==0.25.7 streamlit==1.34.0 zhipuai==2.0.1.20240429 tiktoken==0.7.0 modelscope==1.13.0 cryptography==42.0.8 shapely==2.0.4 pyclipper==1.3.0.post5 pdfplumber==0.11.0 markdownify==0.12.1 datrie==0.8.2 hanziconv==0.3.2 PyPDF2==3.0.1 lxml_html_clean==0.1.1 docx2txt==0.8 构建docker镜像# 在QAnything目录下执行 docker build -t xixihahaliu01/qanything-linux:v1.5.1 . docker-compose-linux.yaml优化在qanything_local下的volumes,其实不用把整个QAnything映射到容器中,只需要映射需要的文件即可 volumes: - ${DOCKER_VOLUME_DIRECTORY:-.}/qanything_kernel:/workspace/QAnything/qanything_kernel - ${DOCKER_VOLUME_DIRECTORY:-.}/logs:/workspace/QAnything/logs - ${DOCKER_VOLUME_DIRECTORY:-.}/volumes:/workspace/QAnything/volumes - ${DOCKER_VOLUME_DIRECTORY:-.}/QANY_DB:/workspace/QAnything/QANY_DB - ${DOCKER_VOLUME_DIRECTORY:-.}/scripts/entrypoint.sh:/workspace/QAnything/scripts/entrypoint.sh代码优化qanything_kernel/core/retriever/vectorstore.py@get_time def delete_expr(self, expr): # 如果expr为空,则不执行删除操作 result = self.get_local_chunks(expr) if result is None or len(result) == 0: debug_logger.info(f'expr: {expr} not found in local milvus') return qanything_kernel/dependent_server/embedding_server/embedding_server.py 和 qanything_kernel/dependent_server/rerank_server/rerank_server.py增加以下代码from sanic.worker.manager import WorkerManager WorkerManager.THRESHOLD = 600 qanything_kernel/configs/model_config.py增加以下配置DEFAULT_PROMPT_TEMPLATE = """ 参考信息: {{context}} --- 我的问题或指令: {{question}} --- 请根据上述参考信息回答我的问题或回复我的指令。前面的参考信息可能有用,也可能没用,你需要从我给出的参考信息中选出与我的问题最相关的那些,来为你的回答提供依据。回答一定要忠于原文,简洁但不丢信息,不要胡乱编造。我的问题或指令是什么语种,你就用什么语种回复,你的回复: """ # 匹配后单段上下文长度 CHUNK_SIZE = 800 修改以下配置# 知识库检索时返回的匹配内容条数 VECTOR_SEARCH_TOP_K = 5 # embedding检索的相似度阈值,归一化后的L2距离,设置越大,召回越多,设置越小,召回越少 VECTOR_SEARCH_SCORE_THRESHOLD = 0.5 qanything_kernel/core/local_doc_qa.py # 在下面语句后增加 DEFAULT_PROMPT_TEMPLATE from qanything_kernel.configs.model_config import DEFAULT_PROMPT_TEMPLATE # 586~592做以下修改 if custom_prompt: # prompt_template = CUSTOM_PROMPT_TEMPLATE.replace("{{custom_prompt}}", custom_prompt) prompt_template = custom_prompt else: # system_prompt = SYSTEM.replace("{{today_date}}", today).replace("{{current_time}}", now) # prompt_template = PROMPT_TEMPLATE.replace("{{system}}", system_prompt).replace("{{instructions}}",INSTRUCTIONS) prompt_template = DEFAULT_PROMPT_TEMPLATE 启动项目run.sh 修改# 修改run.sh 93行 source ./.env启动# 在QAnything目录下执行 bash run.sh出现以下信息表示启动成功了访问项目在运行run.sh过程中会询问是在本地部署还是云服务上部署,如果是云服务器部署,就填入弹性IP的地址即可。体验项目新建知识库上传文档目前支持文件格式md、txt、pdf、jpg、png、jpeg、docx、xlsx、pptx、eml、csv, 单个文档小于30M, 单张图片小于5M, 文件总大小不得超过125M.文档越大,处理时间越长.备注中可以看大部分时间都耗费在embedding中,如果文档太大也可能会超时导致失败.预览切片结果PDF文件的解析原理是将其转换成Markedown文件,这可以最大限度保证原版的样式和内容.可以对照源文件对比查看,支持编辑修改.配置LLM大模型这里使用华为云ModelArts Studio大模型服务来作为LLM的提供商进入产品官网ModelArts Studio在API Key管理菜单项中申请一个Api Key进入在线推理菜单项,领取大模型服务免费额度进入对应服务的调用说明获取调用参数配置模型提供商问答会话接下来就可以进行问答会话了,这里用的是外部LLM服务,响应还是非常快的.
  • [技术干货] Word Embedding、BERT原理、Transformer原理
    一、Word EmbeddingWord2vec,是一群用来产生词向量的相关模型。这些模型为浅而双层的神经网络,用来训练以重新建构语言学之词文本。网络以词表现,并且需猜测相邻位置的输入词,在word2vec中词袋模型假设下,词的顺序是不重要的。训练完成之后,word2vec模型可用来映射每个词到一个向量,可用来表示词对词之间的关系,该向量为神经网络之隐藏层。–百度百科Word2vec主要有两种模式:-Skip-Gram:给定输入的文字预测上下文-CBOW:给定上下文预测输入的文字二、BERT原理1.Pre-training预训练确实存在通用的语言模型,先用文章预训练通用模型,然后再根据具体应用,用supervised训练数据,精加工(fine tuning)模型,使之适用于具体应用。2.Deep Bidirectional Transformers假如句子“能实现语言表征[mask]的模型”,遮盖住其中“目标”一词。从前往后预测[mask],也就是用“能/实现/语言/表征”,来预测[mask](从前往后);用“模型/的”,来预测[mask](从后往前)。-------单向预测,不能完整地理解整个语句的语义。双向预测bi-directional:用上下文全向来预测[mask],也就是用“能/实现/语言/表征/…/的/模型”,来预测[mask]。3.BERT中的双向表示BERT的预训练模型中,预训练任务是一个mask LM,随机把句子中的单词替换成mask,然后对单词进行预测对于模型,输入的是一个被挖了空的句子,由于Transformer的特性,它是会注意到所有的单词的=>导致模型会根据挖空的上下文来进行预测,从而本身就实现了双向表示(BERT是一个双向的语言模型)Transformer的核心是Attention机制,对于一个语句,可以同时启用多个聚焦点4.BERT训练模型的参数,使用了两种策略,两个预训练任务4.1 Mask LM把一篇文章中,15%的词汇遮盖,让模型根据上下文全向地预测被遮盖的词。通过全向预测被遮盖住的词汇,来初步训练Transformer模型的参数。3种mask的方式:80%:用[MASK]标记替换单词10%:用一个随机的单词替换该单词10%:保持单词不变4.2 预测下一句因为涉及到问答(QA)和自然语言推理(NLI)任务,所以增加了第二个预训练任务。目的是让模型理解两个句子之间的联系。当选择句子A和B作为预训练样本时,B有50%的可能是A的下一个句子,也有50%的可能是来自语料库的随机句子。比如:S1:[CLS] the man went to [MASK] store [SEP]S2: he bought a gallon [MASK] milk [SEP]Label = IsNextS1:[CLS] the man [MASK] to the store [SEP]S3:penguin [MASK] are flight ##less birds [SEP]Label = NotNext最终预训练模型的准确率在97-98%4.BERT的输入表示用WordPiece分词,一共30,000个token的词汇表。用##表示分词,用[CLS]分割样本, [SEP]分隔样本中的不同句子。每一个token由三种向量相加而成,即Input = Token Embeddings + Segmentation Embeddings + Position Embeddings在海量语料上训练完BERT后,可以将它应用到NLP的各个任务中了=> 迁移学习,进行Fine-Tuning微调即可三、Transformer原理1.Transformer机制Transformer是一个利用注意力机制来提高模型训练速度的模型。Transformer由且仅由self-Attenion和Feed Forward Neural Network组成。1.1 Attention机制通过Attention机制,让模型可以集中在所有对于当前目标单词重要的输入信息上,预测效果大大提升。通过观察attention权重矩阵的变化,可以更好了解哪部分翻译对应哪部分的原文文字。2.Transformer本质Transformer的本质上是一个Encoder-Decoder的结构2.1 Encoder首先使用embedding算法将输入的word转换为vector,输入给Encoder #1在每个Encoder内部,输入向量经过self-attention,再经过feed-forward层每个Encoder的输出向量是下一个Encoder的输入Transformer的一个关键性质,即每个位置的单词在Encoder中都有自己的路径,self-attention层中的这些路径之间存在依赖关系,然而在feed-forward层不具有那些依赖关系=>feed-forward层可以并行执行2.2 DecoderEncoder通过处理输入序列开始工作。最上端的Encoder的输出之后会被转化为一个包含向量K(键向量)和V(值向量)的注意力向量集这些向量会用于每个decoder的encoder-decoder attention层,有助于解码器聚焦在输入序列中的合适位置Decoder阶段的每个步骤都会输出一个输出序列,直到到达一个特殊的终止符号,它表示transformer的解码器已经完成了它的输出会在Encoder和Decoder的输入中添加位置编码,表示每个单词的位置转载链接:【云驻共创】华为云AI之《情感专家》在线分析影评情感基调_云汉ai顾问 情感板块-CSDN博客