Skip to content

Operator CLI UX: FormRunner, huh pickers, Lipgloss chrome#73

Merged
maxBRT merged 3 commits into
mainfrom
ship/20260721-201914.210129954
Jul 22, 2026
Merged

Operator CLI UX: FormRunner, huh pickers, Lipgloss chrome#73
maxBRT merged 3 commits into
mainfrom
ship/20260721-201914.210129954

Conversation

@maxBRT

@maxBRT maxBRT commented Jul 21, 2026

Copy link
Copy Markdown
Owner

Summary

Lands the Charm/huh operator UX slice: a FormRunner seam with shared Lipgloss theme tokens, huh Agent picker on Init, huh Queue multi-select with Shift+↑/↓ reorder, styled ship --help, and Lipgloss Run chrome (header, denser Phase observe strip, louder Abort). Color/ANSI for Run chrome, throbber, and observe is gated on stderr being a TTY so redirected logs stay plain.

Linked issues

RISK

  • TTY / non-TTY mismatch (medium). Init and Queue confirmation now depend on huh detecting a real terminal. CI pipes, script, or weird PTYs can mis-detect and either skip the picker (ErrNonInteractive / default Agent) or hang waiting for input. Operators piping ship output or running under automation are most affected.
  • Queue order surprises (medium). Selected order is Run order; Shift+↑/↓ only reorders the focused selected row. Operators who expect list position (not selection order) to drive Iterations can process Tickets in the wrong sequence.
  • Cancel semantics (low–medium). Esc/cancel on Init must not write .ship/config.yaml; cancel on Queue confirmation must abort the Run before Claim. A regression would leave a half-written config or claim Tickets the operator never confirmed.
  • ANSI in help when redirected (low). WriteUsage / ship --help still emits Lipgloss color unconditionally; only Run chrome/observe/throbber are TTY-gated. Log scrapers or screenshots of --help may show escape codes.
  • Charm dependency surface (low). New direct deps (huh, lipgloss) can break builds if module resolve fails or Charm APIs change; limited to this CLI binary, not agent Phase adapters.

QA — stress-test plan for a human

1. Happy path

  1. In a clean checkout with gh auth and at least two GitHub issues labeled ship, run ship init on a real TTY: confirm the huh Agent single-select (blurbs + keyhints), pick an Agent kind, and verify .ship/config.yaml gets that agent:.
  2. Run ship (or ship --help then a full Run): confirm styled Usage/Flags/Config sections and aligned flag columns.
  3. On Queue confirmation, multi-select ≥2 Tickets, use Shift+↓ / Shift+↑ to reorder the focused selected row, confirm. Verify the Run processes Iterations in that selected order (Implement → Review per Ticket).
  4. Watch Run chrome: once-per-Run header with Agent kind + branch; throbber shows dim remaining-queue hint while Tickets remain; successful Phase lines get a compact tools/tokens strip; finish through Final / PR open if you have a short queue.

2. Edges / failure cases

  1. Non-TTY Init: ship init </dev/null (or pipe stdin closed) — should default Agent to cursor without a TUI and still write config (or fail cleanly per existing non-TTY Init rules); must not hang on huh.
  2. Non-TTY Queue: ship </dev/null with candidates present — expect ErrNonInteractive / no Claim; no hang.
  3. Cancel Init: open ship init, Esc/cancel before accept — no .ship/config.yaml write (or no overwrite of agent if you staged a dry run carefully).
  4. Cancel Queue: start ship, Esc on Queue confirmation — Run stops; Tickets must not be Claimed / moved to In Progress.
  5. Empty selection: try confirming Queue with zero Tickets selected — must refuse / stay in picker per form validation, not start an empty Run.
  6. Abort chrome: force a Phase failure (bad Agent binary or short --timeout) — stderr shows loud red Abort, report path under .ship/runs/…, last tools; redirected stderr (ship 2>run.log) should be plain text without ANSI.
  7. Reorder focus: with 3+ selected Tickets, move focus to an unselected row and hit Shift+↑/↓ — confirm only selected rows reorder and Run order matches selection order, not visual list index alone.

3. Out of scope

  • Agent adapter correctness inside Implement/Review/Final (cursor/pi/codex/claude prompts).
  • GitHub label ensure / Claim / Done / Abort tracker edge cases beyond “cancel did not Claim”.
  • install.sh / GoReleaser / update paths.
  • Replacing typed-line TypedLines FormRunner beyond the production huh path (tests may still stub it).

Made with Cursor

maxBRT and others added 3 commits July 21, 2026 17:25
Operators pick Agent kind on Init and confirm/reorder Tickets on Queue via keyboard-friendly forms; tests stub FormRunner without a live TUI.

Co-authored-by: Cursor <cursoragent@cursor.com>
Brand Usage/Flags/Config headings and render each flag as name, meaning, and default on one aligned row.

Co-authored-by: Cursor <cursoragent@cursor.com>
Print a once-per-Run agent/branch header, queue-remaining throbber hint, compact tools/in/out success dump, and louder Abort framing; gate color on stderr TTY and keep the two-line throbber from scrolling.

Co-authored-by: Cursor <cursoragent@cursor.com>
@maxBRT
maxBRT force-pushed the ship/20260721-201914.210129954 branch from d309037 to c21cf98 Compare July 21, 2026 21:25
@maxBRT
maxBRT merged commit e5f191f into main Jul 22, 2026
4 checks passed
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