@llama_index: 大多数AI管道的质量取决于我们提供的数据,而这些数据通常意味着PDF或其他非结构化文档…

X AI KOLs Timeline 工具

摘要

Parse-Flow 是 LlamaIndex 构建的一个开源可视化工作流设计器,它将四个文档处理原语——Parse(解析)、Classify(分类)、Split(分割)和 Extract(提取)——串联到一个由 LlamaAgents 工作流驱动的拖拽画布中,能够从非结构化企业文档(如PDF、合同和发票)中可靠地提取结构化数据。

大多数AI管道的质量仅取决于我们提供的数据,而通常这意味着PDF或其他非结构化文档。 合同、发票、报告……它们都混合了特殊的布局、语言和上下文,从这些文档中可靠地提取结构化数据仍然是企业AI领域最难解决的未解难题之一。 Parse-Flow 是我们为解决这一问题而构建的开源项目。它将四个文档处理原语置于可视化工作流设计器的核心: Parse — 从原始文档中清理出干净的 Markdown 和文本 Classify — 将文档分配到用户定义的类别 Split — 将文档分割成带类型的块 🪏 Extract — 根据模式提取结构化 JSON 您将步骤拖拽到画布上,放入一个文档,然后观察事件在管道运行时流回来。底层由 LlamaAgents 工作流驱动,该工作流一步一步地遍历您的流程,使每个转换都可观察,每个失败都成为一等公民。 关于架构的完整文章:https://llamaindex.ai/blog/designing-a-visual-document-intelligence-workflow-with-llamaparse?utm_medium=socials&utm_source=twitter&utm_campaign=2026-jun-… 源代码:http://github.com/run-llama/parse-flow…
查看原文
查看缓存全文

缓存时间: 2026/06/05 02:22

大多数 AI 流水线的质量取决于我们提供给它们的数据,而这通常意味着 PDF 或其他非结构化文档。

合同、发票、报告……这些文档都混合了特殊的布局、语言和上下文,要从它们中提取出可靠的结构化数据,仍然是企业 AI 领域最难解决的问题之一。

Parse-Flow 是我们为直面这一问题而构建的开源项目。它将四个文档处理原语置于一个可视化工作流设计器的核心:

  • 解析 (Parse) — 从原始文档中提取干净的 Markdown 和文本
  • 分类 (Classify) — 将文档分配到用户定义的类别
  • 分割 (Split) — 将文档分割成带类型标记的片段
  • 🪏 提取 (Extract) — 根据模式提取结构化 JSON

你可以将步骤拖拽到画布上,放入文档,然后观察流水线运行时事件流回。其底层由 LlamaAgents 工作流驱动,该工作流会逐步遍历你的流程,使每一次转换都可观察,每一次失败都成为一等值。

有关架构的完整文章在此:https://llamaindex.ai/blog/designing-a-visual-document-intelligence-workflow-with-llamaparse?utm_medium=socials&utm_source=twitter&utm_campaign=2026-jun-… 源代码在此:http://github.com/run-llama/parse-flow…


Parse-Flow:开源可视化文档智能工作流设计器

来源:https://www.llamaindex.ai/blog/designing-a-visual-document-intelligence-workflow-with-llamaparse?utm_medium=socials&utm_source=twitter&utm_campaign=2026-jun-

非结构化文档仍然是企业存储和共享其运行所需信息的主要界面。从合同到发票再到报告,这些文档都有一个共同点:它们都是布局、语言和上下文的混合体,下游系统无法直接使用。文档智能,即将这些文档转化为结构化、机器可读数据的技术,是使现代 AI 栈的其他部分真正对企业有用的关键层,因为如果没有稳健的解析、分类、分割和提取,每一个检索流水线、每一个智能体、每一个分析仪表盘都将建立在脆弱的基础之上。

Parse-Flow 是一个小型开源项目,它将四个文档处理原语——解析 (Parsing)提取 (Extraction)分类 (Classification)分割 (Splitting)——置于可视化工作流设计器、异步工作进程和实时事件仪表盘的中心。你可以将步骤拖拽到画布上,放入文档,然后观察流水线运行时事件流回。本文将介绍它的构建方式,并特别关注后端工作流是如何基于 llama-agents (https://github.com/run-llama/llama-agents) 工作流 (https://github.com/run-llama/llama-agents) 设计的。

[ParseFlow 画布]

系统形态

Parse-Flow 由四个协作进程组成:

  • 一个 React 前端,承载基于节点的工作流设计器、运行视图和任务仪表盘。
  • 一个 Bun 服务器,负责接收上传文件、与 LlamaParse 平台通信、将任务加入队列、从 Postgres 读取历史记录,并通过服务器推送事件 (Server-Sent Events) 将事件流桥接到浏览器。
  • 一个 Python 工作进程,负责消费任务并执行实际的文档工作流。
  • Redis 作为任务队列和事件总线,Postgres 作为任务及其事件历史的主记录系统。

通信模式如下:Bun 服务器将任务推送到 Redis 列表,工作进程取出任务,并在任务运行时,将每个事件添加到每个任务的 Redis 流中,同时持久化到 Postgres。Bun 服务器通过创建一个专用的订阅者连接、发送心跳包并在观察到最终事件后关闭连接,将此流桥接到浏览器。

这种分离带来了两个主要好处:

  • 工作进程可以慢速运行而不会阻塞 HTTP 层。
  • 每个事件都被捕获两次(一次在实时流中,一次在持久化存储中),因此重新加载页面的用户可以查看并重放从 Postgres 重建的完整历史记录。

四个原语,任意组合

工作流词汇表故意设计得狭窄,并专注于 LlamaParse 平台提供的服务:

  • parse — 使用 Parse 将文档转换为干净的 Markdown 和文本,可指定层级和可选提示。
  • classify — 根据一组用户定义的规则,为文档分配一个类别,并附带推理过程和置信度分数。
  • split — 根据类别列表将文档分割成带类型标记的片段。
  • extract — 根据用户提供的 JSON 模式,从文档中提取结构化 JSON。

赋予系统表达能力的并非是原语本身,而是允许配对图 (allowed-pairs graph),它限制了原语之间如何链式连接。并非所有转换都是有意义的:extract 总是终止步骤,parse 可以交给其他三个中的任何一个,classifysplit 可以根据匹配的规则或类别路由到 parseextract。前端在流程提交之前会根据此图进行验证,后端在接收时也会重新验证。

最终结果是一个基于 JSON 的小型特定领域语言:FlowDefinition 包含有序的步骤和类型化的交接点,它足够丰富以描述大多数真实的文档流水线(解析后提取、分类后路由到正确模式、按章节分割后以不同方式解析每个部分),同时又足够小巧以便进行全面推理。

[ParseFlow 中流程的 JSON 定义]

核心的 LlamaAgent 工作流

有趣的设计工作主要集中工作进程中,这里有一个 LlamaAgent Workflow 在运行时解释用户定义的流程。

llama-agents 框架提供了一个事件驱动、无偏见的 (unopinionated) 工作流引擎:每个 @step 是一个异步函数,接收一个事件并返回一个或多个事件,运行时将事件路由到类型签名匹配的步骤。状态存储在一个类型化的 Context 存储中,步骤可以事务性地读取和编辑。通过 ctx.write_event_to_stream 写入的事件会被暴露给观察该运行的对象(在我们的场景中,即将其转发到 Redis 和 Postgres 的工作进程)。

Parse-Flow 的 DocumentWorkflow 只暴露了三个步骤,执行系统的关键在于它们如何协作来遍历任意长度的流程。

步骤 1 — 引导 (bootstrap)

第一个步骤接收一个携带已解析的 FlowDefinition 和 LlamaCloud 文件 ID 的 RedisInitialEvent。它将流程写入工作流状态,记录当前索引为零,并发出当前第一步所需的类型化输入事件(ParsingInputEventClassifyInputEventSplitInputEventExtractInputEvent)。从这之后,工作流由数据驱动;引导步骤再也不会运行。

步骤 2 — 工作 (worker)

工作步骤的输入类型故意设计得很宽:任何 InputEvent。它根据事件类型进行模式匹配,推进状态中的步骤索引,并调度到 LlamaParse 平台上对应的操作。每个操作返回一个类似 Rust 的 Result (https://github.com/AstraBert/better-result-py/blob/71f5973c7296727e307738b540ce2aa54442712e/src/better_result/result.py#L60),该结果被解包为类型化的成功事件(包含解析后的 Markdown、分类结果、分割后的片段或提取的 JSON)或携带失败信息的 ErrorOutputEvent

一个虽小但重要的细节:一旦 parse 步骤产生了 parse_job_id,后续的 classifyextract 操作会优先使用该 ID 而非原始文件。这意味着当用户链式使用 parse → extract 时,提取步骤会基于已解析的表示进行操作,而不是从头开始重新解析文件,这是通过跨步骤共享状态而带来的免费延迟和成本降低。

步骤 3 — 路由器 (router)

后处理步骤是运行时实际执行允许配对图的地方。它会查看最后的输出事件、流程中的当前步骤以及前一步记录的交割描述。根据这三条信息,它决定下一步发出什么:

  • 如果已经走到流程末尾,它将最后的输出包装在 WrapperStopEvent 中,工作流终止。
  • 如果输出是错误,则短路直接停止。
  • 否则,它根据交割类型(classify-extractparse-classifysplit-parse 等)构造下一个输入事件。对于路由交割,这需要查找与上一步匹配的规则对应的 JSON 模式、解析层级和提示或类别,并将它们打包到下一个输入事件中。

然后这个路由器再次发出一个 InputEvent,该事件循环回到工作步骤。引导-工作-路由器三元组成为一个状态机,逐步遍历用户的流程,每一步都是类型化的,每一次交割都经过验证,每一个事件都可观察。

[仪表盘显示 ParseFlow 运行期间的事件]

为什么这个设计能站住脚

三个特性使得这个设计用起来很舒服。

流程存在于事件中,而非代码中。 同一个 DocumentWorkflow 运行所有任务。新的流水线不需要新的 Python 代码,只需要一个新的 JSON 流程定义。这正是使其上面的可视化设计器成为可能的原因。

每一次转换都是可观察的。 因为每个步骤在返回之前都会将其事件写入流,仪表盘看到的工作流与工作流自身看到的一致。没有单独的日志层会与现实脱节。

失败是一个值。 错误是一等输出事件,路由器知道如何将它们干净地转换为停止。用户会收到一个带有实际消息的最终事件;系统永远不会无声地挂起。

文档智能才是关键

在 2026 年,人们很容易认为解析和提取是已经解决的问题,隐藏在模型调用背后。但事实并非如此。一个用错误模式对发票进行分类、在错误边界分割合同、或从错误页面提取日期的流水线,会以下游无法通过任何检索技巧恢复的方式失败。那些持久的系统是那些认真对待文档智能,并将其视为一等工程问题的系统:可组合的原语、经过验证的转换、可观察的运行、持久化的历史。

Parse-Flow 是一个小型的例子,展示了当你让自己正确设计工作流层时会是什么样子:四个原语、一个类型化的交割图、以及一个唯一任务就是遍历它的 LlamaAgent 工作流。

尝试它

完整的源代码是开放的。克隆它,指向一个 LlamaCloud 密钥,然后带上你自己的文档。

github.com/run-llama/parse-flow (http://github.com/run-llama/parse-flow)

相似文章