Workflow Context
The main interface for interacting with Stepflow workflows
Workflow Context
The WorkflowContext is the primary interface provided to your workflow handler. it provides methods for executing steps, sleeping, waiting for events, and logging.
const myWorkflow = createWorkflow({ id: "my-workflow" }, async (ctx) => {
// ctx is the WorkflowContext
});Properties
event
The event that triggered the workflow execution.
ctx.event.id: Unique event IDctx.event.name: Name of the event (usually the workflow ID)ctx.event.data: The payload passed to the triggerctx.event.timestamp: When the event was created
execution
Metadata about the current execution.
ctx.execution.id: Unique execution IDctx.execution.runId: The ID of the workflow run (persists across retries)ctx.execution.attempt: Current retry attempt (starts at 1)ctx.execution.startedAt: When the execution first started
Step Methods
step.run()
Executes a function as a checkpointed step. If the workflow retries, completed steps are skipped and their cached results are returned.
const result = await ctx.step.run(
"my-step",
async () => {
return await fetchData();
},
{
timeout: "30s",
idempotencyKey: "custom-key",
},
);step.parallel()
Executes multiple functions in parallel. Like step.run(), the entire group is checkpointed.
const [res1, res2] = await ctx.step.parallel("parallel-fetch", [
() => fetchOne(),
() => fetchTwo(),
]);step.invoke()
Invokes another workflow as a child. The parent workflow will wait for the child to complete.
const result = await ctx.step.invoke("child-workflow", {
some: "data",
});step.sendEvent()
Sends an event to the event bus. This is useful for triggering other workflows or notifying workflows waiting via waitForEvent.
await ctx.step.sendEvent("external-event-id", { status: "ok" });Durable Delays
sleep()
Pauses the workflow for a specific duration. The delay is durable and survives worker restarts.
await ctx.sleep("wait-a-while", "1h");sleepUntil()
Pauses the workflow until a specific date and time.
await ctx.sleepUntil("wait-for-deadline", new Date("2026-01-01"));External Events
waitForEvent()
Pauses the workflow until an external event is received or a timeout occurs.
const { eventData, timeout } = await ctx.waitForEvent(
"wait-for-approval",
"approval-id",
{
timeout: "24h",
},
);
if (timeout) {
// Handle timeout
}Logging
Stepflow provides structured logging that is captured in the workflow's timeline and visible in the dashboard.
ctx.log.info("Processing order", { orderId: "123" });
ctx.log.warn("Retryable error occurred");
ctx.log.error("Fatal error", { details: "..." });
ctx.log.debug("Internal state", { state: "..." });Metadata
Metadata allows you to store arbitrary state that is visible to real-time subscribers (like the React SDK) and the dashboard.
await ctx.setMetadata("progress", 50);
const progress = ctx.getMetadata<number>("progress");