Skip to content
decodecodeveloper docs
Storefront → Templates → Migration

Migrate script

What npx -p @decocms/blocks-cli deco-migrate actually does.

@decocms/blocks-cli provides deco-migrate for migrating a retired Fresh/Deno site to the released Blocks 7.x TanStack binding. This page documents what it does, what flags it accepts, and what it doesn't.

Quick start

# from your v1 site directory
npx -p @decocms/blocks-cli deco-migrate

That's it. The script analyzes the source layout, scaffolds Blocks 7.x files, transforms imports/JSX/APIs, cleans up dead code, generates a report, verifies the result, and bootstraps deps.

Flags

FlagPurpose
--source <dir>Source directory (default: current directory)
--dry-runPreview changes without writing files
--verboseShow detailed output for every transformation
--no-compileSkip the post-transform tsc --noEmit + vite build step
--no-cleanup-auditSkip the post-migration audit (read-only sanity check)
--strictFail the run on any cleanup audit warning
--with-buildRun a full vite build (default is typecheck only)
--help, -hShow help

The seven phases

Pulled from scripts/migrate.ts:

1. Analyze   — scan source, detect Preact/Fresh/Deco patterns
2. Scaffold  — generate vite.config.ts, wrangler.jsonc, routes, setup.ts, worker-entry
3. Transform — rewrite imports (70+ rules), JSX attrs, Fresh APIs, Deno-isms, Tailwind v3→v4
4. Cleanup   — delete islands/, old routes, deno.json, move static/ → public/
5. Report    — generate MIGRATION_REPORT.md with manual review items
6. Verify    — 18+ smoke tests (zero old imports, scaffolded files exist)
7. Bootstrap — Bun install, generate CMS blocks, generate routes

After phase 7, the script optionally:

  • Compiles (--no-compile to skip): runs tsc --noEmit and (with --with-build) vite build. Compile failures are reported but don't fail the migration unless --strict.
  • Cleanup audit (--no-cleanup-audit to skip): a read-only audit of leftover Fresh patterns. Surfaces things like leftover compat/ folders or stray useScript(fn) calls.

Layout detection

Phase 0 accepts classic Fresh projects with sections/, islands/, and related directories at the repository root, and modern projects with those directories under src/. Both layouts are scanned natively.

A mixed layout (both populated root and src/ directories) or an empty layout aborts before migration writes begin. Check the source path or restore a clean source checkout rather than rearranging a supported src/ layout. A dry run uses the same preflight.

What MIGRATION_REPORT.md contains

After a real run, the report has:

  • Run mode (DRY_RUN or EXECUTED) and timestamp.
  • File counts — scaffolded, transformed, deleted.
  • Full file lists for each category.
  • Loader inventory — every loaders/*.ts and actions/*.ts found, with port status.
  • Tailwind v3 → v4 pitfalls — negative z-index, opacity migrations, @apply rewrites.
  • @decocms/blocks boilerplate duplication — places where the migrated code overlaps with framework-provided helpers (candidates for cleanup).
  • Concrete next steps — exact commands to run.

The report is written at the site root. Review it and commit it with the migration so reviewers can inspect what changed.

Configuration file

You can pin script behavior via .deco-migrate.config.json at your project root:

{
  "sectionConventions": {
    "extend": {
      "eagerSync": ["Header"],
      "sync": ["Hero"],
      "listingCache": ["ProductShelf"],
      "staticCache": ["Footer"]
    }
  }
}

extend adds section file names to the defaults; replace uses only your lists. This file does not implement exclude, skipPhases, or verbose; use the documented CLI flags and review the migration diff. See section conventions.

Companion scripts

deco-post-cleanup

Run after the migration to clean up leftover boilerplate the framework has since absorbed:

npx -p @decocms/blocks-cli deco-post-cleanup

This is read + write — review the diff before committing.

deco-htmx-analyze

Specifically for sites that used HTMX during the v1 era. Reports HTMX usage so you can plan the conversion to React patterns. HTMX is not shipped in @decocms/blocks — sites that depended on it need to rewrite to React.

npx -p @decocms/blocks-cli deco-htmx-analyze

What the script doesn't do

  • Doesn't migrate useCart / useUser / useWishlist overrides. If your v1 site monkey-patched these, you'll need to port the overrides manually using the v2 hook factories. See VTEX hooks.
  • Doesn't migrate custom worker logic. Custom proxies, A/B harnesses, edge transforms — the script generates a vanilla worker-entry.ts and leaves you to layer custom logic on top using createDecoWorkerEntry.
  • Doesn't fix runtime correctness. A successful migration produces compiling code; runtime issues (cart not loading, PDP showing wrong product, hydration mismatches) need human attention.
  • Doesn't translate non-storefront sites. The script is tuned for the deco.cx storefront archetype. Marketing sites with very custom Fresh setups should expect more manual work.

Troubleshooting

"Layout not classic — aborting"

The current migrator accepts root and src/ layouts. For mixed or empty input, verify --source and restore a complete source checkout; read the specific CLI diagnostic before changing directories.

tsc --noEmit fails after migration

Read MIGRATION_REPORT.md. Common culprits:

  • A platform hook (useCart, etc.) that needs site-specific implementation.
  • A useScript(fn) that the script transformed but the calling code doesn't accept.
  • A custom matcher or loader that uses Deno-only APIs.

vite build fails

Run with --with-build to surface this during migration. Then read the error — most are missing imports caused by an island that was deleted but still referenced.

Production deploy works but admin preview is broken

You probably moved admin handlers into the TanStack server entry instead of the worker entry. See Worker entry reference.

See also