系列导航

  • 第 0 章 前言:为什么企业 AI 工程师必须掌握 RAGFlow
  • 第 1 章:安装部署与基础配置**——从零跑通第一个 RAG Pipeline
  • 第 2 章:RAGFlow RAGFlow 代码介绍
  • 第 3 章:攻克企业复杂文档——理解 DeepDoc、Naive、MinerU 与 Docling 的区别
    • 第一节 RAGFlow 配置参数全景图与实验结论
    • 第二节 实验Chunk Method (解析方法与布局识别)
    • 第三节 实验Chunk Token Num & Overlap (切片与重叠)
    • 第四节 实验Similarity Threshold (相似度阈值)
    • 第五节 实验Vector/Keyword Weight (混合搜索权重)
    • 第六节 MinuerBridge安装配置与运行使用(本文)
  • 第 4 章:理解 Agentic RAG 核心——定义与低代码实现
  • 第 5 章:工作流编排——构建基于图(Graph)的 RAG
  • 第 6 章:Deep Research 模板应用——部署自动拆解子问题的深度研究智能体
  • 第 7 章:企业级扩展——API 接入与外部工具集成(MCP)
  • 第 8 章:评估与复盘——从"玄学"到量化 RAG 性能指标评测

写在前面

RAGFlow 是一款开源 RAG 引擎,核心能力是把文档解析、切片、检索、重排和大模型问答串成完整链路。MinerU 是 OpenDataLab 团队开发的高精度文档解析引擎,擅长把 PDF、图片、DOCX 等非结构化文档转换为 Markdown、JSON 等机器可读格式。

MineruBridge 的目的很明确:在 RAGFlow 中引入 MinerU,但不把 MinerU 直接塞进 RAGFlow 主环境
MineruBridge 的参考链接 🔗: https://github.com/dlv2008/MinerU-Bridge.git

我希望它承担的是一个独立的 PDF 解析微服务角色:

  • RAGFlow 和 mineru_bridge 各自独立运行
  • 两者通过本机 HTTP 通讯
  • 直接复用官方 mineru-api
  • 为 RAGFlow 提供可独立安装、独立运维、独立排障的 MinerU 解析服务

整体关系如下:

宿主环境

mineru_bridge

RAGFlow

MINERU_APISERVER

mineru-api

Web

Backend

config/mineru.json

output/

logs/mineru-api.log

一、接入后能得到什么

接入完成后,RAGFlow 的文档解析链路会变成下面这样:

POST /file_parse

ZIP

用户上传 PDF

RAGFlow Web

RAGFlow Backend

mineru-api

MinerU 输出目录

RAGFlow 临时处理目录

RAGFlow 入库流程

对使用者来说,效果是:

  1. 在 RAGFlow 中选择 MinerU 作为 PDF parser
  2. RAGFlow 将 PDF 发送给 mineru-api
  3. MinerU 返回包含 *_content_list.json 的 ZIP
  4. RAGFlow 读取其中的文本、表格、图片、公式结果
  5. RAGFlow 继续执行后续入库、切片和检索流程

我实测时的环境如下:

组件 说明
RAGFlow v0.24.x 路线
MinerU 官方 3.x 路线
接入方式 RAGFlow 远程调用 mineru-api
部署方式 RAGFlow 与 mineru_bridge 跑在同一个 WSL 上
默认访问地址 http://127.0.0.1:8886

二、为什么要做成独立微服务

安装前建议先接受两个工程原则:

  • MinerU 不要直接装进 RAGFlow 主环境
  • 默认优先使用 pipeline,不要一开始就上 VLM

原因很现实:

  • 依赖隔离更清晰
  • 升级和回滚更容易
  • 故障边界更明确
  • RAGFlow 场景里的优先目标是“稳定解析”,不是“追逐最复杂的推理链路”

本方案基于 MinerU 3.x 的当前能力设计,重点依赖以下事实:

  • mineru-api 保留了 POST /file_parse 兼容接口
  • 返回结果中仍然包含 content_list.json
  • 表格结果仍然通过 table 块和 table_body 表达

这些能力使 MinerU 可以作为 RAGFlow 的远程 PDF parser 服务。

三、下载 mineru_bridge 项目

原 README 里只写了“复制目录”,但如果你是第一次部署,更自然的方式是直接从 GitHub 下载项目。

项目地址:

https://github.com/dlv2008/MinerU-Bridge.git

推荐安装到和 RAGFlow 同级的目录,便于路径管理:

cd /path/to/workspace
git clone https://github.com/dlv2008/MinerU-Bridge.git mineru_bridge
cd mineru_bridge

如果你的 RAGFlow 已经在 /home/your_user/ragflow,可以放成这种结构:

/home/your_user/
  ragflow/
  mineru_bridge/

如果你已经把 mineru_bridge 放在 RAGFlow 仓库内部,也可以继续使用,只要后续路径填写准确即可。

四、目录结构

mineru_bridge 的核心目录如下:

mineru_bridge/
  .env.example
  .python-version
  pyproject.toml
  config/
  logs/
  output/
  tmp/
  scripts/

各目录职责如下:

路径 作用
config/ MinerU 本地配置文件
logs/ mineru-api 运行日志
output/ MinerU 服务端任务输出目录
tmp/ 可供 RAGFlow 作为临时处理目录使用
scripts/ 安装、下载、启动、检查脚本
ragflow_patch/ 需要修改的ragflow中代码

最容易混淆的是下面三类目录:

路径 谁使用 作用
config/mineru.json MinerU 模型与运行配置
output/ MinerU 服务端任务输出
MINERU_OUTPUT_DIR RAGFlow 返回 ZIP 的本地保存、解压、处理目录

它们不是一回事,路径不同是正常的。

五、安装与运行

5.1 准备环境变量

进入 mineru_bridge 目录后,先复制环境变量模板:

cp .env.example .env

.env.example 中的变量已经带有中文注释,通常默认值就可以先跑起来。关键配置包括:

变量 默认值 说明
MINERU_HOST 0.0.0.0 MinerU API 监听地址
MINERU_PORT 8886 MinerU API 监听端口
MINERU_MODEL_SOURCE modelscope 模型来源,支持 huggingfacemodelscopelocal
MINERU_FORMULA_ENABLE true 是否启用公式解析
MINERU_TABLE_ENABLE true 是否启用表格解析
MINERU_ENABLE_VLM_PRELOAD false 是否在服务启动时预热 VLM

5.2 安装运行时

./scripts/install.sh

这个步骤会:

  • uv 创建独立虚拟环境
  • 安装官方 mineru[core]
  • 检查 mineru-apiminerumineru-models-download 命令是否可用

5.3 下载模型

中国大陆网络环境下,建议先用 modelscope 下载模型:

MINERU_MODEL_SOURCE=modelscope ./scripts/download_models.sh

下载完成后,建议把 .env 中的模型来源改成本地:

MINERU_MODEL_SOURCE=local

这样后续服务启动时会优先使用本地模型,减少运行时网络依赖。

5.4 启动服务

./scripts/start_api.sh

默认监听:

项目
host 0.0.0.0
port 8886
本机访问地址 http://127.0.0.1:8886

5.5 健康检查

./scripts/healthcheck.sh

5.6 冒烟测试

准备一个 PDF,然后执行:

./scripts/smoke_test.sh /absolute/path/to/sample.pdf

这个脚本会检查:

  • POST /file_parse 是否可用
  • 返回 ZIP 中是否包含 *_content_list.json
  • 返回结果中是否存在 table 块和 table_body

5.7 一页看懂安装流程

git clone 项目

cp .env.example .env

./scripts/install.sh

./scripts/download_models.sh

修改 .env 为 local

./scripts/start_api.sh

./scripts/healthcheck.sh

./scripts/smoke_test.sh sample.pdf

六、RAGFlow 侧如何接入

RAGFlow 侧接入分为两部分:

  • Web 设置:告诉 RAGFlow 去哪里调用 MinerU
  • 代码适配:让 RAGFlow 正确读取官方 MinerU 3.x 的返回结果

6.1 在 RAGFlow 中添加 MinerU 模型

推荐优先在 RAGFlow 的 MinerU 模型设置界面中完成配置,而不是先记环境变量名。

进入路径:

  1. User Setting
  2. Model
  3. Add Model
  4. 选择 MinerU
    在这里插入图片描述

按下面方式填写:

界面字段 应填写的内容 说明
模型名称 自定义名称,例如 MinerU_Local 用于在 RAGFlow 中标识这套 MinerU 配置
MinerU API 服务器配置 http://127.0.0.1:8886 指向正在运行的 mineru-api
MinerU 输出目录路径 /path/to/mineru_bridge/tmp/ragflow_output 供 RAGFlow 保存、解压、处理 MinerU 返回 ZIP / JSON
MinerU 处理后端类型 pipeline 推荐默认值
处理完成后删除输出文件 可先保持开启 需要保留中间文件排障时再关闭

最关键的是两个输入框:

  • MinerU API 服务器配置
  • MinerU 输出目录路径

可以直接理解成:

  • 第一个告诉 RAGFlow 去哪里调用 MinerU 服务
  • 第二个告诉 RAGFlow 把 MinerU 返回结果临时放到哪里处理
    在这里插入图片描述

6.2 在知识库中启用 MinerU

进入 Dataset 配置后,建议第一次用下面这组默认配置:

项目 推荐值
PDF parser MinerU
MinerU backend pipeline
parse method auto
表格解析 开启
公式解析 开启

在这里插入图片描述

七、RAGFlow 代码适配

如果直接使用当前很多 RAGFlow 版本里的 MinerU 逻辑,可能会遇到一个实际问题:

  • MinerU 服务端已经成功返回 ZIP
  • ZIP 中也确实存在 *_content_list.json
  • 但 RAGFlow 仍然报错,或者最终显示 No chunk built

根因通常是:RAGFlow 侧对官方 MinerU 3.x 的输出目录结构支持不完整。

需要关注两个文件:

  • deepdoc/parser/mineru_parser.py
  • rag/app/naive.py

7.1 修改 mineru_parser.py:扩展 content_list.json 搜索路径

官方 MinerU 3.x 返回的 ZIP 解压后,结果文件不一定直接落在根目录,也可能出现在:

  • ocr/
  • txt/
  • auto/
  • 其它 method 对应子目录

因此 deepdoc/parser/mineru_parser.py 需要支持:

  • 优先检查 method 目录
  • 检查 ocr/txt/auto/
  • 最后做一次递归兜底搜索 *_content_list.json

否则会出现一种表面很诡异、实际很常见的错误:

  • MinerU 服务端成功
  • content_list.json 实际存在
  • RAGFlow 因为没在正确目录里找到文件而误判失败

核心改动如下:

diff --git a/deepdoc/parser/mineru_parser.py b/deepdoc/parser/mineru_parser.py
@@
-        jf = output_dir / f"{file_stem}_content_list.json"
-        attempted.append(jf)
-        if jf.exists():
-            subdir = output_dir
-            json_file = jf
-        else:
-            nested_alt = output_dir / safe_stem / f"{safe_stem}_content_list.json"
-            attempted.append(nested_alt)
-            if nested_alt.exists():
-                subdir = nested_alt.parent
-                json_file = nested_alt
+        candidate_dirs = [output_dir]
+        if method:
+            candidate_dirs.append(output_dir / method)
+        candidate_dirs.extend(
+            [
+                output_dir / "auto",
+                output_dir / "ocr",
+                output_dir / "txt",
+                output_dir / safe_stem,
+            ]
+        )
+
+        seen_dirs = set()
+        candidate_dirs = [p for p in candidate_dirs if not (p in seen_dirs or seen_dirs.add(p))]
+
+        for candidate_dir in candidate_dirs:
+            for candidate_name in (f"{file_stem}_content_list.json", f"{safe_stem}_content_list.json"):
+                candidate = candidate_dir / candidate_name
+                attempted.append(candidate)
+                if candidate.exists():
+                    subdir = candidate.parent
+                    json_file = candidate
+                    break
+            if json_file:
+                break
+
+        if not json_file:
+            recursive_candidates = []
+            for candidate_name in (f"{file_stem}_content_list.json", f"{safe_stem}_content_list.json"):
+                recursive_candidates.extend(sorted(output_dir.rglob(candidate_name)))
+            if recursive_candidates:
+                json_file = recursive_candidates[0]
+                subdir = json_file.parent

这个改动解决的是:

  • MinerU 服务端明明成功返回了 ZIP
  • content_list.json 也确实存在
  • 但文件落在 ocr/ 之类的子目录中
  • 旧逻辑找不到,于是 RAGFlow 误判失败

7.2 修改 naive.py:保留真实错误

rag/app/naive.py 里对 MinerU 解析失败的兜底处理,建议不要把所有异常都统一报成:

MinerU not found.

更合理的做法是:

  • 如果真的是没配置 MinerU,再报 not found
  • 如果是解析过程中失败,就把真实错误透出来

核心改动如下:

diff --git a/rag/app/naive.py b/rag/app/naive.py
@@
-    pdf_parser = None
+    pdf_parser = None
+    last_error = None
@@
-            except Exception as e:  # best-effort fallback
-                logging.warning(f"fallback to env mineru: {e}")
+            except Exception as e:  # best-effort fallback
+                logging.warning(f"fallback to env mineru: {e}")
+                last_error = e
@@
-            except Exception as e:
-                logging.error(f"Failed to parse pdf via LLMBundle MinerU ({mineru_llm_name}): {e}")
+            except Exception as e:
+                logging.error(f"Failed to parse pdf via LLMBundle MinerU ({mineru_llm_name}): {e}")
+                last_error = e
@@
-    if callback:
-        callback(-1, "MinerU not found.")
+    if callback:
+        if last_error:
+            callback(-1, f"MinerU parse failed: {last_error}")
+        else:
+            callback(-1, "MinerU not found.")

这个改动解决的是:

  • 服务端已经返回了结果
  • 但 RAGFlow 读取时出错
  • Web 页面却只显示 MinerU not found.

这种误导性错误会极大增加排障成本,因此建议一定要改。

7.3 RAGFlow 侧改动清单

文件或位置 改动点 目的
deepdoc/parser/mineru_parser.py 扩展 content_list.json 搜索路径 适配官方 3.x 返回目录结构
deepdoc/parser/mineru_parser.py 增加 method 子目录、ocr/txt/auto/ 以及递归兜底搜索 解决 ZIP 已返回但读取失败的问题
rag/app/naive.py 不再把所有异常都报成 MinerU not found. 让真实错误可见
RAGFlow 模型设置界面 填写 MinerU API 服务器配置 让 RAGFlow 能访问 MinerU 微服务
RAGFlow 模型设置界面 填写 MinerU 输出目录路径 让 RAGFlow 有自己的结果处理目录
RAGFlow Web 配置 添加 MinerU 模型并保存 让前端可选择 MinerU
数据集解析配置 使用 MinerU + pipeline + auto 以最稳配置先跑通链路

7.4 建议的接入顺序

配置并验证 mineru-api

修改 mineru_parser.py

修改 naive.py

在 MinerU 模型设置界面填写 API 地址

在 MinerU 模型设置界面填写输出目录

重启 RAGFlow Backend

重启 Task Executor

Web UI 添加 MinerU

数据集启用 MinerU

真实 PDF 验证

完整总览如下:

安装 mineru_bridge

下载模型

启动 mineru-api

smoke test

修改 RAGFlow 代码

在 MinerU 模型设置界面填写 API 地址和输出目录

重启 RAGFlow Backend 与 Task Executor

Web UI 添加 MinerU

数据集启用 MinerU

真实 PDF 验证

八、pipelineVLM 怎么选

MinerU 当前可以理解成两条路线:

  • pipeline
  • VLM

8.1 pipeline

pipeline 是传统多小模型流水线。例如:

  • OCR 用 PaddleOCR
  • 表格检测用专用表格模型
  • 表格分类、方向分类、版面分析由不同小模型协作完成
  • 最终由 MinerU 做统一后处理

优点是:

  • 稳定
  • 成熟
  • 硬件要求低
  • 易部署
  • 更适合作为 RAGFlow 的默认生产方案

8.2 VLM

VLM 是端到端多模态模型路线。

它直接用一个多模态模型去理解文档结构,理论上在复杂版面、多语言、手写、公式等场景更有潜力。

但工程上要注意:

  • 未加速的 VLM 很慢
  • 实际生产里通常要搭配 SGLang 或类似加速链路
  • Windows 原生环境并不适合作为这类加速方案的优先部署环境

8.3 RAGFlow 场景下的建议

如果目标是“先把 RAGFlow 稳定接通,并且优先解决表格解析”,建议:

  • 默认使用 pipeline
  • 不要把未加速的 VLM 当默认方案
  • 只有在高配 NVIDIA GPU + Linux 环境 + 具备加速栈维护能力时,再单独评估 VLM

选型决策图如下:

目标: 给 RAGFlow 提供稳定 MinerU 微服务

是否已有高质量 GPU 环境

选择 pipeline

是否愿意维护 VLM 加速链路

先用 pipeline 跑通

再单独验证 VLM

九、文件生命周期

一个 PDF 从上传到入库,大致会经历下面的生命周期:

用户上传 PDF

RAGFlow Backend

POST /file_parse

mineru-api

读取 config/mineru.json

写入 output/

返回 ZIP

RAGFlow 写入 MINERU_OUTPUT_DIR

解压

读取 *_content_list.json

抽取文本 表格 图片 公式

进入 RAGFlow 入库流程

理解这张图很重要,因为排障时要先判断问题发生在哪一段:

  • mineru-api 没返回 ZIP:问题在 MinerU 服务端
  • ZIP 里没有 *_content_list.json:问题在 MinerU 输出结果
  • ZIP 里有结果但 RAGFlow 找不到:问题多半在 RAGFlow 读取路径
  • RAGFlow 能读取但没有 chunk:继续看内容结构和后续入库逻辑

十、运维方式

10.1 直接命令启动

开发和调试阶段,直接执行:

./scripts/start_api.sh

日志可查看:

logs/mineru-api.log

10.2 使用 systemd 托管

如果希望把它作为长期服务运行,建议使用 systemd

示例:

[Unit]
Description=MinerU Bridge API Service
After=network.target

[Service]
Type=simple
User=your_user
WorkingDirectory=/path/to/mineru_bridge
ExecStart=/path/to/mineru_bridge/scripts/start_api.sh
Restart=always
RestartSec=5

[Install]
WantedBy=multi-user.target

部署步骤:

sudo vim /etc/systemd/system/mineru-bridge.service
sudo systemctl daemon-reload
sudo systemctl enable mineru-bridge
sudo systemctl start mineru-bridge
sudo systemctl status mineru-bridge

常用命令:

sudo systemctl restart mineru-bridge
sudo systemctl stop mineru-bridge
sudo journalctl -u mineru-bridge -f

十一、故障排查

11.1 /openapi.json 能访问,但 RAGFlow 仍然失败

先不要猜配置,直接做两件事:

  1. 运行 smoke_test.sh
  2. 检查返回 ZIP 中是否有 *_content_list.json

如果 ZIP 自己都没有结果文件,问题在 MinerU 侧。

如果 ZIP 里有结果文件,但 RAGFlow 仍然失败,问题在 RAGFlow 读取链路。

11.2 Web 上提示 No chunk built

优先检查:

  • content_list.json 是否存在
  • 结果文件是否在 ocr/txt/auto/ 子目录中
  • RAGFlow 是否已经应用前面提到的代码修改
  • RAGFlow 后端和任务执行器是否已经重启

11.3 日志里报 MinerU not found

这个错误需要分两种情况:

  • 真的没有配置 MinerU
  • 其实 MinerU 已配置,但解析过程中抛了异常,错误信息被错误地统一吞掉

因此建议按前文方式修改 rag/app/naive.py,保留真实异常。

11.4 首次请求很慢

这是正常现象,原因可能是:

  • 首次模型加载
  • OCR / 表格模型初始化
  • VLM 预热

11.5 面向 Web 报错场景的排障决策树

如果你在 Web 页面上看到的是“任务失败”“No chunk built”或者其他泛化错误,建议按下面这张图排查,而不要直接猜是模型、路径还是代码问题。

Web 页面报错

mineru-api 是否可访问

先检查 healthcheck.sh 与服务进程

smoke_test.sh 是否成功

问题在 mineru_bridge / MinerU 服务端

ZIP 中是否有 *_content_list.json

问题在 MinerU 输出结果

RAGFlow 是否已应用代码适配

修改 mineru_parser.py 与 naive.py

RAGFlow Backend 与 Task Executor 是否已重启

重启 RAGFlow 相关进程

日志里是否出现真实异常

继续检查兜底错误是否仍在吞异常

content_list.json 中是否有 table_body

问题在 MinerU 解析结果本身

问题在 RAGFlow 后续处理链路

11.6 最实用的排查顺序

如果只想记住一条顺序,就按这个来:

  1. 先看 mineru-api 是否正常
  2. 再跑 smoke_test.sh
  3. 再看 ZIP 中是否存在 *_content_list.json
  4. 再看 content_list.json 里是否存在 table_body
  5. 再确认 RAGFlow 是否已经应用代码修改并重启
  6. 最后才去查 RAGFlow 后续入库和 chunk 构建逻辑

也可以简化成下面这张图:

Web 页面报错

先跑 smoke_test.sh

ZIP 中是否有 *_content_list.json

问题在 MinerU 服务端

RAGFlow 是否能读取该文件

检查 RAGFlow 代码适配与重启

是否有 table_body

问题在 MinerU 解析结果

问题在 RAGFlow 后续处理链路

十二、最终检查清单

正式验证前,可以按这个清单走一遍:

检查项 期望结果
已 clone mineru_bridge 本地存在独立项目目录
.env 已创建 .env.example 复制而来
./scripts/install.sh 已执行 mineru-api 命令可用
模型已下载 .env 中可切换为 MINERU_MODEL_SOURCE=local
./scripts/start_api.sh 已启动 http://127.0.0.1:8886 可访问
./scripts/healthcheck.sh 成功 API 服务健康
./scripts/smoke_test.sh sample.pdf 成功 ZIP 中存在 *_content_list.json
RAGFlow 已配置 MinerU 模型 API 地址和输出目录正确
RAGFlow 已启用 MinerU parser Dataset 中选择 MinerU
RAGFlow 代码适配已应用 能读取 MinerU 3.x 子目录输出
Backend 与 Task Executor 已重启 新代码和新配置生效

参考资料

Logo

AtomGit 是由开放原子开源基金会联合 CSDN 等生态伙伴共同推出的新一代开源与人工智能协作平台。平台坚持“开放、中立、公益”的理念,把代码托管、模型共享、数据集托管、智能体开发体验和算力服务整合在一起,为开发者提供从开发、训练到部署的一站式体验。

更多推荐