refactor(cli): replace Zod with ArkType everywhere#2729
Conversation
Unify CLI schemas on ArkType (already used by the backend) and upgrade the MCP server to the v2 beta Standard Schema API so Zod can be dropped as a direct dependency. Co-authored-by: Cursor <cursoragent@cursor.com>
|
Note Reviews pausedIt looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the Use the following commands to manage reviews:
Use the checkboxes below for quick actions:
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: Organization UI Review profile: ASSERTIVE Plan: Pro Run ID: ⛔ Files ignored due to path filters (1)
📒 Files selected for processing (3)
🔗 Linked repositories identifiedCodeRabbit considers these linked repositories for cross-repo context during reviews:
📝 WalkthroughWalkthroughThe CLI migrates runtime schemas from Zod to ArkType, adds Standard Schema parsing helpers, and updates MCP tooling from ChangesArkType validation and domain schemas
MCP registration migration
Estimated code review effort: 4 (Complex) | ~60 minutes Possibly related PRs
Suggested labels: Suggested reviewers: 🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✨ Finishing Touches📝 Generate docstrings
Warning There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure. 🔧 Checkov (3.3.8)cli/package.jsonTraceback (most recent call last): package.jsonTraceback (most recent call last): Comment |
|
Review the following changes in direct dependencies. Learn more about Socket for GitHub.
|
Merging this PR will not alter performance
Comparing Footnotes
|
Update CLI MCP tests to @modelcontextprotocol/client, trim unused ark_validation/config exports so knip passes, and keep only live types. Co-authored-by: Cursor <cursoragent@cursor.com>
Bugbot couldn't run - usage limit reachedBugbot is counted against Cursor usage for this user or team, and this run hit a usage or spend limit. A user or team admin can review and increase usage limits in the Cursor dashboard. (requestId: serverGenReqId_a6e7ac46-eabe-4b7e-a636-9ad616e28162) |
There was a problem hiding this comment.
Stale comment
Risk: medium. Cursor Bugbot did not complete (check skipped — usage limit reached), and this broad CLI Zod→ArkType validation refactor exceeds the low-risk approval threshold. Not approving; WcaleNieWolny is already assigned for human review.
Sent by Cursor Approval Agent: Pull Request Approver External
|
@coderabbitai review |
✅ Action performedReview finished.
|
There was a problem hiding this comment.
All reported issues were addressed across 36 files
Confidence score: 5/5
- Safe to merge after the addressed issues were fixed.
Tip: instead of fixing issues one by one fix them all with cubic
Tip: cubic can generate docs of your entire codebase and keep them up to date. Try it here.
Re-trigger cubic
Register prompts via registerPrompt, strip undeclared keys with ArkType '+': 'delete', allow optional undefined, and add toJsonSchema fallback so tools/list works with MCP Standard Schema export. Co-authored-by: Cursor <cursoragent@cursor.com>
Bugbot couldn't run - usage limit reachedBugbot is counted against Cursor usage for this user or team, and this run hit a usage or spend limit. A user or team admin can review and increase usage limits in the Cursor dashboard. (requestId: serverGenReqId_31dd2a26-e4dd-4547-9214-aa62791e4ecd) |
There was a problem hiding this comment.
Stale comment
Risk: medium. Cursor Bugbot did not complete (check skipped — usage limit reached), and this broad CLI Zod→ArkType validation refactor exceeds the low-risk approval threshold. Not approving; WcaleNieWolny is already assigned for human review.
Sent by Cursor Approval Agent: Pull Request Approver External
There was a problem hiding this comment.
Actionable comments posted: 3
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (1)
cli/src/mcp/server.ts (1)
429-478: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick winDocument why
capgo_update_channeluses two schemas.The advertised
inputSchema(mcpUpdateChannelInputSchema) omits the mutual-exclusivity checks thatupdateChannelOptionsSchema.narrow(...)enforces (e.g.rolloutEnable/rolloutDisable, therolloutPause/rolloutResume/rolloutRollback/rolloutPromotegroup,autoPauseEnabled/autoPauseDisabled), which is whyparseSchema(updateChannelOptionsSchema, ...)re-validates inside the handler. This split is very likely required because ArkType.narrow()predicates aren't convertible to JSON Schema, soupdateChannelOptionsSchemaitself can't be used as the wire-facinginputSchema. Worth a short comment here (or at the two schema definitions) explaining that rationale, since it's easy for a future reader to "simplify" by collapsing the two schemas and unknowingly break tool registration or silently drop the narrow constraints.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@cli/src/mcp/server.ts` around lines 429 - 478, Document the intentional two-schema flow in capgo_update_channel: add a brief comment explaining that mcpUpdateChannelInputSchema is used for wire-facing tool registration because ArkType narrow predicates cannot be converted to JSON Schema, while parseSchema(updateChannelOptionsSchema, ...) revalidates the mutual-exclusivity constraints inside the handler. Keep both schemas and the existing validation behavior unchanged.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@cli/src/mcp/tool-schemas.ts`:
- Around line 4-8: Update the bare fields in mcpAddAppInputSchema,
mcpUpdateAppInputSchema, mcpUploadBundleInputSchema,
mcpCleanupBundlesInputSchema, mcpGetStatsInputSchema,
mcpRequestBuildInputSchema, and the applicable fields of
mcpUpdateChannelInputSchema to use ArkType .describe() metadata, matching the
descriptive style of the already-documented schemas in this file. Add clear
descriptions for fields including rollout, force, nodeModules, and all
rollout/auto-pause flags without changing validation behavior.
In `@cli/src/schemas/validate.ts`:
- Around line 15-16: Factor out a shared Standard Schema path formatter that
converts `{ key }` segments to their keys, joins segments with dots, and returns
“value” for empty paths. Replace the direct path joining in
cli/src/schemas/validate.ts:15-16 and cli/src/utils.ts:2088-2090 with this
formatter; both sites require the change.
In `@cli/test/test-mcp-live-update-onboarding.mjs`:
- Around line 156-162: Update the schema validation assertions in the onboarding
test to parse the `inputSchema` captured from each registered tool in
`server.tools`, rather than the imported schema constants. Apply this to the
affected assertions around `capgo_live_update_onboarding_explain` and the
additional locations noted by the review, preserving the existing valid and
invalid fixture expectations.
---
Outside diff comments:
In `@cli/src/mcp/server.ts`:
- Around line 429-478: Document the intentional two-schema flow in
capgo_update_channel: add a brief comment explaining that
mcpUpdateChannelInputSchema is used for wire-facing tool registration because
ArkType narrow predicates cannot be converted to JSON Schema, while
parseSchema(updateChannelOptionsSchema, ...) revalidates the mutual-exclusivity
constraints inside the handler. Keep both schemas and the existing validation
behavior unchanged.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: ASSERTIVE
Plan: Pro
Run ID: f709bddf-7d74-43a4-a0b7-e9d2d4503270
⛔ Files ignored due to path filters (1)
bun.lockis excluded by!**/*.lock
📒 Files selected for processing (35)
cli/package.jsoncli/src/build/onboarding/mcp/build-tool-schemas.tscli/src/build/onboarding/mcp/build-tools.tscli/src/build/onboarding/mcp/credentials-manage.tscli/src/build/onboarding/mcp/onboarding-tools.tscli/src/init/mcp/live-update-tools.tscli/src/mcp/registrar.tscli/src/mcp/server.tscli/src/mcp/tool-schemas.tscli/src/schemas/app.tscli/src/schemas/ark_validation.tscli/src/schemas/auth.tscli/src/schemas/base.tscli/src/schemas/build.tscli/src/schemas/bundle.tscli/src/schemas/channel.tscli/src/schemas/common.tscli/src/schemas/config.tscli/src/schemas/index.tscli/src/schemas/live-update-onboarding.tscli/src/schemas/onboarding.tscli/src/schemas/organization.tscli/src/schemas/sdk.tscli/src/schemas/validate.tscli/src/utils.tscli/test/test-capacitor-config-target.mjscli/test/test-mcp-build-tools.mjscli/test/test-mcp-credentials-manage.mjscli/test/test-mcp-live-update-onboarding.mjscli/test/test-mcp-oauth-reopen.mjscli/test/test-mcp-onboarding.mjscli/test/test-mcp.mjscli/test/test-upload-validation.mjspackage.jsontests/organization-api.test.ts
🔗 Linked repositories identified
CodeRabbit considers these linked repositories for cross-repo context during reviews:
Cap-go/capacitor-updater(manual)
💤 Files with no reviewable changes (1)
- cli/src/schemas/index.ts
There was a problem hiding this comment.
Actionable comments posted: 1
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (2)
cli/src/mcp/tool-schemas.ts (1)
4-167: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick winFactor out shared MCP schema fragments.
These MCP inputs are intentional subsets of the SDK options, but the shared bounds and field shapes still live in two places. Reuse common fragments fromcli/src/schemas/sdk.tswhere possible to keep MCP and SDK validation from drifting.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@cli/src/mcp/tool-schemas.ts` around lines 4 - 167, Refactor the MCP schemas in the exported mcp*InputSchema definitions to reuse applicable shared field fragments and bounds from cli/src/schemas/sdk.ts instead of duplicating them locally. Prioritize overlapping options such as rollout, retention, auto-pause, and Capacitor configuration while preserving each MCP schema’s intentional subset and existing validation behavior.Source: Coding guidelines
cli/src/schemas/channel.ts (1)
9-26: 🗄️ Data Integrity & Integration | 🟠 Major | 🏗️ Heavy liftDo not narrow the public
versionfield without a compatibility plan.The schema now accepts only an optional object-shaped
version, whereas the previous contract accepted any optional value. Existing API responses containing a scalar, array,null, or another valid legacy format will now fail parsing. Preserve the broad field shape, or gate the stricter object form by API/plugin version and add regression coverage.As per coding guidelines, public APIs and plugin interfaces must remain backward compatible; do not change existing fields, meanings, formats, or status codes.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@cli/src/schemas/channel.ts` around lines 9 - 26, Update the version field in channelSchema to preserve the previous broad optional-value contract instead of requiring an object shape. Keep Channel inference compatible with scalar, array, null, and other legacy version values, and do not narrow the public API field without version gating.Source: Coding guidelines
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@cli/src/schemas/arktype_config.ts`:
- Around line 5-10: Update the ArkType JSON Schema configuration in configure so
fallback.default only returns ctx.base for unsupported optional-undefined cases;
make all other unsupported nodes throw or otherwise fail explicitly. Preserve
narrow constraints used by the channel and SDK schemas instead of silently
dropping them.
---
Outside diff comments:
In `@cli/src/mcp/tool-schemas.ts`:
- Around line 4-167: Refactor the MCP schemas in the exported mcp*InputSchema
definitions to reuse applicable shared field fragments and bounds from
cli/src/schemas/sdk.ts instead of duplicating them locally. Prioritize
overlapping options such as rollout, retention, auto-pause, and Capacitor
configuration while preserving each MCP schema’s intentional subset and existing
validation behavior.
In `@cli/src/schemas/channel.ts`:
- Around line 9-26: Update the version field in channelSchema to preserve the
previous broad optional-value contract instead of requiring an object shape.
Keep Channel inference compatible with scalar, array, null, and other legacy
version values, and do not narrow the public API field without version gating.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: ASSERTIVE
Plan: Pro
Run ID: d1d70b95-8b10-43f1-8979-742470c8c909
📒 Files selected for processing (21)
cli/src/build/onboarding/mcp/build-tool-schemas.tscli/src/build/onboarding/mcp/onboarding-tools.tscli/src/init/mcp/live-update-tools.tscli/src/mcp/registrar.tscli/src/mcp/tool-schemas.tscli/src/schemas/app.tscli/src/schemas/ark_validation.tscli/src/schemas/arktype.tscli/src/schemas/arktype_config.tscli/src/schemas/auth.tscli/src/schemas/base.tscli/src/schemas/build.tscli/src/schemas/bundle.tscli/src/schemas/channel.tscli/src/schemas/common.tscli/src/schemas/live-update-onboarding.tscli/src/schemas/onboarding.tscli/src/schemas/organization.tscli/src/schemas/sdk.tscli/test/test-mcp-live-update-onboarding.mjscli/test/test-mcp-onboarding.mjs
🔗 Linked repositories identified
CodeRabbit considers these linked repositories for cross-repo context during reviews:
Cap-go/capacitor-updater(manual)
There was a problem hiding this comment.
All reported issues were addressed across 21 files (changes from recent commits).
Reply with feedback, questions, or to request a fix.
Fix all with cubic | Re-trigger cubic
|
@coderabbitai review |
✅ Action performedReview finished.
|
|
@coderabbitai review |
✅ Action performedReview finished.
|
Use a unit-only toJsonSchema fallback for optional undefined, prefer ArkType problem text in validateOptions, and trim/reject blank locale keys for localized store release notes. Co-authored-by: Cursor <cursoragent@cursor.com>
Bugbot couldn't run - usage limit reachedBugbot is counted against Cursor usage for this user or team, and this run hit a usage or spend limit. A user or team admin can review and increase usage limits in the Cursor dashboard. (requestId: serverGenReqId_84373d7d-6558-4ff3-9565-f5f8157fa6a6) |
There was a problem hiding this comment.
Stale comment
Risk: medium. Cursor Bugbot did not complete (check skipped — usage limit reached), and this broad CLI Zod→ArkType validation refactor exceeds the low-risk approval threshold. Not approving; WcaleNieWolny is already assigned for human review.
Sent by Cursor Approval Agent: Pull Request Approver External
There was a problem hiding this comment.
Actionable comments posted: 1
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@cli/src/schemas/build.ts`:
- Around line 4-18: Reject duplicate locale keys after trimming in the localized
release-notes validation: in cli/src/schemas/build.ts lines 4-18, check
Object.hasOwn(out, key) before assigning out[key] and reject duplicates; apply
the same validation in cli/src/schemas/sdk.ts lines 21-35. Preserve the existing
non-empty key and value checks.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: ASSERTIVE
Plan: Pro
Run ID: b681ee39-87b9-4536-b8df-8b4f06d30a62
📒 Files selected for processing (4)
cli/src/schemas/arktype_config.tscli/src/schemas/build.tscli/src/schemas/sdk.tscli/src/schemas/validate.ts
🔗 Linked repositories identified
CodeRabbit considers these linked repositories for cross-repo context during reviews:
Cap-go/capacitor-updater(manual)
There was a problem hiding this comment.
All reported issues were addressed across 4 files (changes from recent commits).
Tip: instead of fixing issues one by one fix them all with cubic
Tip: Review your code locally with the cubic CLI to iterate faster.
Re-trigger cubic
Share one null-prototype locale-notes schema that rejects blank/duplicate keys, keep paths on ArkType problems, and throw a typed error for unsupported JSON Schema units. Co-authored-by: Cursor <cursoragent@cursor.com>
Bugbot couldn't run - usage limit reachedBugbot is counted against Cursor usage for this user or team, and this run hit a usage or spend limit. A user or team admin can review and increase usage limits in the Cursor dashboard. (requestId: serverGenReqId_fbecb14f-2333-46ba-9558-d58f52d66417) |
There was a problem hiding this comment.
Stale comment
Risk: medium. Cursor Bugbot did not complete (check skipped — usage limit reached), and this broad CLI Zod→ArkType validation refactor exceeds the low-risk approval threshold. Not approving; WcaleNieWolny is already assigned for human review.
Sent by Cursor Approval Agent: Pull Request Approver External
There was a problem hiding this comment.
All reported issues were addressed across 6 files (changes from recent commits).
Tip: Review your code locally with the cubic CLI to iterate faster.
Fix all with cubic | Re-trigger cubic
Require a plain object for localized release notes, and always prefix ArkType problems with the issue path in validateOptions. Co-authored-by: Cursor <cursoragent@cursor.com>
Bugbot couldn't run - usage limit reachedBugbot is counted against Cursor usage for this user or team, and this run hit a usage or spend limit. A user or team admin can review and increase usage limits in the Cursor dashboard. (requestId: serverGenReqId_58c80f81-61b7-4e1c-8d26-1b0ee3a35d9e) |
There was a problem hiding this comment.
Stale comment
Risk: medium. Cursor Bugbot did not complete (check skipped — usage limit reached), and this broad CLI Zod→ArkType validation refactor exceeds the low-risk approval threshold. Not approving; WcaleNieWolny is already assigned for human review.
Sent by Cursor Approval Agent: Pull Request Approver External
There was a problem hiding this comment.
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (1)
cli/src/schemas/index.ts (1)
68-69: 🗄️ Data Integrity & Integration | 🟠 Major | ⚡ Quick winRestore the removed config-schema exports.
Removing
capacitorConfigSchemaandextConfigPairsSchemabreaks existing imports from this public barrel. Re-export both schemas alongside their types.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@cli/src/schemas/index.ts` around lines 68 - 69, Update the Config exports in the public schema barrel to re-export capacitorConfigSchema and extConfigPairsSchema alongside CapacitorConfig and ExtConfigPairs, preserving existing imports.Source: Coding guidelines
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Outside diff comments:
In `@cli/src/schemas/index.ts`:
- Around line 68-69: Update the Config exports in the public schema barrel to
re-export capacitorConfigSchema and extConfigPairsSchema alongside
CapacitorConfig and ExtConfigPairs, preserving existing imports.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: ASSERTIVE
Plan: Pro
Run ID: 8cea7b03-7b48-4ae2-8345-0abd4c1385ce
📒 Files selected for processing (6)
cli/src/schemas/arktype_config.tscli/src/schemas/build.tscli/src/schemas/common.tscli/src/schemas/index.tscli/src/schemas/sdk.tscli/src/schemas/validate.ts
🔗 Linked repositories identified
CodeRabbit considers these linked repositories for cross-repo context during reviews:
Cap-go/capacitor-updater(manual)
Resolve cli/package.json and bun.lock conflicts while keeping ArkType + MCP v2 and main dependency bumps. Co-authored-by: Cursor <cursoragent@cursor.com>
Bugbot couldn't run - usage limit reachedBugbot is counted against Cursor usage for this user or team, and this run hit a usage or spend limit. A user or team admin can review and increase usage limits in the Cursor dashboard. (requestId: serverGenReqId_b0dcbd3f-cb91-4aaf-bb39-477efaaf48f5) |
There was a problem hiding this comment.
Risk: medium. Cursor Bugbot did not complete (check skipped — usage limit reached), and this broad CLI Zod→ArkType validation refactor exceeds the low-risk approval threshold. Not approving; WcaleNieWolny is already assigned for human review.
Sent by Cursor Approval Agent: Pull Request Approver External
|





Summary (AI generated)
cli/src/schemas/to ArkType, matching the backend validation stack@modelcontextprotocol/sdkv1 to@modelcontextprotocol/serverv2 beta so tools can register ArkType/Standard SchemainputSchemadirectlyzoddependencies from root and CLIpackage.json(Zod may still appear transitively via MCP/knip)Motivation (AI generated)
Backend validation already standardized on ArkType + Standard Schema. Keeping Zod only in the CLI duplicated dependencies and patterns. MCP SDK v2 accepts ArkType natively, so we can drop Zod from our direct dependency tree.
Business Impact (AI generated)
Smaller/simpler CLI dependency surface and one validation library across Capgo backend + CLI. MCP tool schemas stay LLM-friendly via ArkType
.describe()metadata. Note: MCP server package is currently on a beta release.Test Plan (AI generated)
bun run cli:lintbun run cli:typecheckbun run cli:buildtest-upload-validation,test-mcp-live-update-onboarding,test-mcp-onboarding,test-mcp-build-tools,test-mcp-credentials-manage,test-mcp-oauth-reopen,test:mcp)Generated with AI
Made with Cursor
Summary by CodeRabbit