跳到正文

RAG PROJECT INTERVIEW · Q05 / 25

MinerU 能直接解决 RAG 文档解析吗?哪些页面必须二次处理?

不把开源解析器当黑盒:逐项分析阅读顺序、复杂表格、OCR、公式、输出一致性与资源限制,并给出可插拔的后处理链路。

作者与复核:吴师兄内容依据:公开 RAG 教程、GitHub 教学代码与工程推导查看关联教程 →查看吴师兄公开作品 →

25 道题目Q05
本页内容12 节

30 秒先说结论

MinerU 可以作为文档解析基线,但不能假设所有页面一次处理就正确。多栏阅读顺序、复杂或跨页表格、小语种 OCR、公式和结构化语义仍可能失败。稳妥做法是保存中间结果,对低置信度或特殊页面分类路由,再用专用表格模型、OCR、规则或人工复核处理。

先设一个教学场景。

你把一份几十页的 PDF 交给 MinerU,程序没有报错,Markdown 和 JSON 也正常生成。打开结果一看,正文、标题、表格似乎都有。

这时候能不能直接切成 Chunk,写进向量库?

很多人的第一反应是可以。解析工具已经把 PDF 变成了文本,后面无非就是切分、向量化和检索。

用户真正关心的是输出能不能长期稳定使用:同一区域有没有重复出现,正文和表格是否表达了两份冲突内容,解析器升级后字段结构会不会变化,重新处理时旧 Chunk 能不能被正确替换,答案又能否回到原页。“文件已经生成”只回答了任务状态,没有回答这些质量问题。

只要其中一处出错,系统依旧可能顺利入库,却再也搜不到正确证据。

所以这道面试题真正问的是:

MinerU 已经完成 PDF 解析,为什么还需要后处理?哪些页面要二次处理,又怎么判断它们可以进入 RAG?

解析成功,离 RAG 可用还差什么?

PDF 不是一条连续字符串。

一页里可能同时有标题、正文、页眉、页脚、表格、图片、公式、脚注和印章。解析器需要先判断每个区域是什么,再识别其中的内容,最后按照某种顺序输出。

只要文件被成功转换,只能说明这条程序链路走完了。它不能证明输出顺序符合人的阅读方式,也不能证明每个结构都被正确保留。

RAG 对结果还有额外要求。

第一,内容必须能被正确切分。标题要和所属正文建立关系,表头不能与数据行分离,列表前导句不能丢失。

第二,内容必须能被稳定索引。同一页重复出现两个文本块,向量库里就可能产生两份近重复证据。字段顺序或名称每次变化,也会影响稳定 ID 和增量更新。

第三,内容必须能够追溯。模型回答以后,用户应该能回到原文件、页码和具体区域核对,而不是只看到一个笼统文件名。

第四,失败必须可见。某一页识别失败时,系统不能悄悄把其余页面当成完整文档发布。

从解析成功到 RAG 可用的差距

Markdown 或 JSON 成功生成,只是解析链路结束。结构、顺序、追溯和完整性通过检查后,内容才具备入库条件。

可以把 MinerU 放在整个离线链路的前半段理解。它负责提供版面元素、文字、表格以及位置等中间信息。后处理层再把这些信息整理成下游长期依赖的内部格式。

这两层职责分开很重要。

如果业务逻辑直接依赖某个工具的输出字段,解析器一升级,字段名、段落顺序或嵌套结构发生变化,后面的切分、稳定 ID 和索引更新都可能被影响。

更稳妥的做法,是让外部解析器负责“尽量看懂文档”,内部 Schema 负责“稳定地交给 RAG”。

哪四类输出异常最值得先抓?

工具可能在每页都返回结果,但真正影响后处理稳定性的,通常是下面四类异常。

第一类,同一区域重复或缺失

同一段正文可能同时出现在段落列表和页面块列表中,页眉也可能被当成正文重复输出。相反,某个区域虽然出现在版面结果里,却没有进入最终 Markdown 或 JSON。

检查时需要用页码、坐标、内容类型和规范化文本共同定位区域。只按文本完全相等去重,会误删正文中的合法引用;只按数组序号比对,又无法发现版本升级后的顺序变化。

第二类,同一内容存在冲突表示

表格可能既有结构化单元格,又被展开成一段普通文本;图片中的 OCR 文字也可能再次出现在相邻正文块里。如果两种表示内容不一致,下游不能把它们都当成独立事实写入索引。

后处理要明确哪一份是原始识别结果,哪一份用于展示,哪一份只用于增强检索。冲突无法自动判断时,应保留原始区域并进入复核,而不是把两份内容拼成更长的 Markdown。

第三类,字段和层级发生漂移

解析器版本变化后,标题层级、内容类型名称、坐标格式或嵌套结构都可能调整。业务代码如果直接读取外部 JSON 的临时字段,一次升级就可能让切分器找不到标题,让引用拿不到页码。

因此外部结果必须经过适配层。适配层负责把不同版本映射到稳定字段,并在缺少必要字段时明确失败,不能用默认空值把不兼容输出静默放行。

第四类,稳定 ID 随输出顺序变化

如果 Chunk ID 只由页面内数组序号生成,前面新增一个块,后续所有 ID 都会改变。重新解析时,系统无法判断哪些内容没有变化、哪些应该替换,旧索引也可能继续残留。

更可靠的 ID 需要组合原文件、页码、区域、内容类型和规范化内容,并把解析器版本作为复现信息保存。稳定不等于永远不变,而是同一内容在没有实质变化时能够被识别出来。

MinerU 异常输出的分流处理

默认解析后先识别重复、冲突、字段漂移和 ID 变化,再进入对应处理分支,最终统一到稳定 Schema。

把所有错误统称为“解析不准”,后面就只能不断更换模型。把错误拆成类型,系统才知道应该核对重复区域、处理冲突表示、适配字段版本,还是把确实识别失败的页面交给专项解析。

为什么不把所有页面都交给最重的模型?

一个看似省事的方案是:每一页都先用 MinerU 解析,再让视觉模型或大语言模型重写一遍。

问题在于,常规单栏正文原本可能已经正确。再增加一次生成式处理,不但增加计算和等待,还可能改写原文、补出不存在的连接词,或者让相同页面在不同时间得到不同输出。

更合理的是先走基线解析,再根据异常信号分流。

普通页面通过结构检查后,直接进入统一格式和切分。

检测到同一区域同时存在普通文本和结构化表格时,先做表示一致性检查,再确定保留方式。

输出出现重复块或缺失区域时,进入区域比对和去重分支,同时保留原始结果用于核验。

解析器版本导致字段或层级变化时,进入适配与 Schema 校验;关键字段无法映射时,不把空值结果继续放行。

只有页面内容本身确实需要重新识别时,才进入表格、OCR 或顺序校正等专项处理。工具输出问题和页面识别问题要分开,不要全部归结为“再解析一次”。

这里的核心不是某条规则一定完美,而是让每次升级都有明确作用范围。即使异常检测偶尔判断不准,也能通过后面的固定坏样本持续修正,而不是把整条链路变成无法解释的黑盒。

可以把分流流程记成五步:默认解析,异常检测,专用处理,结构统一,质量放行。

内部 Schema 应该保存什么?

后处理的目标,不是产出一份更漂亮的 Markdown。

Markdown 适合人阅读,但下游需要明确知道一块内容是什么、来自哪里、是否可信、经过了哪个版本的处理。

一条内部内容记录,至少应考虑这些信息:内容文本、内容类型、页码、坐标、标题层级、父子关系、识别置信度、异常标记、解析器版本和原文件标识。

内容类型用来区分正文、标题、表格、图片说明、公式和代码。切分器看到表格时,处理方式不会和普通段落完全一样。

页码和坐标负责追溯。用户点击引用时,可以回到原始区域核验。

标题层级与父子关系负责补上下文。一段正文即使没有重复写章节名,也能知道自己属于哪个主题。

置信度和异常标记负责质量路由。低质量区域可以暂缓入库,也可以以“不完整”状态对外呈现。

解析器版本负责复现。当同一文件前后结果不一致时,团队能判断差异来自文档变化,还是解析工具和配置变化。

MinerU 输出到内部 Schema 的后处理链路

外部工具输出先经过顺序校正、结构去重和字段校验,再映射到稳定 Schema。Markdown 只是展示形式,不应成为唯一数据真相。

统一 Schema 还有一个容易被忽略的价值:稳定更新。

如果内容 ID 能由原文件、页码、区域和规范化文本稳定生成,那么重新处理一页时,系统可以识别哪些内容没有变化,哪些需要替换,哪些应当删除。

反过来,如果每次都按临时数组位置编号,前面新增一个文本块,后面所有 ID 都可能变化。一次小调整会变成全量重建,旧 Chunk 也更难清理。

Schema 还应区分“原始识别内容”和“规范化内容”。前者用于核对解析器到底看到了什么,后者用于清理空白、统一字段并交给切分。两者分开保存,出现争议时才能判断错误来自识别,还是来自后处理。若只留下最终文本,一旦清洗规则误删内容,团队就很难在不重新跑文件的情况下还原现场。

四类输出故障,应该怎么排查?

以下四个纯教学示例只用于展示检查顺序,不涉及任何真实项目。

教学示例一:同一段文字被写入两次

如果出现这种情况,可以检查重复来自 MinerU 的多个输出字段,还是适配层把同一区域映射了两次。坐标、内容类型、规范化文本和原文件标识可以帮助判断它们是否指向同一块原文。

教学示例二:表格同时出现结构化内容和扁平文本

如果出现这种情况,可以比较两种表示是否来自同一区域、字段和值是否一致,以及下游分别怎样消费。作为待验证的设计,可以让结构化表格用于切分和展示,让增强文本用于检索,但不能把两份表示当成两条独立证据重复入库。

教学示例三:解析器升级后标题路径消失

如果出现这种情况,可以比较升级前后的原始输出,再检查适配层是否识别了新字段或新层级。若外部结构已改变,版本映射与固定输入回归都需要重新验证,而不是直接在切分器里增加临时兼容判断。

教学示例四:同一页面重跑后所有 ID 都变化

如果出现这种情况,可以检查 ID 是否依赖数组位置或不稳定字段,再确认旧索引的替换条件。稳定 ID 的设计目标,是让未变化区域保持可识别,同时对真正变化的内容生成新版本;是否达到目标,要用相同输入反复运行并核对结果。

这四个教学例子想说明:后处理不应只剩一个统一的“清洗函数”。一种待验证的工程设计,是把它拆成有入口、有证据、有回归样本的故障处理链。

怎么证明后处理真的有用?

第一步不是看最终回答,而是建立固定解析样本。

样本不必一开始就覆盖所有文档,但要覆盖会改变输出结构的情况:同一区域出现多种表示、重复块与缺失块、标题层级变化、必要字段缺失、数组顺序改变,以及解析器升级后稳定 ID 大面积变化。

每个样本不一定逐字标注整份文件。可以先人工确认关键区域的期望类型、唯一表示、标题路径、原页位置和稳定标识,再保存解析器原始输出与内部 Schema,方便逐版本比较。

第二步是记录版本。

同一份输入要保存解析器、配置和后处理版本。否则今天结果变好,团队也无法判断是哪项修改造成的。遇到结果变差,更难稳定复现。

第三步是把解析测试与检索问题连起来。

每道问题仍要标注参考答案和正确证据位置,但 MinerU 后处理先检查的是这段证据在原始输出和内部 Schema 中是否对应同一区域,是否被重复写入,稳定 ID 与引用位置有没有变化。只有内部记录完整且一致、检索仍然找不到时,问题才交给召回和排序环节继续排查。

第四步是按异常类型看结果。

重复与缺失、表示冲突、必要字段、稳定 ID 和位置追溯不应该被压成一个总分。两次修改即使总分相同,也可能一次减少了重复块,另一次却让大量未变化内容获得新 ID。

MinerU 后处理版本验收清单

输出一致性、检索回归和版本差异要同时检查,解析器升级才具备替换旧链路的条件。

持续运行时,还要比较同一输入在不同解析器和适配版本下的结构差异。重复块数量、必要字段缺失、稳定 ID 变化和引用位置漂移都应单独记录;否则一次工具升级即使没有报错,也可能让索引发生大面积无效更新。

解析器升级最好分成候选生成、差异审查和索引切换三步。候选生成只写入隔离版本,不覆盖当前可检索内容;差异审查比较同一页面的区域数量、标题路径、表格表示、稳定 ID 和来源位置;确认必要字段与旧坏样本都通过后,才让新版本接管查询。

差异很多时,不能只用“新版更强”解释。先按原因分类:原文内容变化、解析器输出结构变化、适配层映射变化,还是后处理规则变化。正文相同但 ID 全变,通常优先检查身份生成规则;区域数量突然翻倍,优先检查重复表示;引用页码漂移,则要检查外部页序与内部位置字段的映射。

切换还需要清理和回退方案。新索引启用后,旧内容要退出检索,但不必立即销毁用于复盘的版本记录。若固定问题出现退化,可以恢复上一份可用索引,并根据保存的原始输出重现差异。没有候选版本和回退入口,工具升级就会变成一次不可逆的全量重建。

面试中讲到这里,可以把“后处理价值”落到一个明确结果:它让外部解析器可以替换,但下游看到的内容契约、引用方式和更新行为保持可检查。真正的验收对象不是某个工具是否返回成功,而是升级前后有没有重复证据、丢失结构、漂移引用和无法解释的大面积变更。

候选版本还可以用影子方式跑一批真实输入,但不参与正式回答。对同一个问题分别记录当前版本和候选版本会召回哪些内容、引用落在哪里,再按异常类型复核差异。影子结果只用于比较,不能因为某几次回答看起来更好就直接替换。

如果差异集中在少数文档类型,可以限定新适配器只处理已经验证的页面,其余仍走当前版本。这样发布范围与证据范围一致,也便于发生退化时快速退出。是否扩大范围,应由新增样本和固定坏样本共同决定,而不是由解析器版本号决定。

面试官继续追问,怎么接?

MinerU 和后处理层的职责怎么划分?

MinerU 负责把 PDF 中的版面、文字、表格等内容转换成中间结果。后处理层负责校正顺序、识别异常、统一内部字段、保留追溯信息并执行质量门槛。

前者关注尽可能提取,后者关注能否稳定进入下游。职责分开后,解析器可以替换,切分和索引不必跟着重写。

为什么不用大模型把所有输出重写一遍?

因为常规页面可能已经正确,额外重写会增加计算、延迟和不确定性,还可能改动原文。更稳妥的是先用可复现信号识别异常页,再对特定类型调用专用处理器,并保留前后结果用于回归。

只做 Schema 校验,能发现语义顺序错误吗?

不能。Schema 能发现字段缺失、类型错误和重复结构,却不能自动证明人类阅读顺序正确。顺序还要结合坐标、栏结构、标题关系和固定页面样本检查。结构合法与内容正确是两层问题。

解析器升级后,怎样判断可以直接替换旧版本?

先用同一批固定输入比较字段、层级、区域数量、稳定 ID 和引用位置,再跑对应检索问题。只要必要字段无法映射、旧坏样本复发或大量未变化内容获得新 ID,就不应直接替换旧索引,而要先修复适配层或限定升级范围。

后处理做到什么程度才算结束?

Markdown 看起来整齐只是起点。内容还要能够稳定切分、正确检索、返回原页,并且解析器升级后固定坏样本没有回退。是否继续增加复杂处理,要看它修复了哪些真实错误,以及新增成本是否值得。

MinerU 输出之后,怎样交付可维护的入库数据

把重点压缩成一段面试口述,可以这样回答:

MinerU 解析成功,只说明 PDF 已经生成了中间文本或结构,不代表内容可以直接进入 RAG。RAG 还要求输出结构稳定、重复与冲突可识别、结果能够增量更新并追溯到原页。

我的处理思路是先走默认解析,再检查重复块、缺失区域、同一内容的冲突表示、字段层级漂移和稳定 ID 变化。普通结果直接进入结构统一,异常结果分别进入区域去重、表示核对、版本适配或专项解析。所有结果最终映射到内部 Schema,保存内容类型、页码、坐标、标题层级、异常状态和解析器版本,再通过质量门槛进入切分。

验证时,我会固定同一批输入,保存升级前后的原始输出和内部 Schema,比较必要字段、区域数量、稳定 ID 与引用位置,再用同一批检索问题确认正确证据仍能进入候选。只有结构回归和检索回归同时通过,解析器版本才可以替换旧链路。

面试回答不能停在工具调用,还应说明外部输出如何进入稳定接口、版本变化怎样被发现、异常怎样分流,以及一次升级如何验证没有制造重复索引和引用漂移;这才是后处理能够长期维护的依据。

INTERVIEW FOLLOW-UPS

面试官会怎样继续追问?

这些追问会继续检查方案取舍、验证方法和项目事实。
  1. Q01

    哪些页面继续走默认解析,哪些要触发二次处理?

  2. Q02

    如何定义低置信度与异常输出,而不是凭肉眼判断?

  3. Q03

    为什么不把所有页面都交给最重的模型?

  4. Q04

    解析器升级后怎样做回归测试,避免旧文档变差?

PROJECT CHECK

换成你的项目,这几件事能否说清楚?

  • 按失败类型整理 MinerU bad case
  • 记录二次处理的触发条件
  • 比较准确性、延迟和资源消耗
  • 保留版本升级前后的回归样本
用自己的项目经历练一次