Add emdash migrate command - #2438
Conversation
Deploying with
|
| Status | Name | Latest Commit | Updated (UTC) |
|---|---|---|---|
| ✅ Deployment successful! View logs |
emdash-demo-do | 05bc7da | Aug 18 2026, 02:35 PM |
Deploying with
|
| Status | Name | Latest Commit | Updated (UTC) |
|---|---|---|---|
| 🔵 In progress View logs |
emdash-playground | ea0bb74 | Aug 13 2026, 09:00 AM |
Deploying with
|
| Status | Name | Latest Commit | Updated (UTC) |
|---|---|---|---|
| ✅ Deployment successful! View logs |
docs | 05bc7da | Aug 18 2026, 02:36 PM |
Deploying with
|
| Status | Name | Latest Commit | Updated (UTC) |
|---|---|---|---|
| ✅ Deployment successful! View logs |
emdash-demo-cache | 05bc7da | Aug 18 2026, 02:32 PM |
🦋 Changeset detectedLatest commit: 05bc7da The changes in this PR will be included in the next version bump. This PR includes changesets to release 17 packages
Not sure what this means? Click here to learn what changesets are. Click here if you're a maintainer who wants to add another changeset to this PR |
Scope checkThis PR changes 1,235 lines across 5 files. Large PRs are harder to review and more likely to be closed without review. If this scope is intentional, no action needed. A maintainer will review it. If not, please consider splitting this into smaller PRs. See CONTRIBUTING.md for contribution guidelines. |
There was a problem hiding this comment.
Pull request overview
Adds a new deployment-oriented emdash migrate CLI subcommand to explicitly check/status/apply core migrations recorded at build time, aligning with the goal of avoiding runtime auto-migrations in production-like environments.
Changes:
- Introduces
emdash migratewith manifest/config loading, target display + fingerprint confirmation, JSON/human reporting, and bounded cleanup on signals. - Adds unit + integration coverage for CLI behavior and SQLite execution (including idempotency and signal cleanup).
- Registers the new subcommand in the CLI entrypoint and adds a minor-version changeset.
Reviewed changes
Copilot reviewed 5 out of 5 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
| packages/core/src/cli/commands/migrate.ts | Implements the migrate command (options validation, manifest loading, executor wiring, reporting, confirmation, signal handling, redaction). |
| packages/core/src/cli/index.ts | Wires migrate into the top-level CLI command map. |
| packages/core/tests/unit/cli/migrate.test.ts | Unit coverage for command flow, option conflicts, confirmation gating, JSON output stability, and redaction/cleanup behaviors. |
| packages/core/tests/integration/cli/migrate-sqlite.test.ts | Integration coverage against the built CLI for SQLite apply/check idempotency and real SIGTERM cleanup behavior. |
| .changeset/add-deployment-migrate-cli.md | Announces the new emdash migrate command as a minor release. |
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
There was a problem hiding this comment.
The approach is sound: this adds the deployment-side emdash migrate command on top of the migration identity/manifest/executor protocol already landed in the base branch, and it links to the approved design discussion (#2418). The implementation is dependency-injected for testing, handles interactive vs non-interactive apply, redacts secrets from executor errors, and includes both unit and SQLite integration coverage. Code is generally clean against AGENTS.md conventions (proper changeset, no SQL interpolation, no admin UI/i18n concerns, sensible CLI patterns).
There is one real logic bug: the isRecord helper currently accepts arrays, so if a migration executor returns an array instead of a MigrationReport object, safeReport treats it as a valid record with all-undefined fields and reports an empty success. For emdash migrate --check this would incorrectly exit 0 and hide pending/unknown migrations. The fix is to make isRecord reject arrays, and a regression test for non-object reports should be added.
a305b32 to
124025b
Compare
@emdash-cms/admin
@emdash-cms/auth
@emdash-cms/auth-atproto
@emdash-cms/blocks
@emdash-cms/cloudflare
@emdash-cms/contentful-to-portable-text
emdash
create-emdash
@emdash-cms/gutenberg-to-portable-text
@emdash-cms/plugin-cli
@emdash-cms/plugin-types
@emdash-cms/registry-client
@emdash-cms/registry-lexicons
@emdash-cms/registry-verification
@emdash-cms/sandbox-workerd
@emdash-cms/x402
@emdash-cms/plugin-ai-moderation
@emdash-cms/plugin-atproto
@emdash-cms/plugin-audit-log
@emdash-cms/plugin-color
@emdash-cms/plugin-embeds
@emdash-cms/plugin-field-kit
@emdash-cms/plugin-forms
@emdash-cms/plugin-webhook-notifier
commit: |
124025b to
2334fc5
Compare
There was a problem hiding this comment.
This re-review looks good overall. The approach is sound: emdash migrate plugs cleanly into the existing migration identity / manifest / executor protocol from the base branch and links to the approved design discussion (#2418). The only prior finding — isRecord accepting arrays, which let an executor array report slip through safeReport and hide pending/unknown migrations on --check — is fixed, and a regression test for array-shaped reports was added.
I re-read packages/core/src/cli/commands/migrate.ts, the CLI wiring in packages/core/src/cli/index.ts, the new unit coverage, and the SQLite integration test. The fix is correct (!Array.isArray(value)), tests fail on arrays, secret redaction is preserved, signal cleanup is bounded, and the changeset is present and well-written.
One small non-blocking note: the header comment in packages/core/src/cli/index.ts that inventories CLI commands no longer matches the actual subCommands map now that migrate has been added.
There was a problem hiding this comment.
Re-review of #2438 confirms the prior finding is fixed and the non-blocking note is addressed.
- Prior
isRecordbug: Fixed.isRecordnow rejects arrays (!Array.isArray(value)), so an executor array-shaped report cannot slip throughsafeReportand hide pending/unknown migrations on--check. - Outdated header comment: Removed entirely from
packages/core/src/cli/index.ts, which is consistent with the comment-discipline guidance (no command inventories in comments).
I re-read packages/core/src/cli/commands/migrate.ts, the CLI wiring, the unit tests, and the SQLite integration test. The approach remains sound: emdash migrate plugs cleanly into the existing migration identity / manifest / executor protocol, supports manifest/config resolution, target selection, interactive and non-interactive modes, JSON output, secret redaction, bounded signal cleanup, and stable check/apply/status semantics. The new tests cover array-shaped reports, target mismatch, secret redaction, signal cleanup, idempotent apply, and option validation.
I found no new issues against AGENTS.md conventions (imports, SQL safety, API envelope shape, localization/RTL, locale filtering, index discipline, comment discipline, changesets) and no logic regressions. The changeset is present and well-written.
LGTM.
8b9e1f5 to
d229512
Compare
There was a problem hiding this comment.
Re-review of #2438 after the prior approved pass. I re-read the full diff and the changed files, traced the migration CLI against the existing migration identity/manifest/executor protocol, and checked the new unit and SQLite integration tests against AGENTS.md conventions.
- Approach: the change is the right follow-up to the migration-core work (#2276).
emdash migratewires cleanly into the existing manifest/config-loader/protocol layer, supports the requested discovery modes (manifest default,--manifest,--from-config), target overrides, interactive and non-interactive apply, JSON output, and bounded signal cleanup. The linked approved Discussion (#2418) is present, and the changeset is user-facing and concise. - Prior
isRecordissue: still fixed —isRecordrejects arrays, so an array-shaped executor report cannot masquerade as a valid report insafeReport. - Comment discipline: the command inventory header was removed from
packages/core/src/cli/index.ts; the newmigrate.tshas no narrative/justification comments. - Conventions: imports use
.jsextensions, type-only imports are separate, SQL is not touched by the CLI, no user-visible admin UI strings are introduced, and no content-table/locale queries are involved. - Tests cover array-shaped reports, target mismatch, secret redaction, signal cleanup, idempotent apply, option validation, D1 warnings, and the real built CLI against SQLite.
I found no new logic bugs, regressions, or AGENTS.md violations in the current head. LGTM.
d229512 to
d3a185a
Compare
There was a problem hiding this comment.
Re-review of #2438 after the prior approved pass. I re-read the full diff and the changed files, traced the new emdash migrate command against the existing migration identity/manifest/executor protocol, and checked the unit and SQLite integration tests against AGENTS.md conventions.
The current head remains clean:
- The approach is sound and follows the approved Discussion (#2418):
emdash migratewires into the existing manifest/config-loader/protocol layer, supports manifest/config discovery, target overrides, interactive and noninteractive apply, JSON output, stable exit codes, and bounded signal cleanup. - No AGENTS.md violations: internal imports use
.jsextensions, type-only imports are separate, the CLI does not touch SQL or content tables, there are no new user-visible admin UI strings, no logged-out route queries, no new indexes, and no narrative/justification comments. - The changeset is user-facing and concise.
- Tests cover array-shaped reports, target mismatch, secret redaction, signal cleanup, idempotent apply, option validation, D1 warnings, and the real built CLI against SQLite.
I found no new logic bugs, regressions, or convention violations. The prior approval stands. LGTM.
d3a185a to
8cda7b2
Compare
8cda7b2 to
05bc7da
Compare
What does this PR do?
Adds the
emdash migratedeployment command, including manifest/config resolution, target selection, confirmation and non-interactive modes, JSON output, error handling, and SQLite integration coverage.Part of #2276
Type of change
Checklist
pnpm typecheckpassespnpm lintpassespnpm testpasses (or targeted tests for my change)pnpm formathas been runmessages.pochanges except in translation PRs — a workflow extracts catalogs on merge tomain.Approved design discussion: #2418. Package typechecking, quick lint, and targeted formatting pass.
AI-generated code disclosure
Screenshots / test output
Non-visual change. The CLI unit suite and SQLite migration integration coverage pass.