混合RAG服务器

基于LangChain的混合RAG服务器,整合文档QA、命令JSON生成和数据库联动功能,支持多格式文档处理和PDF自动识别。

  • by MaoEmong
  • Python
  • 本地部署
  • 更新于
在 GitHub 查看 MaoEmong/RAG-LangChain-MCP

使用说明

基于LangChain的混合RAG服务器(MCP)

FastAPI RAG服务器,集成了基于文档的QA、命令生成和数据库集成。
包括Parent-Document Retriever、FlashRank Re-Ranking、DB+文档混合响应、intent自动分支、模型上下文协议(MCP)支持。

文档状态:在所有Python文件中添加韩语文档和详细注释(公开产品组合)

主要功能

  • 加载多格式文档 →收听→矢量加载(ingest_langchain.py)
    • PDF(自动区分文本PDF/扫描PDF)
    • 文本文件(TXT,MD)
    • Word文档(DOCX)
    • HTML文件
  • PDF自动处理:
    • 文本PDF:PyMuPDF直接提取文本
    • 扫描PDF:Tesseract OCR图像文本识别(支持韩语/英语)
  • DB+文档混合QA (/ask):
    • LLM选择并验证后运行MySQL白名单查询
    • 将数据库结果和文档搜索上下文合并 hybrid_answer用回答
  • Parent-Document Retriever:child是搜索/排名,parent是LLM上下文(Chroma+SQLite)
  • 第二步搜索:矢量搜索→FlashRank Re-Ranking
  • Guardrail&Confidence:top score切,good hit个数,可信度分数/级返回
  • Intent分类(/ask:自动路由到explain/command
  • 命令生成JSON+解析+白名单验证(/command)
  • 包含来源/score/预览的RAG响应(/chat)

技术堆栈

  • Python 3、FastAPI、Uvicorn
  • LangChain(OpenAI、Chroma、文本拆分器、社区)
  • 父文档检索器패턴 (Chroma子节点+SQLite父节点)
  • FlashRank重新排名
  • 皮丹提克
  • PyMuPDF(PDF文本提取)
  • Tesseract OCR(扫描PDF图像识别)
  • Mysql+mysql-connector-python(数据库排名/分数查询)

文件夹结构

.
├── api/                  # FastAPI 서버 관련 파일
│   └── rag_server.py     # FastAPI 엔트리포인트 (/chat, /command, /ask)
├── chains/               # LLM 체인 구현 (RAG/SQL/DB/하이브리드)
│   ├── __init__.py
│   ├── rag_chain.py
│   ├── sql_query_chain.py
│   ├── db_query_chain.py
│   ├── db_summary_chain.py
│   ├── hybrid_chain.py
│   ├── hybrid_onecall_chain.py
│   └── command_chain.py
├── commands/             # 명령 화이트리스트
│   ├── __init__.py
│   └── registry.py       # 허용 명령 목록 및 파라미터 정의
├── docs/                 # 원본 문서 저장 폴더
├── ingest/               # 문서 수집 및 벡터DB 구축
│   ├── __init__.py
│   ├── ingest_langchain.py   # 문서 적재 스크립트
│   ├── docstore_sqlite.py    # SQLite 기반 Parent 문서 저장소
│   └── debug_chroma_scan.py  # ChromaDB 디버깅 스크립트
├── loaders/              # 문서 로더 (다중 포맷 지원)
│   ├── auto_loader.py    # 자동 문서 로더 (PDF 자동 구분)
│   ├── pdf_detector.py   # PDF 종류 판별기 (텍스트/스캔)
│   ├── pdf_text_loader.py # 텍스트 PDF 로더
│   ├── pdf_scan_loader.py # 스캔 PDF 로더 (OCR)
│   └── rules.py          # 파일 확장자별 로더 규칙
├── ocr/                  # OCR 엔진
│   ├── __init__.py
│   ├── base.py           # OCR 베이스 클래스
│   ├── tesseract_ocr.py  # Tesseract OCR 구현
│   └── dummy_ocr.py      # 더미 OCR (테스트용)
├── preprocess/           # 전처리 유틸리티
│   └── text_cleaner.py   # 텍스트 정리
├── prompts/              # LLM 프롬프트 템플릿
│   ├── __init__.py
│   ├── command_prompt.py
│   ├── intent_prompt.py
│   ├── rag_prompt.py
│   ├── sql_query_prompt.py
│   ├── db_query_prompt.py
│   ├── db_summary_prompt.py
│   ├── hybrid_onecall_prompt.py
│   └── hybrid_prompt.py
├── reasoning/            # LLM 기반 추론 모듈
│   ├── __init__.py
│   ├── chains/          # LLM 체인들
│   ├── prompts/         # 프롬프트 템플릿
│   ├── schemas/         # Pydantic 스키마
│   └── services/        # 검색/파싱/검증 서비스
├── retrieval/            # 검색 및 벡터화
│   ├── retrieval.py      # Parent-Child 검색 + FlashRank re-ranking
│   ├── vector_store.py   # ChromaDB 벡터 저장소
│   └── rerank_flashrank.py # FlashRank 재정렬 엔진
├── schemas/              # Pydantic 스키마 정의
│   ├── __init__.py
│   ├── command.py
│   ├── intent.py
│   ├── rag_answer.py
│   ├── sql_query.py
│   ├── db_query.py
│   ├── db_summary.py
│   └── hybrid_answer.py
├── services/             # 비즈니스 로직 서비스
│   ├── __init__.py
│   ├── retrieval.py      # Parent-Child 검색
│   ├── vector_store.py   # 벡터 저장소 관리
│   ├── intent_classifier.py        # 의도 분류
│   ├── command_parser.py           # 명령 JSON 파싱
│   ├── command_validator.py        # 명령 검증
│   ├── db_service.py               # MySQL 연결 및 쿼리 실행
│   ├── db_router.py                # DB 질문 판별
│   ├── db_schema_provider.py       # DB 스키마 정보 제공
│   ├── db_query_parser.py          # DB 쿼리 JSON 파싱
│   ├── db_query_validator.py       # DB 쿼리 검증
│   ├── db_summary_parser.py        # DB 요약 결과 파싱
│   ├── db_fallback_summary.py      # DB 요약 폴백
│   ├── sql_query_parser.py         # SQL 쿼리 파싱
│   ├── sql_validator.py            # SQL SELECT 전용 검증
│   ├── hybrid_parser.py            # 하이브리드 답변 파싱
│   └── confidence.py               # 신뢰도 계산
├── test/                 # 테스트 스크립트
│   ├── test_loaders.py   # 로더 테스트
│   ├── test_retrieval.py # 검색 기능 테스트
│   └── test_db.py        # DB 연결 테스트
├── config.py             # 전역 설정 파일
├── query_test.py         # 검색 단독 테스트
├── requirements.txt      # 프로젝트 의존성
├── chroma_db/            # ChromaDB 벡터 저장소 (자동 생성)
└── README.md             # 이 파일

主要文件说明

根目录

FastAPI服务器

  • api/rag_server.py:FastAPI服务器主文件
    • /chat, /command, /ask 提供端点
    • 运行二级搜索管道(矢量搜索+FlashRank Re-Ranking)
    • Guardrail和Confidence计算
    • 所有端点均包含详细的韩语文档

收集和测试文档

  • ingest/ingest_langchain.py:文档收集和矢量数据库构建脚本

    • docs/ 读取文件夹中的文档并将其保存到ChromaDB
    • 保存为Parent-Child结构(搜索为child,LLM上下文为parent)
    • 文档窃听和嵌入转换
    • 包括详细的韩语文档
  • query_test.py:仅测试矢量搜索功能的脚本

    • 无需运行服务器即可查看搜索结果
    • 包括韩语使用注释
  • config.py:项目全局设置文件

    • OpenAI API密钥、模型设置、Guardrail参数等
    • 将敏感信息显示为占位符
    • 添加详细的韩语说明

装载机/

  • auto_loader.py:自动文档加载程序
    • 自动检测文件夹中的所有文档,并选择适当的加载程序
    • 对于PDF文件,自动区分文本PDF和扫描PDF进行处理
    • 自动添加文档元数据(doc_id、source、kind、domain等)
  • pdf_detector.py:PDF类型辨识器
    • 通过检查是否存在文本层自动识别文本PDF/扫描PDF
  • pdf_text_loader.py:文本PDF加载程序
    • 使用PyMuPDF直接从文本层提取文本
    • 将整合加载到每个文件一个Document
  • pdf_scan_loader.py:扫描PDF加载程序
    • 使用Tesseract OCR从图像中提取文本
    • 韩语/英语多语言支持
    • 将整合加载到每个文件一个Document
  • rules.py:按文件扩展名加载规则
    • 加载程序映射,如TXT、MD、PDF、DOCX、HTML等

ocr/

  • base.py:OCR基类
    • 定义OCR引擎的通用接口
  • tesseract_ocr.py:Tesseract OCR实施
    • 将PDF渲染为图像并执行OCR
    • 多语言支持(韩语、英语等)
  • dummy_ocr.py:堆叠OCR(测试用)

预处理/

  • text_cleaner.py:文本清理实用程序
    • 统一改行文字、消除过多空白等

reasoning/包

reasoning/chains/ -LLM链实施

  • rag_chain.py:RAG链

    • 将矢量搜索的文档转换为上下文
    • 使用LangChain链配置问题→搜索→答案生成管道
    • 所有函数都包含韩语文档
  • sql_query_chain.py:SQL查询创建链

    • 自然语言→SQL查询转换
    • 通过SELECT专用验证增强安全性
  • db_query_chain.py:DB查询选择链

    • LLM指南选择允许的数据库查询列表之一
  • db_summary_chain.py:DB摘要链

    • 用自然语言概括DB查询结果
  • hybrid_chain.py:二级混合链

    • 合并DB摘要+文档上下文以生成最终答案
  • hybrid_onecall_chain.py:单呼叫混合链

    • 一次处理DB rows+文档上下文
  • command_chain.py:命令创建链

    • 将自然语言命令转换为JSON格式

reasoning/prompts/ -LLM提示模板

  • intent_prompt.py:目的分类提示

    • 将用户输入分类为“command”或“explain”
  • rag_prompt.py:RAG响应提示

    • 创建基于搜索到的文档上下文的响应
  • sql_query_prompt.py:SQL生成提示

    • 自然语言→SQL转换提示
  • db_query_prompt.py:DB查询选择提示

    • 从允许的查询列表中选择
  • db_summary_prompt.py:DB摘要提示

    • 结果摘要提示
  • hybrid_onecall_prompt.py:混合单一呼叫提示

    • DB+文档集成提示
  • hybrid_prompt.py:混合二级提示

    • 用于回退的混合提示
  • command_prompt.py:命令生成提示

    • 生成JSON命令提示

reasoning/schemas/ -Pydantic模式

  • intent.py:目的分类结果模式

    • IntentResult 模型
  • rag_answer.py:RAG答案方案

    • 基于搜索的响应结构
  • sql_query.py:SQL查询模式

    • 生成的SQL查询结构
  • db_query.py:DB查询请求模式

    • DBQueryRequest 模型
  • db_summary.py:DB摘要结果方案

    • DBSummaryResult 模型
  • hybrid_answer.py:混合回答方案

    • DB+文档集成响应结构
  • command.py:命令模式

    • CommandResponse, CommandAction 模型

reasoning/services/ -业务逻辑服务

所有服务均遵循单一责任原则(SRP),包括详细的韩语文档:

搜索和排名

  • retrieval.py:父母子女검색 + FlashRank重新排名

    • 实施二级搜索管线
    • OCR关键字偏斜
  • rerank_flashrank.py:FlashRank重新排序引擎

    • 根据搜索结果的语义相关性重新排序

目的分类和路由

  • intent_classifier.py:分类用户意图

    • 基于Rule+基于LLM的混合
    • “command”或“explain”分类
  • db_router.py:识别DB问题

    • 识别用户问题是否与DB相关

命令处理

  • command_parser.py:命令解析JSON

    • LLM生成命令解析JSON
  • command_validator.py:验证命令白名单

    • commands/registry.py 基础验证

SQL查询处理

  • sql_query_parser.py:解析SQL查询

    • LLM生成SQL解析
  • sql_validator.py:仅验证SQL SELECT

    • 阻止DML(INSERT,UPDATE,DELETE)

数据库查询处理

  • db_service.py:运行SQL连接和查询

    • 基于白名单运行允许的查询
  • db_schema_provider.py:提供数据库模式信息

    • 要提供给LLM的数据库结构信息
  • db_query_parser.py:DB查询解析JSON

    • LLM生成的DB查询解析JSON
  • db_query_validator.py:验证DB查询

    • 验证允许的查询和参数

数据库摘要

  • db_summary_parser.py:解析数据库摘要结果

    • 解析LLM摘要结果
  • db_fallback_summary.py:数据库摘要回退

    • LLM失败时生成基于规则的摘要

混合答案

  • hybrid_parser.py:解析混合答案
    • 解析DB+文档集成响应

可靠性和guardrail

  • confidence.py:计算可靠性
    • 基于搜索分数+良好的文档数量计算可信度
    • high/medial/low级别分类

测试文件(test/文件夹)

  • test/test_loaders.py:文档加载程序测试脚本

    • PDF类型判别测试
    • 文本PDF提取示例输出
    • 扫描PDF OCR样例输出
    • AutoLoader完整摘要
    • 包括韩语文档
  • test/test_retrieval.py:搜索功能测试脚本

    • 在ChromaDB中搜索Child文档
    • 按doc_id排序
    • 从SQLiteDocStore恢复Parent文档
    • 详细的韩语函数说明
  • test/test_db.py:测试数据库连接和查询

    • 检查您的MySQL连接
    • 运行示例查询
    • 包括韩语文档
  • query_test.py (根):测试ParentDocumentRetriever行为

    • 测试交互式问答

安装&首选参数

1.安装软件包

pip install -r requirements.txt

2.安装Tesseract OCR(用于扫描PDF处理)

处理扫描PDF文件需要Tesseract OCR。

窗户:

  1. Tesseract OCR安装程序 下载和安装
  2. 默认安装路径: C:\Program Files\Tesseract-OCR\tesseract.exe
  3. loaders/auto_loader.py哇 ocr/tesseract_ocr.py在中检查/修改路径

Linux(Ubuntu/Debian):

sudo apt-get install tesseract-ocr
sudo apt-get install tesseract-ocr-kor  # 한국어 지원

macOS:

brew install tesseract
brew install tesseract-lang  # 다국어 지원

注意:

  • 建议安装韩语语言包以支持韩语
  • 安装后的语言代码: "eng+kor" (英语+韩语)

环境变量(建议env)

OPENAI_API_KEY=your-api-key
EMBED_MODEL=text-embedding-3-small
CHAT_MODEL=gpt-4o-mini
CHROMA_DIR=./chroma_db
COLLECTION_NAME=my_rag_docs
TOP_K=4
DOCSTORE_PATH=./parent_docstore.sqlite

# 선택사항 - MySQL 설정 (DB 질문 사용 시)
MYSQL_HOST=localhost
MYSQL_PORT=3306
MYSQL_USER=your_user
MYSQL_PASSWORD=your_password
MYSQL_DATABASE=your_db

# 선택사항 - Tesseract OCR 설정 (스캔 PDF 처리)
TESSERACT_CMD=C:\\Program Files\\Tesseract-OCR\\tesseract.exe
OCR_LANGUAGE=eng+kor

安全建议:

  • 敏感信息使用环境变量或保密服务
  • Git上 .env 禁止提交文件(.gitignore添加到)

数据装载(ingest)

将文档 docs/放入并运行:

python ingest/ingest_langchain.py

支持文件格式

  • PDF:自动区分文本PDF和扫描PDF
    • 文本PDF:PyMuPDF直接提取文本
    • 扫描PDF:Tesseract OCR识别图像文本
  • 文本文件:TXT,MD
  • Word文档:DOCX
  • HTML文件:HTML、HTM

处理方式

  • 区块设置:默认800个字符,重叠100个字符(config.py / ingest/ingest_langchain.py)
  • 存储方式:儿童→Chroma,父母→SQLite(parent_docstore.sqlite)
  • PDF处理:每个文件合并一个Parent文档(无分页)
  • 元数据:自动添加到每个文档
    • doc_id:每个文件的唯一ID
    • source:文件路径
    • kind:文档类型(pdf_text、pdf_scan_ocr、txt、md等)
    • domain:域标签
    • page:页码(当年)
  • 重新运行:更改源文档时重新运行

处理流

# ingest/ingest_langchain.py 실행
# 1. docs/ 폴더 스캔
# 2. PDF 자동 구분 (텍스트 vs 스캔)
# 3. 텍스트 추출 (PyMuPDF 또는 Tesseract OCR)
# 4. 파일별 Parent 문서 생성 및 SQLite 저장
# 5. Child 청크 생성 및 ChromaDB 벡터 저장
# 6. 진행 상황 콘솔 출력

运行服务器

1.装载文档(仅第一次)

python ingest/ingest_langchain.py

2.启动FastAPI服务器

uvicorn api.rag_server:app --reload --port 8000

或内置测试:

python -m uvicorn api.rag_server:app --reload --port 8000

3.API测试

在浏览器中查看交互式API文档:

http://localhost:8000/docs

API端点

/chat -基于RAG的Q&A

请求:

{
  "question": "질문 내용"
}

回答:

{
  "answer": "응답 텍스트",
  "sources": [
    {
      "source": "문서 경로",
      "score": 0.95,
      "preview": "미리보기 텍스트..."
    }
  ],
  "guard": {
    "reason": "ok",
    "top_score": 0.85,
    "good_hits": 3
  },
  "confidence": {
    "level": "high",
    "score": 0.92,
    "details": {
      "base": 0.85,
      "bonus": 0.07
    }
  }
}

/command -命令JSON建议

请求:

{
  "question": "어떤 작업을 하고 싶은지"
}

回复:

{
  "speech": "요약 음성",
  "actions": [
    {
      "action": "명령이름",
      "params": {
        "param1": "값1"
      }
    }
  ],
  "confidence": 0.9,
  "guard": {
    "reason": "ok"
  }
}

/ask -基于目的的集成界面

请求:

{
  "question": "질문 또는 명령"
}

回答(如果是DB问题):

{
  "type": "hybrid_answer",
  "question": "...",
  "speech": "...",
  "db_summary": "DB 조회 결과 요약",
  "doc_notes": "관련 문서 추가 설명",
  "answer": "최종 통합 답변",
  "query": "GetTopScores",
  "params": { "limit": 10 },
  "rows": [ ... ],
  "sources": [ ... ],
  "guard": { "reason": "ok" }
}

回答(如果是一般问题):

{
  "type": "rag_answer",
  "answer": "...",
  "sources": [ ... ],
  "guard": { "reason": "ok" },
  "confidence": { "level": "high", "score": 0.9 }
}

呼叫示例

# RAG 질문
curl -X POST http://localhost:8000/chat \
  -H "Content-Type: application/json" \
  -d '{"question": "RAG 파이프라인 설명"}'

# 명령 요청
curl -X POST http://localhost:8000/command \
  -H "Content-Type: application/json" \
  -d '{"question": "화면 밝기 올려줘"}'

# 통합 인터페이스 (의도 자동 판별)
curl -X POST http://localhost:8000/ask \
  -H "Content-Type: application/json" \
  -d '{"question": "지난주 상위 점수는?"}'

动作流

1.收集文档(Ingest)

  1. docs/ 在文件夹中自动浏览文档
  2. PDF文件:文本PDF/扫描自动识别PDF
    • 文本PDF:PyMuPDF提取文本
    • 扫描PDF:Tesseract OCR识别图像文本
  3. 在每个文件中 doc_id 赋予(每个文件的唯一ID)
  4. 每个文件创建一个Parent文档(合并所有页面)
  5. 将Parent文档拆分为Child区块(800个字符,100个重叠字符)
  6. Parent存储SQLite,Child存储在ChromaDB中作为矢量

2.请求搜索(文档)

  1. 搜索Child文档similarity(initial_k=20)
    • OCR关键字查询时优先搜索OCR文档(关键字偏置)
  2. 使用FlashRank Re-ranking重新排列结果
  3. Parent文档还原和重复数据删除
  4. 按Parent计算最小distance score
  5. Guardrail和可靠性计算

3. /chat 端点

  1. Parent上下文格式(每个文档900个字符,共3500个字符)
  2. _trim_context最多限制12000个字符
  3. 生成LLM响应+返回来源信息

4. /command 端点

  1. 使用相同上下文
  2. LLM生成JSON格式命令
  3. 解析JSON并验证白名单
  4. 信任度低则屏蔽

5. /ask 端点(DB+文档混合)

  1. 如果问题与DB有关:
    • LLM选择允许查询列表(DB白名单)之一生成JSON
    • 在服务器上验证后运行MySQL(最多使用50条rows)
    • 与文档搜索上下文合并 hybrid_answer用回答
    • 失败时:默认查询 GetTopScores +基于规则的摘要回退
  2. 如果与DB无关:
    • intent分类(command/explain)后 /command 或 /chat 运行逻辑

主要设置点

  • ingest_langchain.py:父母/子女分开(build_parent_retriever), COLLECTION_NAME
  • config.py: CHUNK_SIZE=800, CHUNK_OVERLAP=100, TOP_K, TOP_SCORE_MAX, MIN_GOOD_HITS, GOOD_HIT_SCORE_MAX, CONF_SCORE_MIN/MAX, DOCSTORE_PATH
  • rag_server.py: INITIAL_K=20, _trim_context 最多12000个字符
  • services/retrieval.py: fetch_multiplier=3将rerank范围扩大到top_k,以缓解parent deducpe损失
  • commands/registry.py:允许命令/定义必需的args

体系结构注释(Parent-Document Retriever)

  • 搜索为child区块(Chroma),LLM上下文为parent(SQLite)
  • 流:child搜索→FlashRank rerank→parent恢复/重复数据删除→每个parent的最小distance score→guard/considence→上下文剪切→LLM

操作/安全提示

  • API密钥使用环境变量/保密服务
  • chroma_db/需要时可再生(ingest重新运行)
  • PDF文件处理:
    • 文本PDF可以快速处理
    • 扫描PDF的OCR处理可能需要很长时间(与文件大小和页数成正比)
    • 建议使用高分辨率PDF以提高OCR准确度
  • 发生问题时 docs/troubleshooting.txt 参考

主要功能

PDF自动分隔

  • 自动确定是否存在文本层
  • 文本PDF:快速直接提取
  • 扫描PDF:OCR识别图像文本

优化OCR关键字搜索

  • 在搜索运单编号、跟踪码等关键词时,首先搜索OCR文档
  • 通过关键字偏置提高搜索准确度

Parent-Child结构

  • 搜索是小Child区块,提高了准确度
  • LLM上下文作为整个Parent文档提供,以保留上下文