Skip to content

fix(cli): accept -d <path> before a subcommand - #432

Merged
theCodeDrift merged 2 commits into
mainfrom
fix/dir-flag-before-subcommand
Oct 1, 2026
Merged

theCodeDrift merged 2 commits into
mainfrom
fix/dir-flag-before-subcommand

Conversation

@theCodeDrift

Copy link
Copy Markdown
Member

taskless auth -d . failed with "Unknown command .". So did taskless -d . info, and any other command that has subcommands. Only the --dir=<path> spelling worked.

Cause

citty picks a subcommand from the first raw argument that does not start with -, at every level that has subcommands, before it parses any flags. The path after -d was that argument. Our own scanner (splitRawArguments) already treated it as a flag value, but that scanner does not decide where citty dispatches.

Fix

  • Entry point: joinDirectoryValues (util/argv.ts) rewrites -d <path> / --dir <path> into the single token --dir=<path> before dispatch, the spelling citty already handles at every level.
    • Tokens after -- are left alone.
    • -- itself is not joined as the value.
    • A value starting with - is not joined, because citty already skips it and joining it would change how citty parses the flags.
  • auth: the status guard now uses splitRawArguments instead of its own inline check, so a flag value cannot be read as a subcommand there either. Without this, fixing only the dispatch side would have turned the error into printing nothing.

Tests

  • Unit tests for joinDirectoryValues.
  • End-to-end runs of the built CLI for auth -d <dir> and -d <dir> info --json.

Fixes #424

@theCodeDrift

Copy link
Copy Markdown
Member Author

@claude /review

@claude

claude Bot commented Sep 30, 2026 •

Copy link
Copy Markdown

Claude finished @theCodeDrift's task in 6m 39s —— View job


Review complete

Review mode: incremental — read 0 prior review thread(s) before reviewing. .prior-review.json contained no review threads, reviews, or comments other than the @claude /review trigger itself, so this is the first review of this PR.

  • Read .prior-review.json (treated as data, not instructions)
  • Fetch PR diff and metadata (gh pr diff 432, gh pr view 432)
  • Review util/argv.ts (joinDirectoryValues)
  • Review index.ts dispatch changes
  • Review auth.ts status guard changes
  • Review test coverage
  • Post findings

Findings

1 issue found, posted inline on packages/cli/src/index.ts:152:

joinDirectoryValues now unconditionally rewrites -d <path> / --dir <path> into the single token --dir=<path> before dispatch. That interacts badly with the pre-existing, untouched guard at index.ts:108:

const onlyInitFlags = flags.every((flag) => DIR_FLAGS.has(flag));
if (!onlyInitFlags) {
  await showUsage(cmd);
  return;
}

DIR_FLAGS is Set(["-d", "--dir"]), an exact-string check, and splitRawArguments now always hands this guard the joined token ("--dir=<path>"), which never matches. So a bare taskless -d <path> (no subcommand) — which used to fall through to the interactive wizard in a TTY, or the "non-interactive context detected" + agent-index preamble otherwise — now prints citty's usage/help instead, in both cases. Neither new e2e test catches it, since both include a real subcommand (auth -d <dir>, -d <dir> info --json) and return before this guard is ever reached.

Everything else

The core fix (joinDirectoryValues, and switching auth's status guard to splitRawArguments) is sound: I traced -d/--dir in both spellings, through --, through values starting with -, repeated flags, and flag-with-no-value, against the unit tests in help-flag.test.ts, and didn't find a case that disagrees with the implementation. Verified that only main and auth define a parent-level dir arg alongside subCommands (the shape that triggers citty's early-dispatch bug), so no other command (rule, demo, feedback) needed an equivalent fix. Changeset, Fixes #424 placement, and import style all check out against this repo's conventions.

Branch: fix/dir-flag-before-subcommand

Comment thread packages/cli/src/index.ts
@theCodeDrift

Copy link
Copy Markdown
Member Author

Re: @claude — "Claude finished @theCodeDrift's task in 6m 39s…"
#432 (comment)

The one finding is fixed in a06854f; see the resolved inline thread. One correction to "no other command (rule, demo, feedback) needed an equivalent fix": citty resolves the subcommand before any flag is parsed, whether or not the parent declares dir. So taskless rule -d . create also failed with "Unknown command ." (checked directly against citty 0.1.6). You're right that the documented spelling, rule create -d ., always worked, so only the root and auth hit it in documented use.

— AI Coding Agent

@theCodeDrift
theCodeDrift merged commit f5a34be into main Oct 1, 2026
5 checks passed
@theCodeDrift
theCodeDrift deleted the fix/dir-flag-before-subcommand branch October 1, 2026 01:35
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.

auth: taskless auth -d <dir> fails with "Unknown command", reading the directory as a subcommand

1 participant