01什么是 Harness?我这里说的 harness,不是单个工具,而是一套“主控执行框架”。普通 Agent 更像边想边做:用户问题 → 模型思考 → 调工具 → 看结果 → 再调工具 → 输出深度研究 harness 则更像一个有纪律的工程流程:这里的核心不是“能不能并行”,而是主 Agent 有明确角色:它负责判断目标、拆解任务、更新进度;它把可并行、边界清楚的研究子题交给 SubAgent;它负责冲突处理、证据筛选和最终成稿;它负责最终交付,SubAgent 不越权交付文件。这和 Claude CLI 做调研任务时的体验很像:先拆待办,再派子任务,最后把结果收拢成一个可用产物。02第一步:Skill 不是提示词,是任务方法论LightBot 的 Skill 是懒激活的。SkillPrepMiddleware每轮只把 Skill 的名称、描述和依赖摘要注入上下文,模型需要调用read_skill读取完整指令后才真正激活。这样做有两个好处:设计价值摘要先行不把所有 Skill 全量 prompt 塞进上下文,省 token按需激活只有当前任务真的需要“深度研究”时,才读取完整方法论内置deep-researchSkill 很能体现 harness 思路。它不是告诉模型“去搜索一下”,而是定义了完整操作纪律:不清楚时先ask_user澄清范围;用write_todos拆 2~8 个可独立调研的子问题;复杂子题优先派给research-agent;关键数字、冲突结论派给fact-verifier;主 Agent 最后综合成稿,不要机械拼接子智能体结果;只有用户要求可下载文件时,才写入outputs/reports/*.md并交付。这就是 Skill 的价值:它把“怎么做复杂任务”沉淀成可复用的工程流程,而不是每次靠模型临场发挥。03第二步:Todo 是主控面板,不是装饰复杂任务最怕模型做着做着忘了自己在干嘛。所以 LightBot 给父 Agent 自动注入write_todos。write_todos的语义不是简单覆盖列表,而是按稳定id合并:规则目的新传入 id 不存在则新增支持逐步拆计划已有 pending / in_progress 可被更新支持推进状态completed / cancelled 不被回滚防止模型漏传导致已完成项丢失未提及的旧项默认保留防止多次调用覆盖历史前端WriteTodosResult.vue和会话右侧状态栏会实时展示待办进度。后端SessionTodoServiceImpl则从消息 metadata 的工具事件中恢复最新 todo 快照。所以 Todo 在这里承担的是 harness 的“进度账本”:计划拆解 → 子题调研中 → 核验中 → 报告撰写中 → 已交付用户看到的不只是最后答案,还能看到 Agent 的工作过程是否靠谱。04第三步:SubAgent 做窄任务,主 Agent 做总编SubAgent职责research-agent深度研究员围绕单个明确子题检索证据,返回结构化发现fact-verifier事实核验员对关键断言、数字和冲突来源做对抗式核验critique-agent内容审核员审核结构、遗漏、表达和逻辑summarize-agent内容摘要员压缩长内容,提取关键信息注意,内置 prompt 对 SubAgent 的边界写得很死:不负责最终总报告;不调用write_todos;不调用present_artifacts;不继续调用delegate_to_subagent;不向用户追问。这就是主从分工:主 Agent PM 总编 交付人 SubAgent 研究员 / 核验员 / 审稿员SubAgent 是“窄专家”,不是另一个失控的主 Agent。这个边界还有服务端兜底。SubAgentPermissionPolicy会拦截父会话专属工具,当前明确禁止 SubAgent 执行present_artifacts。最终文件只能由主 Agent 汇总后交付。05第四步:委派subagents是同步等待结果的并行工具主 Agent 调用delegate_to_subagent派发任务。它的 schema 会动态注入当前 Agent 已绑定的 SubAgent 名称,也就是说模型看到的subagent_nameenum 就是真实可用列表,不用猜。工具支持两种模式:mode语义sync顺序执行一个或多个任务parallel有界并发执行多个任务现在的实现不是“后台提交后让模型轮询”,而是父 Agent 等每项任务到达终态,拿到 reply 后继续本轮推理。这点很关键。深度研究 harness 需要的是:派发子题 → 等调研完成 → 主 Agent 统一分析 → 最终输出而不是:派发出去 → 用户自己看散落结果并发执行也不是无限开线程。SubAgentTaskServiceImpl设置了硬上限:参数值单批最大任务数5默认并发3max_concurrency1~5 钳制parallel内部用滑动窗口:tasks[0..2] 并行跑完 → refreshBatch → tasks[3..4] 并行跑完 → 汇总这既能并行,又不会把模型 API、搜索 API、线程池一下打爆。06第五步:SubAgent 的运行时如何保证可控?每个 SubAgent 都是一轮独立的模型工具循环:根据 SubAgent 配置构造 system prompt;只加载它自己绑定的工具子集;模型配置优先用 SubAgent 自己的,否则继承主 Agent;执行流式工具调用循环;把最终 reply 写回subagent_run;事件实时推给父会话。几个工程点值得看。1. 独立线程池SubAgent 并行任务使用subAgentExecutor,不和主聊天线程池混用。否则主 Agent 等子 Agent,子 Agent 又排队等主线程池,高并发下容易线程饥饿。2. 确定性 taskId / batchId / threadId批次和任务 ID 基于 requestId、任务内容、index 做 hash。子线程 ID 也由 parentThreadId、subAgentName、requestId 生成。这样同一请求重入时能命中已有记录,支持幂等和续跑。3. 失败隔离单个子任务失败会写入 failed,并作为结果返回;其他并行任务不被直接打断。主 Agent 拿到完整结果后再决定如何处理缺口。4. 重试与超时SubAgent 有连接超时、token 间隔超时和模型重试次数。流式输出期间不按总时长强杀,只判断“长时间无新 token”这种停滞。这些不是炫技,都是为了让“AI 自己派活”在真实系统里可控。07第六步:事件流让用户看见团队在工作SubAgent 不是黑盒。LightBot 会把批次、任务、token、工具调用、错误等事件写回父会话:事件含义subagent_batch_start一批委派开始subagent_task_start单个任务开始subagent_token子智能体流式输出subagent_tool_call子智能体调用工具subagent_tool_result工具返回subagent_error_retry子智能体重试subagent_error子智能体失败subagent_task_done单任务结束subagent_batch_done批次结束前端有两层展示:组件作用SubAgentCallBlock在对话正文里展示本轮委派批次和任务输出ChatSessionRuntimePanel右侧状态栏展示待办、产物、子智能体进度ChatSubAgentRuntimeDrawer会话级子智能体运行抽屉,支持查看和停止SubAgentTaskDetailModal展示单个子任务详情、工具调用、事件和线程快照这就是 harness 体验的关键:用户能看到主 Agent 如何拆计划、谁在调研、哪里失败、最终产物在哪里。08第七步:最终产物只能由主 Agent 交付深度研究最后通常不是一句话,而是一份报告。LightBot 的交付链路是:sandbox_write_file / sandbox_append_file 写入 outputs/reports/research-report.md present_artifacts 校验 outputs/ 路径 生成预签名 URL 前端展示文件卡片present_artifacts只允许交付outputs/目录下的文件,不能交付 Skill 文件或临时工作区文件。这个限制很好:中间草稿可以乱写,最终交付物必须进入正式 outputs 区。前端ChatSessionRuntimePanel会从两类事件里提取产物:present_artifacts的 artifacts;sandbox_write_file/sandbox_append_file写入 outputs 且返回 URL 的文件。这让最终结果不只停留在聊天文本里,而是变成可下载、可预览、可复盘的产物。09为什么这套流程像 Claude CLI?Claude CLI 做调研任务体验好的地方,不是模型更会搜索,而是它把复杂任务组织成了“工程过程”:理解目标 → 拆 todo → 并行派 research agents → 核验与整合 → 写文件 → 交付结果LightBot 的这套设计也是这个方向:能力LightBot 对应实现任务方法论deep-research Skill计划可视化write_todos 状态栏并行调研delegate_to_subagent parallel专家分工research-agent / fact-verifier / critique-agent主控整合SubAgent 只返回子题结果,主 Agent 负责最终报告产物交付sandbox outputs present_artifacts过程观测subagent events runtime panel所以 SubAgent 并行委派不是孤立能力。它必须和 Skill、Todo、文件沙盒、产物交付、事件观测组合起来,才像一个真正能干活的 AI harness。10几个设计取舍取舍LightBot 的选择SubAgent 是否继承父 Agent 全部工具不继承,只用自己绑定的工具子集SubAgent 能否交付文件不能,present_artifacts是父会话专属委派是后台还是同步等待当前同步等待终态,让主 Agent 能继续整合并发是否无限不无限,单批最多 5 个任务token 是否持久化token 主要实时展示,关键事件才持久化Todo 是否覆盖写不覆盖,按 id 合并,防止漏传丢计划这些取舍背后是一句话:让模型有自主性,但不要让流程失控。11写在最后如果只看 SubAgent,它像是一个“并行工具”。但放到完整链路里看,它其实是深度研究 harness 的中间层。真正的价值在于:Skill 规定做事方法;Todo 让计划可见;SubAgent 承担并行调研;主 Agent 保留判断和总编权;文件工具把结果变成产物;事件流让过程可观测。这套机制让 Agent 从“会回答问题”往前走了一步:它开始像一个小型工程团队一样工作。模型可以负责推理,但平台要负责组织、约束和交付。这个边界立住了,复杂任务才有可能稳定完成。