🚀 基于DuckDB的Python RAG服务器
本项目是一个基于Python的服务器,专为文档处理和检索增强生成(RAG)而设计。它提供了一个简单的Web界面和JSON API,用于上传文档、将文档处理成块、生成嵌入向量,并将其存储在DuckDB数据库中,以便进行高效的相似性搜索。
整个应用程序通过Docker进行容器化,并使用uv
进行快速、优化的依赖管理。此外,它还包含一个mcp - rag - service
,用于与MCP(机器理解平台)集成。
✨ 主要特性
- Web界面:简约的用户界面,用于上传文件、启动处理和执行搜索。
- JSON API:提供
/api/search
、/api/stats
和/health
端点,便于进行编程式集成。
- 广泛的文件支持:支持多种文件类型,包括
.txt
、.md
、.pdf
以及多种编程语言的源文件(如.py
、.js
、.java
等)。
- 高级分块处理:根据文件类型采用不同的分块策略(例如,使用
CodeSplitter
处理源代码,使用RecursiveCharacterTextSplitter
处理文本)。
- 高质量嵌入向量:使用
sentence - transformers/paraphrase - multilingual - mpnet - base - v2
(主要,768维)或sentence - transformers/paraphrase - multilingual - MiniLM - L12 - v2
(备用,384维)。
- 向量数据库:利用带有VSS(向量相似性搜索)扩展的DuckDB进行嵌入向量的高效存储和查询。
- 容器化与优化:
- 易于使用Docker构建和运行。
- 使用
uv
实现超快速的依赖安装。
- 采用多阶段Dockerfile,使最终镜像体积更小。
- 支持仅使用CPU的构建,适用于没有GPU的环境。
- MCP集成:包含一个示例
mcp - rag - service
,用于演示与外部系统的集成。
- 目录上传:支持上传整个目录,并可进行文件扩展名过滤。
- 健康监控:内置健康检查端点,便于监控和负载均衡。
📦 安装指南
前提条件
构建和运行Docker容器
- 克隆仓库:
git clone <repository-url>
cd <repository-name>
- 构建Docker镜像:
构建过程使用多阶段Dockerfile和
uv
进行了优化。你可以选择标准构建(包含支持GPU的库)或仅使用CPU的构建。
标准构建(适用于支持GPU的环境):
docker build -t rag-duckdb-server .
仅使用CPU的构建(推荐用于本地开发或CPU服务器):
此构建使用仅支持CPU的PyTorch版本,速度更快,生成的镜像体积更小。
docker build --build-arg USE_CPU_ONLY=true -t rag-duckdb-server-cpu .
- 运行Docker容器:
此命令将启动服务器,并将本地的
uploads
和data
目录映射到容器中。这样,即使容器被移除,你上传的文件和数据库也会保留。
标准构建:
docker run -p 8000:8000 \
-v "$(pwd)/uploads:/app/uploads" \
-v "$(pwd)/data:/app/data" \
--name rag-server \
rag-duckdb-server
仅使用CPU的构建:
docker run -p 8000:8000 \
-v "$(pwd)/uploads:/app/uploads" \
-v "$(pwd)/data:/app/data" \
--name rag-server-cpu \
rag-duckdb-server-cpu
Windows用户注意:在PowerShell中使用${pwd}
代替$(pwd)
。
- 访问应用程序:
打开你的Web浏览器,访问
http://localhost:8000
。
💻 使用示例
基础用法
以下是整个使用流程的步骤:
- 上传文件:使用Web界面选择并上传一个或多个支持的文件。
- 上传目录:也可以上传整个目录,并进行文件扩展名过滤,以便仅处理特定类型的文件。
- 处理文件:点击“开始处理”按钮。服务器将执行以下操作:
- 提取文本内容。
- 将文本分割成易于管理、具有上下文感知的块。
- 为每个块生成向量嵌入。
- 将块及其嵌入保存到
data/rag.duckdb
数据库中。
- 从
uploads
文件夹中删除已处理的文件。
- 搜索文档:文档处理完成后,使用语义搜索栏在所有索引块中查找相关内容。
- 使用API:通过
/api/*
端点以编程方式与服务器进行交互。
高级用法
API使用示例
以下是使用Python请求库调用搜索API的示例:
import requests
url = 'http://localhost:8000/api/search'
params = {
'query': '示例查询',
'top_k': 10,
'search_type': 'semantic',
'use_reranker': True,
'expand_query': False
}
response = requests.post(url, params=params)
print(response.json())
📚 详细文档
支持的文件类型
服务器支持广泛的文件类型:
文本文档
.txt
- 纯文本文件
.md
- Markdown文件
.pdf
- PDF文档
编程语言
.py
- Python
.js
, .ts
, .jsx
, .tsx
- JavaScript/TypeScript
.java
- Java
.c
, .cpp
, .cc
, .cxx
- C/C++
.cs
- C#
.go
- Go
.rs
- Rust
.php
- PHP
.rb
- Ruby
.scala
- Scala
.swift
- Swift
Web技术
.html
, .htm
- HTML
.css
, .scss
, .sass
- CSS及预处理器
shell脚本
.sh
, .bash
, .zsh
, .fish
- shell脚本
数据格式
.json
- JSON
.yaml
, .yml
- YAML
.xml
- XML
.sql
- SQL
.ini
, .toml
- 配置文件
注意:处理过程中,不支持的文件扩展名的文件将自动跳过。
API端点
Web界面
GET /
- 主Web界面
POST /upload-files/
- 上传单个文件
POST /upload-directory/
- 上传带有扩展名过滤的目录
POST /process-files/
- 处理上传的文件
POST /search/
- 搜索界面
POST /delete-file/
- 删除上传的文件
JSON API
POST /api/search
- 编程式搜索端点
GET /api/stats
- 获取集合统计信息
GET /health
- 健康检查端点
搜索API参数
query
(必需):搜索查询字符串
top_k
(可选,默认值:5):返回的结果数量(1 - 50)
search_type
(可选,默认值:"hybrid"):"hybrid"、"semantic"或"keyword"
use_reranker
(可选,默认值:true):启用/禁用结果重排序
expand_query
(可选,默认值:false):启用/禁用查询扩展
MCP集成
项目包含一个单独的MCP(机器理解平台)集成服务,位于mcp - rag - service/
目录中。此服务提供:
- RAG客户端:用于与RAG服务器交互的Python客户端
- 向量分析:包括聚类、异常检测和相似性矩阵等高级分析功能
- MCP服务器:与兼容MCP的工具集成
MCP示例
mcp - rag - service/examples/
目录包含实际示例:
upload_example.py
- 演示文件上传功能
search_example.py
- 展示带有相似性阈值的语义搜索
analysis_example.py
- 全面的向量分析示例
要运行这些示例:
cd mcp-rag-service/examples
python upload_example.py
python search_example.py
python analysis_example.py
项目结构
.
├── app/
│ ├── main.py # FastAPI应用程序、路由和API端点
│ └── services.py # 业务逻辑(文件处理、分块、嵌入、数据库操作)
├── mcp-rag-service/ # MCP集成服务
│ ├── src/
│ │ ├── rag_client.py # RAG服务器客户端
│ │ ├── rag_mcp_server.py # MCP服务器实现
│ │ ├── vector_operations.py # 高级向量分析
│ │ └── utils.py # 实用函数
│ ├── examples/ # 实际示例
│ └── pyproject.toml
├── templates/
│ └── index.html # UI的Jinja2模板
├── uploads/ # 文件上传目录(作为卷挂载)
├── data/ # DuckDB数据库目录(作为卷挂载)
├── .dockerignore # 指定Docker构建上下文中要忽略的文件
├── .gitignore # 指定Git要忽略的文件
├── Dockerfile # 使用uv和多阶段构建的Docker构建说明
├── requirements-base.txt # 基础Python依赖项
├── requirements-cpu.txt # 仅CPU的机器学习依赖项
├── requirements-ml.txt # 完整的机器学习依赖项(用于GPU)
└── README.md # 本文件
配置
- 嵌入模型:主要和备用模型在
app/services.py
中作为常量定义。
- 分块:可以通过
CHUNK_SIZE
和CHUNK_OVERLAP
环境变量调整分块大小和重叠。默认值分别为700和100。
- 数据库路径:DuckDB文件的路径在
app/services.py
中配置。
- 搜索功能:
- 搜索类型:可以在
Hybrid
(语义 + 关键词)、仅Semantic
或仅Keyword
(BM25)搜索之间进行选择。
- 重排序:可以使用交叉编码器模型对搜索结果进行重排序,以提高准确性。可以在UI中切换此功能。
- 查询扩展:可以自动使用从初始搜索中找到的相关术语扩展查询。可以在UI中切换此功能。
- 处理功能:
- TF - IDF关键词:处理文件时,可以选择使用TF - IDF为每个块的元数据生成并附加相关关键词。这可以提高基于关键词的搜索效果。
错误处理
- 不支持的文件:上传和处理过程中,不支持的文件扩展名的文件将自动跳过。
- 空文件:空文件或无法读取的文件将自动从上传目录中删除。
- 处理错误:单个文件的处理错误会被记录,但不会停止整个处理过程。
- API错误:所有API端点都会返回带有适当HTTP状态码的结构化错误响应。
已知限制
- 文件大小:非常大的文件在处理过程中可能会导致内存问题。
- 并发用户:当前实现是为单用户场景设计的。
- 文件格式:仅支持基于文本的文件。不支持二进制文件(如图像、视频等)。
- 语言支持:虽然嵌入模型是多语言的,但分块策略针对英语和常见编程语言进行了优化。
路线图和未来计划
计划功能
- GraphRAG集成:高级的基于图的检索和推理功能
- 多用户支持:用户认证和隔离的文档集合
- 实时处理:支持WebSocket进行实时处理更新
- 高级分析:更复杂的向量分析和可视化工具
- 插件系统:可扩展的架构,用于自定义处理器和分析器
- 性能优化:缓存、索引改进和分布式处理
GraphRAG实现
GraphRAG(基于图的检索增强生成)计划作为一项重大改进,将提供:
- 知识图谱构建:自动提取实体和关系
- 基于图的检索:使用图遍历和推理进行增强搜索
- 多跳推理:需要多个推理步骤的复杂查询
- 上下文理解:更好地理解文档关系和层次结构
此功能目前处于规划阶段,将作为一个单独的模块实现,可以选择启用。
故障排除
常见问题
- Docker构建失败:尝试使用仅CPU的构建,以获得更快、更可靠的构建:
docker build --build-arg USE_CPU_ONLY=true -t rag-duckdb-server-cpu .
-
内存问题:对于大型文档集合,可以考虑以下操作:
- 使用仅CPU的构建(内存占用更小)
- 分批处理文件
- 增加Docker内存限制
-
模型加载问题:如果主模型加载失败,系统会自动切换到较小的模型。
-
数据库问题:首次运行时会自动创建DuckDB数据库。如果遇到数据库错误,可以删除data/
目录以重新开始。
健康检查
使用健康检查端点监控服务状态:
curl http://localhost:8000/health
此命令将返回服务状态、模型加载状态和数据库连接信息。
📄 许可证
本项目采用MIT许可证 - 详情请参阅LICENSE文件。