本指南详细介绍 Cloudflare Workers 内的 Workflows API,包括方法、类型和使用示例。
WorkflowEntrypoint 类是 Workflow 定义的核心元素。Workflow 必须扩展此类并定义至少包含一个 step 调用的 run 方法,才被视为有效的 Workflow。
export class MyWorkflow extends WorkflowEntrypoint<Env, Params> {
async run(event: WorkflowEvent<Params>, step: WorkflowStep) {
// Steps here
}
}-
run(event: WorkflowEvent<T>, step: WorkflowStep): Promise<T>event- 传递给 Workflow 的事件,包括包含数据(参数)的可选payloadstep- 为你的 Workflow 提供步骤方法的WorkflowStep类型
run 方法可以可选地返回数据,通过 Workers API、REST API 和 Workflows 仪表板查询实例状态时可获取。如果你的 Workflow 正在计算结果、返回对象存储中数据的键,或生成你需要操作的某种标识符,这很有用。
export class MyWorkflow extends WorkflowEntrypoint<Env, Params> {
async run(event: WorkflowEvent<Params>, step: WorkflowStep) {
// Steps here
let someComputedState = await step.do("my step", async () => {});
// Optional: return state from our run() method
return someComputedState;
}
}WorkflowEvent 类型接受可选的类型参数 ↗,允许你为 WorkflowEvent 内的 payload 属性提供类型。
请参阅事件与参数文档了解如何在 Workflow 代码中处理事件。
最后,任何 JS 控制流原语(if 条件、循环、try...catch 块、Promise 等)都可在 run 方法内用于管理步骤。
export type WorkflowCronSchedule = {
/** Cron expression that triggered this event. */
cron: string;
/** Timestamp of the scheduled trigger, in milliseconds since the Unix epoch. */
scheduledTime: number;
};
export type WorkflowEvent<T> = {
payload: Readonly<T>;
timestamp: Date;
instanceId: string;
workflowName: string;
schedule?: WorkflowCronSchedule;
};WorkflowEvent是 Workflowrun方法的第一个参数。payload- 默认类型为any,如果提供了类型参数则为类型T。timestamp- 设置为 Workflow 实例创建(触发)时间的Date对象。instanceId- 关联实例的 ID。workflowName- 关联 Workflow 的名称。schedule- 由 cron 调度创建的 Workflow 实例的元数据,包括cron表达式和自 UNIX 纪元以来的scheduledTime(毫秒)。
请参阅事件与参数文档了解如何在 Workflow 代码中处理事件。
-
step.do(name: string, callback: (ctx: WorkflowStepContext): RpcSerializable): Promise<T> -
step.do(name: string, callback: (ctx: WorkflowStepContext): RpcSerializable, rollbackOptions?: WorkflowStepRollbackOptions<T>): Promise<T> -
step.do(name: string, config?: WorkflowStepConfig, callback: (ctx: WorkflowStepContext): RpcSerializable): Promise<T>name- 步骤名称,最多 256 个字符。config(可选)- 可选的WorkflowStepConfig,用于配置步骤特定重试行为。callback- 接收WorkflowStepContext的异步函数,可选返回 Workflow 持久化的可序列化状态。在 JavaScript Workflows 中,这包括用于大型二进制输出的新的、未锁定的ReadableStream<Uint8Array>。
-
step.do(name: string, config?: WorkflowStepConfig, callback: (ctx: WorkflowStepContext): RpcSerializable, rollbackOptions?: WorkflowStepRollbackOptions<T>): Promise<T>name- 步骤名称,最多 256 个字符。config(可选)- 可选的WorkflowStepConfig,用于配置步骤特定重试行为。callback- 接收WorkflowStepContext的异步函数,可选返回 Workflow 持久化的可序列化状态。在 JavaScript Workflows 中,这包括用于大型二进制输出的新的、未锁定的ReadableStream<Uint8Array>。rollbackOptions(可选)- 为步骤注册回滚逻辑。如果 Workflow 后续失败,已注册的回滚将按 step-start 的逆序运行。
在步骤内持久化 ReadableStream<Uint8Array> 对象后,不应重用——依赖从 step 返回的新流。字节从原始流保留,但实现可能不同。
:::
export class MyWorkflow extends WorkflowEntrypoint {
async run(_event, step) {
const reportStream = await step.do("read report from R2", async () => {
const object = await this.env.MY_BUCKET.get("reports/latest.csv");
if (!object?.body) {
throw new Error("Could not read reports/latest.csv from R2.");
}
return object.body;
});
const preview = await new Response(reportStream).text();
return { preview };
}
}type Env = {
MY_BUCKET: R2Bucket;
};
export class MyWorkflow extends WorkflowEntrypoint<Env> {
async run(_event: WorkflowEvent<unknown>, step: WorkflowStep) {
const reportStream = await step.do("read report from R2", async () => {
const object = await this.env.MY_BUCKET.get("reports/latest.csv");
if (!object?.body) {
throw new Error("Could not read reports/latest.csv from R2.");
}
return object.body;
});
const preview = await new Response(reportStream).text();
return { preview };
}
}-
step.sleep(name: string, duration: WorkflowDuration): Promise<void>name- 步骤名称。duration- 休眠时长,以秒数或WorkflowDuration兼容字符串表示。- 请参阅休眠与重试文档了解更多关于 Workflows 重试的信息。
-
step.sleepUntil(name: string, timestamp: Date | number): Promise<void>name- 步骤名称。timestamp- JavaScriptDate对象或自 UNIX 纪元以来的毫秒数,Workflow 实例将休眠至此时间。
step.waitForEvent(name: string, options: ): Promise<void>-name- 步骤名称。 -options- 包含type(最多 100 个字符 1)属性的对象,决定此waitForEvent调用在调用instance.sendEvent时将匹配的事件类型,以及可选的timeout属性,定义waitForEvent调用在抛出超时异常之前将阻塞多长时间。默认超时为 24 小时。
export class MyWorkflow extends WorkflowEntrypoint {
async run(event, step) {
// Other steps in your Workflow
let stripeEvent = await step.waitForEvent(
"receive invoice paid webhook from Stripe",
{ type: "stripe-webhook", timeout: "1 hour" },
);
// Rest of your Workflow
}
}export class MyWorkflow extends WorkflowEntrypoint<Env, Params> {
async run(event: WorkflowEvent<Params>, step: WorkflowStep) {
// Other steps in your Workflow
let stripeEvent = await step.waitForEvent<IncomingStripeWebhook>(
"receive invoice paid webhook from Stripe",
{ type: "stripe-webhook", timeout: "1 hour" },
);
// Rest of your Workflow
}
}请参阅事件与参数文档了解如何向运行中的 Workflow 实例发送事件。
export type WorkflowDynamicDelayContext = {
ctx: WorkflowStepContext;
error: Error;
};
export type WorkflowDelayFunction = (
input: WorkflowDynamicDelayContext,
) => string | number | Promise<string | number>;
export type WorkflowStepConfig = {
retries?: {
limit: number;
delay: string | number | WorkflowDelayFunction;
backoff?: WorkflowBackoff;
};
timeout?: string | number;
};WorkflowStepConfig是WorkflowStep的do方法的可选参数,定义允许你配置该步骤重试行为的属性。- 将
retries.delay设置为固定时长,或传递WorkflowDelayFunction从当前步骤上下文和抛出的错误计算下一次重试延迟。
请参阅休眠与重试文档了解更多关于 Workflows 重试的信息。
type WorkflowRollbackContext<T = unknown> = {
ctx: WorkflowStepContext;
error: Error;
output: T | undefined;
};
type WorkflowRollbackHandler<T = unknown> = (
ctx: WorkflowRollbackContext<T>,
) => Promise<void>;
type WorkflowStepRollbackConfig = Pick<
WorkflowStepConfig,
"retries" | "timeout"
>;
type WorkflowStepRollbackOptions<T = unknown> = {
rollback: WorkflowRollbackHandler<T>;
rollbackConfig?: WorkflowStepRollbackConfig;
};- 将此
WorkflowStepRollbackOptions对象作为step.do()的最终参数传递,为成功的步骤注册补偿操作。 rollback接收原始步骤上下文、导致 Workflow 失败的错误以及前向步骤返回的步骤输出。rollbackConfig将重试和超时设置应用于回滚处理程序本身。
export class BillingWorkflow extends WorkflowEntrypoint {
async run(_event, step) {
await step.do(
"create charge",
async () => {
const charge = await createCharge();
return { chargeId: charge.id };
},
{
rollback: async ({ ctx, output, error }) => {
const { chargeId } = output;
await refundCharge(chargeId, {
reason: `${ctx.step.name}: ${error.message}`,
});
},
rollbackConfig: {
retries: {
limit: 3,
delay: "30 seconds",
backoff: "linear",
},
timeout: "5 minutes",
},
},
);
}
}export class BillingWorkflow extends WorkflowEntrypoint<Env> {
async run(_event: WorkflowEvent<unknown>, step: WorkflowStep) {
await step.do(
"create charge",
async () => {
const charge = await createCharge();
return { chargeId: charge.id };
},
{
rollback: async ({ ctx, output, error }) => {
const { chargeId } = output as { chargeId: string };
await refundCharge(chargeId, {
reason: `${ctx.step.name}: ${error.message}`,
});
},
rollbackConfig: {
retries: {
limit: 3,
delay: "30 seconds",
backoff: "linear",
},
timeout: "5 minutes",
},
},
);
}
}export type WorkflowStepContext = {
step: {
name: string;
count: number;
};
attempt: number;
config: WorkflowStepConfig;
};WorkflowStepContext作为第一个参数传递给step.do回调函数。它提供有关当前步骤的运行时信息。step.name- 传递给step.do的步骤名称。step.count- 在当前 Workflow 运行中使用此名称调用step.do的次数(从 1 开始)。attempt- 当前尝试次数(从 1 开始)。首次尝试为1,第一次重试为2,依此类推。config- 此步骤已解析的WorkflowStepConfig,包括运行时应用的任何默认值。
请参阅步骤上下文文档了解使用示例。
Workers Paid 上的每个 workflow 默认支持 10,000 步骤。你可以在 Wrangler 配置的 Workflow 定义的 limits 属性中配置 steps,将此提高至 25,000 步骤:
{
"$schema": "./node_modules/wrangler/config-schema.json",
"workflows": [
{
"name": "my-workflow",
"binding": "MY_WORKFLOW",
"class_name": "MyWorkflow",
"limits": {
"steps": 25000
}
}
]
}[[workflows]]
name = "my-workflow"
binding = "MY_WORKFLOW"
class_name = "MyWorkflow"
[workflows.limits]
steps = 25_000step.sleep 不计入最大步骤限制。
请注意,Workers Free 上的 Workflows 限制为 1,024 步骤。请参阅 Workflow 限制 了解更多信息。
throw new NonRetryableError(message::string, namestringoptional)NonRetryableError
Workflows 通过绑定(binding) 概念直接向 Workers 脚本暴露 API。绑定允许你安全地调用 Workflow,而无需管理 API 密钥或客户端。
你可以通过在 Wrangler 配置中定义 [[workflows]] 绑定来绑定到 Workflow。
例如,要绑定到名为 workflows-starter 的 Workflow 并在 MY_WORKFLOW 变量上供 Worker 脚本使用,你需要在 [[workflows]] 绑定定义中配置以下字段:
{
"$schema": "./node_modules/wrangler/config-schema.json",
"name": "workflows-starter",
"main": "src/index.ts",
// Set this to today's date
"compatibility_date": "2026-08-17",
"workflows": [
{
// name of your workflow
"name": "workflows-starter",
// binding name env.MY_WORKFLOW
"binding": "MY_WORKFLOW",
// this is class that extends the Workflow class in src/index.ts
"class_name": "MyWorkflow",
},
],
}"$schema" = "./node_modules/wrangler/config-schema.json"
name = "workflows-starter"
main = "src/index.ts"
# Set this to today's date
compatibility_date = "2026-08-17"
[[workflows]]
name = "workflows-starter"
binding = "MY_WORKFLOW"
class_name = "MyWorkflow"你可以通过部署包含 Workflow 定义的 Workers 项目,然后使用 service bindings 或标准 fetch() 调用该 Worker,从 Pages Functions 绑定并触发 Workflows。
请参阅从 Pages 调用 Workflows文档了解示例。
你也可以绑定到与 Workflow 定义所在脚本不同的 Worker 脚本中定义的 Workflow。为此,在 Wrangler 配置的 [[workflows]] 绑定定义中提供带有脚本名称的 script_name 键。
例如,如果你的 Workflow 定义在名为 billing-worker 的 Worker 脚本中,但你从 web-api-worker 脚本调用它,你的 Wrangler 配置文件 将类似于:
{
"$schema": "./node_modules/wrangler/config-schema.json",
"name": "web-api-worker",
"main": "src/index.ts",
// Set this to today's date
"compatibility_date": "2026-08-17",
"workflows": [
{
// name of your workflow
"name": "billing-workflow",
// binding name env.MY_WORKFLOW
"binding": "MY_WORKFLOW",
// this is class that extends the Workflow class in src/index.ts
"class_name": "MyWorkflow",
// the script name where the Workflow is defined.
// required if the Workflow is defined in another script.
"script_name": "billing-worker",
},
],
}"$schema" = "./node_modules/wrangler/config-schema.json"
name = "web-api-worker"
main = "src/index.ts"
# Set this to today's date
compatibility_date = "2026-08-17"
[[workflows]]
name = "billing-workflow"
binding = "MY_WORKFLOW"
class_name = "MyWorkflow"
script_name = "billing-worker"如果你使用 TypeScript,每当你修改 Wrangler 配置文件时,请运行 wrangler types。这将根据你的绑定生成 env 对象的类型,以及运行时类型。
Workflow 类型提供允许你在 Worker 脚本内创建、检查状态和管理运行中 Workflow 实例的方法。
它是 wrangler types 生成的类型的一部分。
interface Env {
// The 'MY_WORKFLOW' variable should match the "binding" value set in the Wrangler config file
MY_WORKFLOW: Workflow;
}Workflow 类型导出以下方法:
创建(触发)给定 Workflow 的新实例。
-
create(options?: WorkflowInstanceCreateOptions): Promise<WorkflowInstance>options- 创建实例时传递的可选属性,包括用户提供的 ID 和 payload 参数。
ID 自动生成,但可以指定用户提供的 ID(最多 100 个字符 1)。当你将 Workflows 映射到系统中的用户、商户或其他标识符时很有用。你也可以提供 JSON 对象作为 params 属性,允许你传递 Workflow 实例作为其 WorkflowEvent 操作的数据。
// Create a new Workflow instance with your own ID and pass params to the Workflow instance
let instance = await env.MY_WORKFLOW.create({
id: myIdDefinedFromOtherSystem,
params: { hello: "world" },
});
return Response.json({
id: instance.id,
details: await instance.status(),
});返回 WorkflowInstance。
如果提供的 ID 已被尚未超过保留限制的现有实例使用,则抛出错误。要使用相同 ID 重新运行 workflow,可以 restart 现有实例。
你也可以在使用 Workers API 的 create 方法创建(触发)Workflow 实例时,为 Workflows 类型提供类型参数。请注意,这不会将类型信息传播到 Workflow 内部,因为 TypeScript 类型是构建时构造。
要向 Workflow 提供可选类型参数,在定义 Workflow 绑定时传递带有类型的类型参数:
interface User {
email: string;
createdTimestamp: number;
}
interface Env {
// Pass our User type as the type parameter to the Workflow definition
MY_WORKFLOW: Workflow<User>;
}
export default {
async fetch(request, env, ctx) {
// More likely to come from your database or via the request body!
const user: User = {
email: user@example.com,
createdTimestamp: Date.now()
}
let instance = await env.MY_WORKFLOW.create({
// params expects the type User
params: user
})
return Response.json({
id: instance.id,
details: await instance.status(),
});
}
}创建(触发)给定 Workflow 的一批新实例,一次最多 100 个实例。
当你一次调度多个实例时很有用。对 createBatch 的调用与对 create(单个实例)的调用处理方式相同,允许你在实例创建限制内工作。
-
createBatch(batch: WorkflowInstanceCreateOptions[]): Promise<WorkflowInstance[]>batch- 创建实例时传递的 Options 列表,包括用户提供的 ID 和 payload 参数。
batch 列表的每个元素都应包含 id 和 params 属性:
// Create a new batch of 3 Workflow instances, each with its own ID and pass params to the Workflow instances
const listOfInstances = [
{ id: "id-abc123", params: { hello: "world-0" } },
{ id: "id-def456", params: { hello: "world-1" } },
{ id: "id-ghi789", params: { hello: "world-2" } },
];
let instances = await env.MY_WORKFLOW.createBatch(listOfInstances);返回 WorkflowInstance 数组。
与 create 不同,此操作是幂等的,如果 ID 已被使用不会失败。如果具有相同 ID 的现有实例仍在其保留限制内,将被跳过并从返回数组中排除。
按 ID 获取特定 Workflow 实例。
get(id: string): Promise<WorkflowInstance>-id- Workflow 实例的 ID。
返回 WorkflowInstance。如果实例 ID 不存在则抛出异常。
// Fetch an existing Workflow instance by ID:
try {
let instance = await env.MY_WORKFLOW.get(id);
return Response.json({
id: instance.id,
details: await instance.status(),
});
} catch (e: any) {
// Handle errors
// .get will throw an exception if the ID doesn't exist or is invalid.
const msg = `failed to get instance ${id}: ${e.message}`;
console.error(msg);
return Response.json({ error: msg }, { status: 400 });
}创建实例时传递的可选属性。
interface WorkflowInstanceCreateOptions {
/**
* An id for your Workflow instance. Must be unique within the Workflow.
*/
id?: string;
/**
* The event payload the Workflow instance is triggered with
*/
params?: unknown;
/**
* The retention policy for the Workflow instance.
* Defaults to the maximum retention period available for the owner's account.
*/
retention?: {
/**
* How long to retain instance state after the Workflow completes successfully.
*/
successRetention?: WorkflowRetentionDuration;
/**
* How long to retain instance state after the Workflow ends in an errored or terminated state.
*/
errorRetention?: WorkflowRetentionDuration;
};
}
type WorkflowRetentionDuration = WorkflowSleepDuration;如果未设置 retention,实例状态将保留账户可用的最大保留期(Workers Free 计划 3 天,Workers Paid 计划 30 天)。请参阅保留限制了解更多信息。
以下示例创建一个实例,成功后保留状态 1 天,出错后保留 7 天:
let instance = await env.MY_WORKFLOW.create({
id: myIdDefinedFromOtherSystem,
params: { hello: "world" },
retention: {
successRetention: "1 day",
errorRetention: "7 days",
},
});表示 Workflow 的特定实例,并提供管理实例的方法。
declare abstract class WorkflowInstance {
public id: string;
/**
* Pause the instance.
*/
public pause(): Promise<void>;
/**
* Resume the instance. If it is already running, an error will be thrown.
*/
public resume(): Promise<void>;
/**
* Terminate the instance. If it is errored, terminated or complete, an error will be thrown.
*/
public terminate(options?: WorkflowInstanceTerminateOptions): Promise<void>;
/**
* Restart the instance from the beginning, or from a specific step.
*/
public restart(options?: WorkflowInstanceRestartOptions): Promise<void>;
/**
* Returns the current status of the instance.
*/
public status(): Promise<InstanceStatus>;
}返回 Workflow 的 id。
返回运行中 Workflow 实例的状态。
暂停运行中的 Workflow 实例。
恢复已暂停的 Workflow 实例。
从头或从特定步骤重启 Workflow 实例。
-
restart(options?: WorkflowInstanceRestartOptions): Promise<void>options- 控制实例从何处重启的可选属性。
let instance = await env.MY_WORKFLOW.get("abc-123");
// Restart the instance from the beginning.
await instance.restart();
// Restart the instance from the step named "aggregate".
await instance.restart({ from: { name: "aggregate" } });
// Restart the instance from the third call to a step named "process".
await instance.restart({ from: { name: "process", count: 3 } });从特定步骤重启时,将重用每个较早步骤的缓存结果,而目标步骤及后续步骤将重新运行。如果在实例执行历史中找不到匹配 from 的步骤,调用将抛出错误。
interface WorkflowInstanceRestartOptions {
/**
* The step to restart the instance from.
* If omitted, the instance restarts from the beginning.
*/
from?: {
/**
* The name of the step.
*/
name: string;
/**
* The 1-based index of the step, used when multiple steps share the same name and type. Defaults to 1 (the first occurrence).
*/
count?: number;
/**
* The step type. Use this to disambiguate when the same name is shared across step types. Defaults to "do".
*/
type?: "do" | "sleep" | "waitForEvent";
};
}from 对象标识要重启的步骤。只有 name 是必需的;仅当同一步骤名称在运行中出现多次时才需要 count 和 type。
name- 步骤名称。count- 步骤的从 1 开始的索引,当多个步骤共享相同名称和类型时使用(例如在循环内)。默认为1(第一次出现)。对应 步骤上下文 中的step.count。type- 步骤类型("do"、"sleep"或"waitForEvent")。默认为"do"。当相同名称在不同步骤类型间共享时使用。
终止 Workflow 实例。
-
terminate(options?: WorkflowInstanceTerminateOptions): Promise<void>options- 控制实例如何终止的可选属性。
let instance = await env.MY_WORKFLOW.get("abc-123");
// Terminate without running rollback handlers.
await instance.terminate();
// Run registered rollback handlers before terminating.
await instance.terminate({ rollback: true });如果 rollback 为 true,Workflows 在实例达到 terminated 状态之前运行已完成或符合条件步骤注册的回滚处理程序。没有回滚处理程序的步骤将被跳过。
interface WorkflowInstanceTerminateOptions {
/**
* If true, run registered rollback handlers before terminating the instance.
*/
rollback?: boolean;
}sendEvent(): Promise<void>-options- 发送给 Workflow 实例的事件type(最多 100 个字符 1)和payload。type必须与 Workflow 中相应waitForEvent调用中的type匹配。
成功时返回 void;如果 Workflow 未运行或处于出错状态则抛出异常。
export default {
async fetch(req, env) {
const instanceId = new URL(req.url).searchParams.get("instanceId");
const webhookPayload = await req.json();
let instance = await env.MY_WORKFLOW.get(instanceId);
// Send our event, with `type` matching the event type defined in
// our step.waitForEvent call
await instance.sendEvent({
type: "stripe-webhook",
payload: webhookPayload,
});
return Response.json({
status: await instance.status(),
});
},
};export default {
async fetch(req: Request, env: Env) {
const instanceId = new URL(req.url).searchParams.get("instanceId");
const webhookPayload = await req.json<Payload>();
let instance = await env.MY_WORKFLOW.get(instanceId);
// Send our event, with `type` matching the event type defined in
// our step.waitForEvent call
await instance.sendEvent({
type: "stripe-webhook",
payload: webhookPayload,
});
return Response.json({
status: await instance.status(),
});
},
};你可以多次调用 sendEvent,设置 type 属性的值以匹配 Workflow 中特定的 waitForEvent 调用。
这允许你同时等待多个事件,或使用 Promise.race 等待多个事件并让第一个事件推进 Workflow。
描述 Workflow 实例的状态。
type InstanceStatus = {
status:
| "queued" // means that instance is waiting to be started (see concurrency limits)
| "running"
| "paused"
| "errored"
| "terminated" // user terminated the instance while it was running
| "complete"
| "waiting" // instance is hibernating and waiting for sleep or event to finish
| "waitingForPause" // instance is finishing the current work to pause
| "unknown";
error?: {
name: string;
message: string;
};
output?: unknown;
rollback: {
outcome: "complete" | "failed";
error: {
name: string;
message: string;
} | null;
} | null;
};如果 Workflow 进入回滚,Workers API 在回滚执行期间继续报告 status: "running" 以保持兼容性。实例达到终端状态后,检查 rollback 以确定补偿步骤是否成功完成或失败。