Skip to content

fix(cli): reject extra positional arguments passed to add - #3891

Open
miga-heygen wants to merge 1 commit into
mainfrom
fix/add-command-extra-positional-args
Open

fix(cli): reject extra positional arguments passed to add#3891
miga-heygen wants to merge 1 commit into
mainfrom
fix/add-command-extra-positional-args

Conversation

@miga-heygen

Copy link
Copy Markdown
Contributor

Summary

add <a> <b> <c> installed only <a> and exited 0, with <b> and <c> silently dropped — no warning, no error. citty's positional-arg binding only assigns the first token to the declared name arg; every token after it still lands in args._, but nothing in add's run() read that array.

add installs exactly one item or tag per invocation today — a tag (e.g. add html-in-canvas) is the existing bulk-install path, expanding to every item with that tag. Passing several explicit item names has never been a supported way to bulk-install, so rather than inventing that as a new feature, this makes the existing single-item contract honest: extra positional arguments are now rejected up front, before any project-config write or registry request, naming exactly what was dropped.

Changes

  • packages/cli/src/commands/add.ts: run() now checks args._.slice(1) for leftover positional tokens and fails with a usage error via the existing failUsage() helper (same one other commands in this package already use for invalid invocations) instead of silently proceeding with just the first name. Added a small exported formatExtraPositionalsError() helper for the message, matching the existing remapTarget/buildSnippet pattern of pulling pure logic out for direct testing.
  • packages/cli/src/commands/add.test.ts: unit tests for the message formatter, plus end-to-end tests that invoke the command's run() wrapper directly (following the same pattern already used in auth/login.test.ts) — including one that runs the arguments through citty's own parseArgs with a flag interleaved between positionals (add a --dir <dir> b) to confirm the fix holds against real parsing, not just a hand-built args object.

Test plan

  • bunx vitest run packages/cli/src/commands/add.test.ts — 29/29 pass
  • Confirmed the new tests actually catch the bug: reverted the add.ts change and reran — the 4 new assertions failed exactly as expected against the old behavior
  • bunx tsc --noEmit -p packages/cli clean
  • bunx oxlint / bunx oxfmt --write clean
  • bunx fallow audit --base origin/main --fail-on-issues clean (0 issues, 2 changed files)
  • Verified against citty's actual source that it only binds the first positional to name while _ retains every token, including when flags are interleaved with positionals (e.g. add a --dir <dir> b)

`add <a> <b> <c>` silently installed only `<a>` and exited 0, discarding
`<b>` and `<c>` with no warning. citty binds only the first positional
token to `name`; every token after it still lands in `args._`, but
nothing read it. `add` now rejects the extra arguments up front, before
touching the registry, naming exactly what was dropped.

Co-Authored-By: Miguel Angel <miguel.sierra@heygen.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant