Skip to content
Development
Skill

/migrating-world-v4-to-v5

Upgrades a custom Workflow SDK World implementation from the v4 spec, or from a 5.0.0 beta, to the current v5 spec (spec version 8). Use when a package implements the `World` interface from `@workflow/world` and is moving to 5.x, or is on a 5.0.0 beta and the runtime reports

From plugin
workflow
2.5k6 skills1 agent1 command

Claude Code

$ npx -y skills add vercel/workflow --skill migrating-world-v4-to-v5 --agent claude-code

SKILL.md

migrating-world-v4-to-v5.SKILL.md
name: migrating-world-v4-to-v5
description: >-
  Upgrades a custom Workflow SDK World implementation from the v4 spec, or from a 5.0.0 beta, to the current v5 spec (spec version 8). Use when a package implements the `World` interface from `@workflow/world` and is moving to 5.x, or is on a 5.0.0 beta and the runtime reports `This Workflow runtime supports Worlds with spec version 6 through 8, but the configured World declares spec version N`; or when it shows event IDs that are ULIDs rather than slot positions, `Event id is not slot-numbered` at replay time, a `specVersion` the runtime refuses, `writeToStream` / `closeStream` / `readFromStream` as top-level World methods, `steps.get` or `events.listByCorrelationId` without a `runId`, a `'step'` queue kind or `__wkf_step_*` topics, a `preconditionGuard` capability, or a `createLocalWorld` / `createVercelWorld` factory.
metadata:
  author: Vercel Inc.
  version: '0.4.0'

Migrating a World from the v4 spec to v5

This skill is for a package that implements `World` from `@workflow/world`: a storage, queue and stream backend the Workflow runtime talks to. It is not for application code. If the task is bumping an app's `workflow` dependency, use the `migrating-workflow-v4-to-v5` skill instead; if the app both uses Workflow and ships its own World, run that skill first and this one second.

An app on the Vercel, Local or Postgres World needs nothing from this skill. Those ship with the SDK and are already on the v5 spec.

One change dominates the work. **Event ID allocation is required, is not visible from the type signatures, and a World that skips it type-checks, starts runs, and fails on the first replay.** Do that part first, then the mechanical rewrites. Do not begin with the type errors: they are the small half, and finishing them produces a World that looks migrated and is not.

Which spec version a pin produces

What a World declares follows the `@workflow/world` version it resolves, and the runtime admits a range. Check both before deciding how much work this is.

| `@workflow/world` | `SPEC_VERSION_CURRENT` / `mintedSpecVersion()` | Admitted by `workflow` 5.2.x (range 6 to 8)? | | --- | --- | --- | | any 4.x | 5 or below | No | | `5.0.0-beta.25` and earlier | 5 or below (no slot identity) | No | | `5.0.0-beta.35` to `beta.37` | 7 | Yes, but not spec 8 | | `5.0.0-beta.39` and later, all 5.0.x stable | 8 | Yes |

The range is printed by the startup error, and lives in the bundled `@workflow/core` as `assertWorldSupportsRuntimeProtocol`. A host that bundles its own copy of the runtime has its own ceiling: grep the bundle for `supports Worlds with spec version` to read it. Declaring above a host's ceiling makes that host refuse the World at startup, so a World that must also run under older hosts states which host versions each of its releases supports.

**A World already on a 5.0.0 beta** with slot-numbered IDs does not redo step 1. Bump `@workflow/world` and `@workflow/errors` to the stable line, confirm the declaration is `mintedSpecVersion()` (step 2), read the spec 8 notes in step 2, then audit the step 5 contract items and the fail checklist: several of them landed late in the beta line and a beta-era World commonly misses lazy `step_started`, the `runs.list` status array and `resolveData: 'skip-step-inputs'`. Run the conformance suite at the new version before calling it done.

**A World that predates event sourcing** (it exposes `runs.create`, `steps.update` and the like, and has no `events.create` that drives entity state) has no v4 event log to port. The whole `events.create` state machine is written from scratch. Use `packages/world-postgres/src/storage.ts` as the reference and keep its event-by-event structure.

Intake

Before editing, establish and report each of these:

1. **Where the World is.** Grep for `implements World`, `: World`, `World>` and `from '@workflow/world'`. Read the factory it exports. 2. **How event IDs are minted today.** Grep for `eventId`, `ulid`, `uuid`, `nanoid`, `nextval`, `AUTO_INCREMENT`, `IDENTITY`. Find the exact line that produces the ID written to storage. Note any place an ID is chosen before the write that stores it, for example an ID planned in advance and saved in a claim record so redeliveries reuse it. That design hands out a position before the commit and needs reworking, not porting. 3. **What settles a write race.** Read the `events.create` implementation. Note whether the ID or ordering is decided in process (read-then-write, an in-memory counter, a `Math.max` over loaded events) or in the store (unique constraint, conditional write, `INSERT ... ON CONFLICT`, a transaction). 4. **Which `specVersion` it declares.** Grep for `specVersion`. Note whether it is a literal or an imported constant. 5. **Which optional members exist.** Grep for `capabilities`, `analytics`, `getRuntimeDeadline`, `getEnvironment`, `createRunId`, `describeRun`, `getEncryptionKeyForRun`, `resolveLatestDeploymentId`, `cancelMany`, `experimentalSetAttributes`. 6. **Whether it provisions step topics.** Grep for `'step'`, `__wkf_step`, `stepQueue`. 7. **Whether it rejects stale writes.** Grep for `PreconditionFailedError`, `preconditionGuard`, `stateUpdatedAt`, `stateEventCount`, `stateCursor`, `412`. 8. **Where its process-wide state lives.** Grep the World's modules for top-level `const`/`let` holding a pool, client, socket, registry, cache, ULID factory, or a log-once boolean. Note every one: these are correct in a `require()`d package and wrong in a bundled one. 9. **How it is tested.** Grep for `@workflow/world-testing` and `createTestSuite`. A World without the conformance suite wired up gets it in this migration. 10. **What its store can make atomic.** A transaction, a conditional write or unique constraint, a server-side script (Redis Lua, a Durable Object or actor that is single-threaded per run), or none (a CRDT or eventually consistent store). Step 1 depends on the answer. 11. **Whether bytes

Read more
@vercel
Ships withworkflow

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

2.5k6 skills1 agent
Get the whole plugin

Stars on GitHub

Momentum

stars in total
2.5k
Star history of vercel/workflow on GitHub, a chart by star-history.com

Other skills on workflow.

internal-dev-workbench

internal-dev-workbench

Spin up a portless + tmux dev session for the Workflow SDK that gives each git worktree isolated `<branch>.<name>.localhost` URLs…

@vercel@vercelInstall Skill
migrating-to-workflow-sdk

migrating-to-workflow-…

Migrates Temporal, Inngest, Trigger.dev, and AWS Step Functions workflows to the Workflow SDK. Use when porting Activities,…

@vercel@vercelInstall Skill
migrating-workflow-v4-to-v5

migrating-workflow-v4-…

Upgrades an app from Workflow SDK 4.x to 5.0. Use when bumping the `workflow` / `@workflow/*` dependencies to v5, or when hitting…

@vercel@vercelInstall Skill
workflow-init

workflow-init

Install and configure Vercel Workflow SDK before it exists in node_modules. Use when the user asks to "install workflow", "set up…

@vercel@vercelInstall Skill
workflow

workflow

Creates durable, resumable workflows using Vercel's Workflow SDK. Use when building workflows that need to survive restarts,…

@vercel@vercelInstall Skill

More skills from other plugins.

brainstorming
Auto-invoked

brainstorming

You MUST use this before any creative work - creating features, building components, adding functionality, modifying behavior, or…

@obra@obraInstall Skill
ask-matt

ask-matt

Ask which skill or flow fits your situation. A router over the skills in this repo.

skills10d309k
@mattpocock@mattpocockInstall Skill
accessibility
Auto-invoked

accessibility

Design, implement, and audit accessible UI to WCAG 2.2 Level AA across Web, iOS, and Android — semantic ARIA roles and labels,…

ecc12d293k
@affaan-m@affaan-mInstall Skill
compiler-commit

compiler-commit

Use when you want to verify compiler changes and commit with the correct convention. Runs tests, lint, and format, then commits…

react1d252k
@facebook@facebookInstall Skill

Questions about migrating-world-v4-to-v5.

Which coding agents can use migrating-world-v4-to-v5?
migrating-world-v4-to-v5 installs in Claude Code, Codex, Cursor, Gemini CLI, GitHub Copilot, OpenCode and Windsurf with the skills CLI, using each agent's flag shown on this page. Flowy's auto-invocation, which fires a skill when your prompt matches, runs in Claude Code only.