Skip to content
Development
Skill

/migrating-to-workflow-sdk

Migrates Temporal, Inngest, Trigger.dev, and AWS Step Functions workflows to the Workflow SDK. Use when porting Activities, Workers, Signals, step.run(), step.waitForEvent(), Trigger.dev tasks / wait.forToken / triggerAndWait, ASL JSON state machines, Task/Choice/Wait/Parallel

From plugin
workflow
2.3k4 skills1 agent1 command
Install
$ npx -y skills add vercel/workflow --skill migrating-to-workflow-sdk --agent claude-code

How it fires

How this skill gets triggered: by you, by Claude, or both.

  • Fires itselfAuto-invocation. Claude auto-loads it when your prompt matches the work.Auto-invocation is when the right skill fires by itself at the right moment, driven by a FLOW.md router and a hook, instead of you invoking it by name. It is the difference between a skill being installed and a skill actually getting used.Read the full definition →
  • You can call itInvoke it directly when you want it.
  • Slash command/migrating-to-workflow-sdk

Context preview

The summary Claude sees to decide when to auto-load this skill.

Migrates Temporal, Inngest, Trigger.dev, and AWS Step Functions workflows to the Workflow SDK. Use when porting Activities, Workers, Signals, step.run(), step.waitForEvent(), Trigger.dev tasks / wait.forToken / triggerAndWait, ASL JSON state machines, Task/Choice/Wait/Parallel

SKILL.md

migrating-to-workflow-sdk.SKILL.md
name: migrating-to-workflow-sdk
description: Migrates Temporal, Inngest, Trigger.dev, and AWS Step Functions workflows to the Workflow SDK. Use when porting Activities, Workers, Signals, step.run(), step.waitForEvent(), Trigger.dev tasks / wait.forToken / triggerAndWait, ASL JSON state machines, Task/Choice/Wait/Parallel states, task tokens, or child workflows.
metadata:
  author: Vercel Inc.
  version: '0.2.0'

Migrating to the Workflow SDK

Use this skill when converting an existing orchestration system to the Workflow SDK.

Intake

1. Identify the source system:

  • Temporal
  • Inngest
  • Trigger.dev
  • AWS Step Functions

2. Identify the target runtime:

  • Managed hosting -> keep examples focused on `start()`, `getRun()`, hooks/webhooks, and route handlers.
  • Self-hosted -> also read `references/runtime-targets.md` and explicitly say the workflow/step code can stay the same, but deployment still needs a `World` implementation and startup bootstrap.

3. Extract the source constructs:

  • entrypoint
  • waits / timers
  • external callbacks / approvals
  • retries / failure handling
  • child workflows / fan-out
  • progress streaming
  • external side effects

Default migration rules

  • Put orchestration in `"use workflow"` functions.
  • Put side effects, SDK calls, DB calls, HTTP calls, and stream I/O in `"use step"` functions.
  • Use `sleep()` only in workflow context.
  • For Signals, `step.waitForEvent()`, and `.waitForTaskToken`, choose exactly one resume surface:
  • `resume/internal` -> `createHook()` + `resumeHook()` when the app resumes from server-side code with a deterministic business token.
  • `resume/url/default` -> `createWebhook()` when the external system needs a generated callback URL and the default `202 Accepted` response is fine.
  • `resume/url/manual` -> `createWebhook({ respondWith: 'manual' })` only when the prompt explicitly requires a custom response body, status, or headers.
  • If a callback-URL prompt does not specify response semantics, default to `resume/url/default` and make the assumption explicit in `## Open Questions`.
  • Never pair `createWebhook()` with `resumeHook()`, and never pass `token:` to `createWebhook()`.
  • Wrap `start()` and `getRun()` inside `"use step"` functions for child runs.
  • Use `getStepMetadata().stepId` as the idempotency key for external writes.
  • Use `getWritable()` in workflow context to obtain the stream, but interact with it (write, close) only inside `"use step"` functions.
  • Prefer rollback stacks for multi-step compensation.
  • Choose app-boundary syntax in this order:

1. If the prompt explicitly asks for framework-agnostic app-boundary code, use plain `Request` / `Response` even when a framework like Hono is named. 2. Otherwise, if the target framework is named, shape app-boundary examples to that framework. 3. Otherwise, keep examples framework-agnostic with `Request` / `Response`. Do not default to Next.js-only route signatures unless Next.js is explicitly named.

> Fast memory aid: > - Callback URL + default ack -> `createWebhook()` > - Callback URL + custom ack -> `createWebhook({ respondWith: 'manual' })` > - Deterministic server-side resume -> `createHook()` + `resumeHook()`

Fast-path router

Load `references/resume-routing.md` when the source pauses for Signals, `step.waitForEvent()`, or `.waitForTaskToken`.

Fast defaults:

  • callback URL only -> `resume/url/default`
  • callback URL + explicit custom response -> `resume/url/manual`
  • deterministic server-side resume -> `resume/internal`
  • self-hosted -> add `runtime/self-hosted`
  • named framework -> add `boundary/named-framework`
  • explicit framework-agnostic request -> add `boundary/framework-agnostic`

Before drafting `## Migrated Code`, write the selected route keys in `## Migration Plan`.

Source references

  • Temporal -> `references/temporal.md`
  • Inngest -> `references/inngest.md`
  • Trigger.dev -> `references/trigger-dev.md`
  • AWS Step Functions -> `references/aws-step-functions.md`

Shared references

  • `references/shared-patterns.md` — reusable code templates for hooks, child workflows, idempotency, streaming, and rollback.
  • `references/runtime-targets.md` — Managed vs custom `World` guidance.
  • `references/resume-routing.md` — route-key selection, obligations, and exact `## Migration Plan` shape.
  • `references/retries.md` — canonical retry mechanics: `stepFn.maxRetries`, `RetryableError({ retryAfter })`, `FatalError`.

Required output shape

Return the migration in this structure:

## Migration Plan
## Source -> Target Mapping
## Migrated Code
## App Boundary / Resume Endpoints
## Verification Checklist
## Open Questions

Verification checklist

Fail the draft if any of these are true:

  • [ ] `## Migration Plan` omits `Route keys`
  • [ ] `## Migration Plan` omits `Why these route keys`
  • [ ] `## Migration Plan` lists route keys that do not match the prompt
  • [ ] `## Migration Plan` lists required code obligations that do not match the selected route keys
  • [ ] Source-framework primitives remain in the migrated code
  • [ ] Side effects remain in workflow context
  • [ ] `sleep()` appears inside a step
  • [ ] Stream interaction (`getWriter()`, `write()`, `close()`) appears inside a workflow function
  • [ ] Child workflows call `start()` / `getRun()` directly from workflow context
  • [ ] External writes omit idempotency keys
  • [ ] Hooks/webhooks are missing where the source used signals, waitForEvent, or task tokens
  • [ ] A callback-URL flow uses `createHook()` + `resumeHook()` instead of `createWebhook()`
  • [ ] A `resume/url/default` or `resume/url/manual` migration invents a user-authored callback route or `resumeWebhook()` wrapper when `webhook.url` should be the only resume surface
  • [ ] `createWebhook()` is given a custom `token` or paired with `resumeHook()`

Validation note:

  • Reading webhook request data in workflow context is allowed. Only `request.respondWith()` is step-only.

Additional fail

Read more
Ships withworkflow

Workflow SDK: Build durable, reliable, and observable apps and AI Agents in TypeScript

Get the whole plugin
Stats
2,304
Stars
325
Forks
Active
Maintenance
TypeScript
Language
Apache-2.0
License
7h ago
Last commit
9mo ago
Created

Repo: vercel/workflow