你用大语言模型做会议摘要时,很可能只发了一轮对话。一个提示词塞进去:这是会议记录,给我一个摘要、把行动项拎出来、再告诉我每个人的情绪怎么样。一次调用,一个模型,返回一大块文字。演示跑通了,一到真实会议记录就挂。这三个任务形状完全不同。摘要是流畅的段落,行动项是带责任人的严格列表,情绪判断要给每个发言人一个结论。把它们挤在一个提示词里,它们会互相打架——模型把摘要的句子塞进行动项,或者忘记标注发言人,或者返回的行动项是一段需要你手动解析的文本。你还为所有内容串行付费,得到的是非结构化文本,而你想要的有一半是结构化数据。

更干净的形状是这样:跑三个专职代理,每个只做一件事,每个用自己的温度参数,其中两个返回的是有类型的对象,而不是自然语言。而且它们同时运行,因为谁也不需要等别人的输出。最后,第四个代理把三个结果合并成一份报告。这篇文章就搭建这么一个系统,素材来自 open-multi-agent 项目里的会议摘要入门示例。整个实现大约 280 行 TypeScript,并行是它的核心。

打开网易新闻 查看精彩图片

最终产出的是一份形状固定的 Markdown 报告:一段散文化的摘要,一张行动项表格,逐人的情绪判断,以及归纳出的下一步安排。这里展示的是针对一段 21 行的工程站会记录实际运行后得到的行动项部分——每一行都是作为有类型数据返回的,而不是脚本还需要去解析的散文。

这份完整报告还带着三段式的摘要、按发言人的情绪解读,以及一个归纳出来的“下一步动作”清单。所有这些内容由四个代理生成,其中三个是并发运行的。接下来就拆解它是怎么接线的。

三个专职代理接收同一份会议记录。每个专职代理都是一个普通的 Agent,拥有自己的系统提示词和温度值。先从摘要代理讲起——它输出的是散文,没有模式约束,温度略高,好让文字读起来自然。配置代码大致是:
名称设置为 ‘summary’,模型是 ‘claude-sonnet-4-6’,系统提示词写的是:“你是一个会议记录员。给你一份会议记录,生成一个三段式摘要:1. 讨论了什么(议程);2. 做出的决定;3. 团队需要记住的重要背景或风险。纯散文,不要列表要点。总共 200-300 词。”允许的最大对话轮次是 1,温度设为 0.3。

另外两个专职代理让这套方案从“给大模型打三次电话”变成了可靠的工程管道:它们返回的是有类型的对象,不是文本。你声明一个 Zod 模型,把它作为 outputSchema 交给代理,然后从 result.structured 上读取解析好的结果。

行动项是一个列表,而且每一条必须携带责任人。截止日期是可选的,因为真实的会议很多时候不会明确提及日期。对应的模式定义是:一个对象,其中 items 是一个数组,数组里每个元素包含一个用字符串描述的任务(“要采取的行动”)和一个字符串代表的责任人。这些字段都有相应的 .describe() 注释来指导模型生成。

情绪判断专职代理同样返回一个结构化结果。它为每个发言人输出一个情绪标签,并且可以附带一句简短的评估。模式可能是每个发言人的名字映射到一个情绪对象,或者是一个发言人数组,其中包含名字、情绪值以及置信度或依据。这个模式会迫使模型对每个发言人做出一个判断,而不是在段落里泛泛地提几句“气氛积极”。

三个代理各拿一份相同的会议记录,各自独立工作。摘要代理用 0.3 的温度产出自然段落;行动项代理用更低的温度(比如 0.1)来保证结构的严格性;情绪代理则可能用适中的温度(比如 0.2),在标签判定上既保持稳定又允许一定灵活性。由于它们互不依赖,可以在同一个时间窗口内同时发起请求,而不是一个接一个地等待。

第四个代理负责合并。它接收其它三个代理已经处理好的结构化结果和摘要文本,以自己的系统提示词和输出模式,生成最终的报告。在这个合并阶段,摘要的散文可以直接拼接,行动项列表可以规范化为 Markdown 表格,逐人情绪可以按发言人在表格中呈现,而下一步动作则是综合行动项和情绪的新推断。合并代理的模式也声明为 Zod 对象,包含摘要字符串、行动项数组、情绪数组、下一步数组等字段,这样报告的结构就被锁死。

这种设计解决了一个关键困境:当你让一个提示词同时干三件事,就必须面对非结构化输出和结构化需求之间的矛盾。通过把每个子任务拆成专职代理,并且对需要结构的部分显式地声明 Zod 模式,你从大模型那里拿到的就不再是需要后续用正则去抓取的模糊文本,而是可以直接用的对象。摘要任务仍然保持散文形式,因为它天然适合散文;而行动项和情绪则变成可以被下拉菜单、数据库直接消费的数据行。

并行的意义不止于缩短端到端耗时。它还让每个专职代理的温度调优变得独立可控。摘要需要一定创造性,用它 0.3 的温度;行动项要绝对精确,用接近 0 的温度;情绪判断介于两者之间。如果把它们混在一个提示词里,你只能设置一个统一的温度,这就必然在某些子任务上妥协。拆开之后,你可以为每个子任务精确设置生成参数,而且因为并发执行,并不会增加总等待时间。

这段实现只有大约 280 行 TypeScript,核心部分是用 open-multi-agent 框架定义 Agent 配置并跑起一个多代理工作流。每个 Agent 的定义都集中在几个关键字段:名字、模型、系统提示词、maxTurns、温度,以及对于要返回结构化数据的代理,还要加上 outputSchema。这些配置对象随后被一个编排器一次性启动,编排器负责向大模型服务发送请求并收集结果。三个代理同时跑,等到全部返回后,再触发合并代理。合并代理拿到摘要文本、行动项数组、情绪数组,以及原始的会议记录,然后按照最终报告的模式组装输出。

真实运行在一段 21 行的工程站会记录上的结果显示了这种模式的稳定性。返回的行动项列表每一条都有清晰的任务描述和责任人,没有任何多余的文字需要剥离。摘要部分三个段落分别覆盖议程、决定和风险,字数控制在 200-300 之间,不会出现突然膨胀到一大段的情况。情绪部分则为每位发言人带来了一个 verdict,不会遗漏谁,也不会把几个人的感受混在一起说。这些都是结构化约束带来的直接好处。

在工程层面,这种做法还引入了一个重要的副产品:失败隔离。如果摘要生成因为上下文太长而失败,行动项和情绪提取依然可以成功,因为它们运行在独立的请求里。你不需要为了一个子任务的崩溃而重新跑整个管线,可以针对出错的专职代理重试,而其他部分保持不变。在串行单提示词的方案中,任何一部分的异常都意味着整个调用需要重来,浪费了之前已生成的所有内容和相应的计算资源。

另外,成本模型也变得更清晰。你可以为不同的专职代理选用不同能力的模型,例如摘要用强写作能力的大模型,行动项和情绪判别用轻量且推理快的模型,合并用中等模型。这样每一分钱都不浪费在不对口的子任务上。在单提示词方案里,你往往只能为了满足最难的那个子任务而选择一个整体更贵的模型,然后让它在简单部分空转。

这套架构的复用性也很高。一旦你把行动项、摘要、情绪这三个代理的配置抽象成可组合的模块,就可以用类似的骨架去搭建复盘助手、客户访谈分析工具,或者医疗记录结构化流水线。只要遵循“分拆子任务、声明输出结构、并发执行、最后合并”的原则,就能把原本只能产出散文的大模型管道,改造成同时产出结构化数据和自然语言文本的混合系统。

从开发者的角度看,280 行 TypeScript 里,真正花在业务逻辑上的并不多。大量的行数用来声明 Zod 模式、定义 Agent 配置对象,以及拼接合并逻辑。这些代码可读性极高,几乎就是在用一种配置语言描述业务规则。相比在单提示词里靠话术去约束输出格式——比如反复强调“请务必以 JSON 格式返回”——用模式声明的方式更不易漂移,因为大模型在这个模式下受到更强的结构诱导,而不是单纯依赖提示词里的文字请求。

会议摘要这个场景天然地暴露了混合输出的痛点。人们在会议里产生的信息是多模态的:有讨论的脉络(适合散文)、有待办的责任划分(适合表格)、有气氛和态度(适合标签或打分)。如果坚持用一个提示词一次性全部输出,就必须在后续用解析器去提取。而解析器脆弱,只要模型稍微变动措辞,格式就可能走样。用并行专职代理加模式声明,从根本上把下游的解析负担往前移,让大模型自己把结构化部分按要求打包好,下游只需要做校验和组装。

这种“多代理、有类型输出”的方式,并不是在否定单一提示词的简单场景。如果你只是偶尔处理一个短会议,并且能够接受一点后续的人工格式化,那么一个提示词仍然是最省事的。但当你的系统需要批量处理每天几十场会议记录,并且要把行动项自动同步到项目管理工具,把情绪统计汇总到团队健康仪表盘时,稳定可靠的结构化输出就成了刚需。那时候,把这 280 行代码放进你的管线,所带来的可靠性提升,会远比每次祈祷模型不要乱写格式要划算。

此外,并行化对某些部署环境还有额外好处。在一些 serverless 平台或边缘运行时中,同时对大模型服务发起多个请求,可以利用连接池和并发处理能力来摊薄延迟。如果你用串行调用,网络往返时间的累加会让总耗时变得很高;并行之后,只要最慢的那个代理返回,整个阶段就结束。对于只有几秒差距的任务,并行几乎能让三个代理的花费等同于一个代理的时长。这对于需要准实时反馈的交互式产品,比如用户在会议结束后立刻想看到摘要的场景,就显得十分关键。

关于提示词设计,这里也暴露出一个常见反模式。很多人在写提示词时会试图用一个“全能型”角色描述,比如“你是一个专业的会议记录和分析师,请总结会议并提取行动项并评估情绪”。这种复合角色让模型的注意力在几个互斥的目标之间游移,尤其在长上下文中,模型容易遗漏结构要求。拆成三个单一职责的角色,每个只用关注自己那部分,相当于给模型减轻了认知负载。这在长会议记录的处理中表现得尤为明显——当记录超过几千字时,单一提示词丢失信息的概率明显上升。

将这个思路推及到其他领域,比如代码审查。你可以把一次 PR 审查拆成几个并行代理:一个专职检查代码风格和命名规范,一个检查潜在的错误模式和安全漏洞,一个总结改动意图和影响范围,最后一个合并成审查意见。每个代理可以独立使用不同的静态分析提示或知识库,温度也可以分别配置。最终产出既有散文式的总结,也有列表式的具体建议,还有关于风险的结构化字段。相比于一个庞大提示词,这种架构更容易维护和调优。

回到会议摘要系统本身,它的输出模式定义其实比表面看起来更讲究。行动项模式里 owner 字段的 .describe() 注释是“行动的责任人”,这促使模型从会议记录中提取出具体姓名或角色,而不是填“团队”。如果会议记录中出现了“我来跟进这个”这样的表述,模型需要将它映射到发言人的名字上,这就要求在系统提示词中配合给出映射规则或者至少提示模型注意人称与发言人的关系。这些细节不是在代码里写死的业务逻辑,而是通过提示词和模式描述传递给模型的信号,其有效性依赖于模型对这些指令的理解和执行。而这只有在子任务足够单一的情况下,模型才能更可靠地完成。

情绪分析代理的模式设计也需要斟酌。单纯输出一个情绪标签(如“正面”“负面”“中性”)可能丢信息。增加一个可选的理由字段,比如“情绪理由”,可以让模型同时输出它做出该判断的依据,比如“提到了项目延期,语气沮丧”。这个理由字段不是给最终报告直接展示的,而是可以用于后续审计或者增强对情绪判断的可解释性。由于它是结构化的,你可以自由选择是否在合并阶段保留它。结构化输出的灵活性就在这里——你有明确的字段,但可以决定显示哪些。

合并代理的生成逻辑其实遵循一个固定模板,但又不完全是死板的字符串拼接。它被要求综合三个子任务的结果来生成“下一步动作”。这个步骤利用了模型的一点推理能力:如果一个行动项截至日期很紧,而相关责任人的情绪显示压力大,合并代理可能会在下一步建议中增加“检查是否有阻塞项”之类的提醒。这种跨子结果的关联推理,在单一提示词方案中也许能自发产生,但没有保障;在并行专用代理架构中,因为前面已经把每部分的可靠结构结果稳定下来,再喂给合并代理,它有了干净的输入,产生这种关联判断的成功率就更高。

最后看一下这个项目的出处:open-multi-agent 的会议摘要示例。它是一个展示多代理并发和结构化输出的 cookbook。280 行 TypeScript 证明了这类系统并不需要庞大的框架。只要用好框架提供的 Agent 配置接口和 outputSchema 能力,平时用大模型干活的工程师可以很快上手改造自己的流水线。很多团队其实都在遭受“一次提示词输出混合内容”的折磨,他们可能已经写了不少正则或自定义解析器,但还是时不时被模型输出的格式变化绊倒。转向把每个任务拆开、显式声明模式的方式,原则上只要照着示例把业务模型替换掉,就能把不稳定的管道变牢靠。

所以回到标题:你的会议摘要工具可能正在一个提示词里悄悄地做三份工作,而这三份工作在互相拖后腿。用三个并行的专职代理,各司其职