Skip to content

refactor: improve z.enum support in CLI framework#1076

Merged
hsablonniere merged 6 commits intomasterfrom
improve-z-enum-support
Apr 2, 2026
Merged

refactor: improve z.enum support in CLI framework#1076
hsablonniere merged 6 commits intomasterfrom
improve-z-enum-support

Conversation

@hsablonniere
Copy link
Copy Markdown
Member

@hsablonniere hsablonniere commented Mar 18, 2026

Context

Enum values defined in z.enum() schemas were manually duplicated in descriptions across 7 files, creating maintenance burden and fragility. When adding a new enum value, every copy had to be updated or things would silently diverge.

Additionally, explicit autocomplete arrays and manual validation were duplicated for each enum, preventing a unified approach to displaying and validating enum choices.

Proposal

Add framework-level introspection for z.enum() schemas:

  1. getEnumValues(schema) — unwrap Zod wrappers (default, optional, nullable, pipe) and extract enum values
  2. Integrate into getCommandInfo() — add enumValues field to OptionInfo and ArgumentInfo
  3. Auto-display in help and docs — enum values appear after description in --help, LLM docs, and markdown reference
  4. Auto-complete — options and arguments with z.enum() get autocomplete for free via bin/clever.js
  5. Migrate drain create — use z.enum() instead of manual validation, leveraging the new framework

This replaces 7 manual enum value lists in descriptions with zero duplication, and provides better UX (help text, autocomplete) without extra code.

How to test

# Help text now shows enum values:
node bin/clever.js logs --help              # Format option shows (human, json, json-stream)
node bin/clever.js drain create --help     # drain-type shows all types
node bin/clever.js deploy --help           # exit-on and same-commit-policy show values

# Validation via Zod (not manual checks):
node bin/clever.js drain create invalid-type http://example.com
# Shows: Invalid option: expected one of "datadog"|"elasticsearch"|...

# Autocomplete works:
node bin/clever.js logs --format <TAB>     # completes with format values

@hsablonniere hsablonniere force-pushed the improve-z-enum-support branch 2 times, most recently from b4f431b to e561dbf Compare March 18, 2026 17:22
@github-actions
Copy link
Copy Markdown

github-actions bot commented Mar 18, 2026

🔎 The preview has been automatically deleted.

Several options and arguments use z.enum() schemas, but enum values are
manually duplicated in descriptions and autocomplete arrays. To enable
automatic extraction, a helper is needed that can unwrap Zod schema wrappers
(default, optional, nullable, pipe) and retrieve the underlying enum values
programmatically.
The command info model is the single source of truth consumed by help display,
docs generation, and autocomplete. Exposing enumValues here makes them
available to all consumers without each one needing to call getEnumValues()
directly on the Zod schema.
Help output, reference docs, and LLM docs each manually formatted enum
values differently. Now that enumValues is part of the command info model,
all three consumers can render them consistently and automatically from the
Zod schema definition.
Options and arguments using z.enum() had to manually specify a complete array
with the same values. By falling back to getEnumValues() when no explicit
complete is provided, autocomplete stays in sync with the schema automatically.
Enum values were listed both in the z.enum() schema and manually in description
strings. Now that help, docs, and autocomplete extract them from the schema,
keeping them in descriptions would result in duplication like "Output format
(human, json) (human, json)".
The drain-type argument was validated with a manual if-check and had a manually
specified complete array, both duplicating the list of valid types. Using
z.enum() instead lets Zod handle validation with a clear error message,
while help display and autocomplete are now derived automatically.
@hsablonniere hsablonniere force-pushed the improve-z-enum-support branch from e561dbf to fb1b8b7 Compare April 1, 2026 14:38
@hsablonniere hsablonniere marked this pull request as ready for review April 1, 2026 14:38
@hsablonniere hsablonniere requested a review from a team as a code owner April 1, 2026 14:38
Copy link
Copy Markdown
Contributor

@pdesoyres-cc pdesoyres-cc left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Perfect. Well done!

@hsablonniere hsablonniere merged commit 6a40a01 into master Apr 2, 2026
6 checks passed
@hsablonniere hsablonniere deleted the improve-z-enum-support branch April 2, 2026 14:40
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.

2 participants