Payload 与错误

所有节点间传递的数据类型,也就是 workflow payload,都必须继承 WorkflowPayload。该类型来自核心包:
export interface WorkflowPayload {
  errCode: number;
  errMessage: string;
}
成功输出统一使用:
{
  errCode: 0,
  errMessage: ""
}

输出 payload

Output node 应该显式返回包含 errCodeerrMessageitems 的对象:
interface WorkflowOutputItem {
  id: string;
  title: string;
  content: unknown;
  contentType?: "markdown" | "text" | "json" | "audio";
  collapsed?: boolean;
}

interface OutputPayload extends WorkflowPayload {
  items: WorkflowOutputItem[];
}

const outputNode = workflow.createOutputNode<Parsed, OutputPayload>({
  name: "output",
  format(result) {
    return workflow.createOutputPayload({
      items: [{
        title: "Result",
        content: result,
        contentType: "json",
        collapsed: false,
      }],
    });
  },
});
items 是当前唯一用户可见输出载体。App、server embed、server/web 日志和 external response 都读取该数组;assistant 消息的完整输出也保存在 items 中,而不是顶层 content 如果业务失败但 executor 没有崩溃,可以返回非零 errCode 和可读 errMessage。外部 Dify 风格 API 会读取最终 report 里的 errCode:只有 executor 成功且 errCode === 0 才映射为 succeeded

WorkflowResult

底层 safe run 会把 workflow 执行结果归一为:
type WorkflowResult<T> =
  | { ok: true; data: T }
  | { ok: false; error: SerializedWorkflowError };
执行报告中的 result 字段会保存该结构。App 和 server web 会根据 report、stdout、stderr 和 output node 输出组合出最终展示。

用户输入等待

用户输入节点会把 workflow 暂停成持久的 waiting_for_input 状态,而不是把它标记为普通失败。报告中会包含:
字段说明
pendingUserInput当前等待的请求,包含 requestId、节点名、标题、描述、表单 params、默认值和节点 metadata。
resolvedUserInputs本 run 已提交的答案数组,包含 requestId、节点名、valuessubmittedAt
Runtime event 会发出 user_input_requesteduser_input_resolved。等待状态的标准错误码映射为 202,用于表示 workflow 仍可恢复;成功恢复后的节点 payload 仍必须继承 WorkflowPayload,默认包含 errCode: 0errMessage: ""requestIdvaluessubmittedAt

WorkflowError

可以主动抛出 workflow.WorkflowError,附带类型、消息、节点和 metadata。框架也会把普通异常转换成 WorkflowError 常见错误类型包括:
  • 输入校验失败。
  • 节点执行失败。
  • workflow 执行失败。
  • 文件解析失败。
  • provider 调用失败。
  • abort 或 timeout。
错误会被序列化,避免直接暴露完整 stack 或第三方 SDK 原始响应。

UI 中的错误

  • App 本地运行会把本地 stdout/stderr 和 report 写进本地运行缓存。
  • server run 会持久化 RunResult,日志页从 /api/workflows/{name}/runs/{runId} 读取。
  • waiting_for_input run 会继续保留 pendingUserInput,App/server embed 可以提交答案恢复同一个 runId
  • 外部 blocking API 返回 data.error;streaming API 通过 SSE error 或最终 workflow_finished 表达失败。

追踪

本文档首版由 issue #32 记录。payload 约束对齐 core/types/payload.tscore/workflow/errors.tsserver/src/routes/external.ts