[object Object]

← back to Cli Printing Press

feat(skills): extract polish protocol into polish-worker agent

af759a2730bc44722497656f67b7eac96a75f838 · 2026-04-04 15:42:38 -0700 · Trevin Chow

Move the fix protocol (diagnostics → fix priorities → rediagnose →
report delta) into agents/polish-worker.md. Both entry points now
dispatch the same agent:

- Main skill Phase 5.5: dispatches agent directly (foreground, no UX)
- Standalone /printing-press-polish: resolves CLI, checks lock,
  dispatches agent, then offers publish

The standalone skill shrinks from 338 to 180 lines — it's now a thin
UX wrapper around the agent. The fix protocol lives in one place.

The agent returns a structured ---POLISH-RESULT--- block with
scorecard/verify before/after, fixes applied, and ship recommendation.
The caller parses it for control flow (promote vs hold).

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

Files touched

Diff

commit af759a2730bc44722497656f67b7eac96a75f838
Author: Trevin Chow <trevin@trevinchow.com>
Date:   Sat Apr 4 15:42:38 2026 -0700

    feat(skills): extract polish protocol into polish-worker agent
    
    Move the fix protocol (diagnostics → fix priorities → rediagnose →
    report delta) into agents/polish-worker.md. Both entry points now
    dispatch the same agent:
    
    - Main skill Phase 5.5: dispatches agent directly (foreground, no UX)
    - Standalone /printing-press-polish: resolves CLI, checks lock,
      dispatches agent, then offers publish
    
    The standalone skill shrinks from 338 to 180 lines — it's now a thin
    UX wrapper around the agent. The fix protocol lives in one place.
    
    The agent returns a structured ---POLISH-RESULT--- block with
    scorecard/verify before/after, fixes applied, and ship recommendation.
    The caller parses it for control flow (promote vs hold).
    
    Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
---
 agents/polish-worker.md               | 170 ++++++++++++++++++++++++++++
 skills/printing-press-polish/SKILL.md | 205 ++++------------------------------
 skills/printing-press/SKILL.md        |  35 +++---
 3 files changed, 215 insertions(+), 195 deletions(-)

diff --git a/agents/polish-worker.md b/agents/polish-worker.md
new file mode 100644
index 00000000..e34162c2
--- /dev/null
+++ b/agents/polish-worker.md
@@ -0,0 +1,170 @@
+---
+name: polish-worker
+description: >
+  Internal worker agent for CLI quality fixes. Dispatched by the printing-press
+  skill (Phase 5.5) and the printing-press-polish skill. Not for direct
+  invocation — requires CLI_DIR, SPEC_PATH, and CLI_NAME passed by the caller.
+model: inherit
+color: yellow
+---
+
+You are the polish worker. You receive a CLI directory path, spec path, and CLI
+name. You run diagnostics, fix all quality issues autonomously, and return a
+structured delta report.
+
+## Rules
+
+- Fix everything without asking. You are fully autonomous.
+- Do not add new features. Polish fixes quality issues only.
+- Do not modify the printing-press generator or any files outside CLI_DIR.
+- Do not offer to publish. The caller handles that.
+- Maximum 1 fix-and-rediagnose pass.
+- Prefer mechanical fixes over creative decisions. When a creative decision is
+  needed (like the CLI description), use the research brief from manuscripts if
+  available.
+
+## Input
+
+Your dispatch prompt contains:
+
+- `CLI_DIR`: absolute path to the CLI directory
+- `CLI_NAME`: e.g., "notion-pp-cli"
+- `SPEC_PATH`: absolute path to the API spec (may be empty or "none")
+
+## Phase 1: Baseline
+
+```bash
+cd "$CLI_DIR"
+
+# Build
+go build -o "$CLI_NAME" ./cmd/"$CLI_NAME" 2>&1
+
+# Diagnostics (use SPEC_FLAG="--spec $SPEC_PATH" when SPEC_PATH is non-empty)
+printing-press dogfood --dir "$CLI_DIR" $SPEC_FLAG 2>&1
+printing-press verify --dir "$CLI_DIR" $SPEC_FLAG --json 2>&1
+printing-press scorecard --dir "$CLI_DIR" $SPEC_FLAG 2>&1
+go vet ./... 2>&1
+```
+
+Parse findings into categories:
+
+| Category | Source | What to look for |
+|----------|--------|------------------|
+| Verify failures | verify --json | Commands with score < 3 |
+| Dead code | dogfood | Dead functions, dead flags |
+| Stale files | dogfood | Unregistered commands |
+| Description issues | dogfood | Boilerplate root Short |
+| README gaps | scorecard | README score < 8 |
+| Example gaps | dogfood | Commands missing examples |
+| Go vet issues | go vet | Any output |
+
+Record baseline scores: scorecard total, verify pass rate, dogfood verdict, go vet issue count.
+
+## Phase 2: Fix
+
+Fix in priority order. After each priority level, update the lock heartbeat:
+```bash
+printing-press lock update --cli "$CLI_NAME" --phase polish 2>/dev/null
+```
+
+### Priority 1: Verify failures
+
+For each command that fails verify dry-run or exec:
+
+1. Read the command file
+2. Find `Args: cobra.ExactArgs(N)` or similar constraint
+3. Remove the `Args:` field
+4. Add at the top of `RunE`:
+   ```go
+   if len(args) == 0 {
+       return cmd.Help()
+   }
+   ```
+5. For commands needing 2+ args, use `if len(args) < 2`
+6. Check for dry-run nil-data crashes and add guards:
+   ```go
+   if flags.dryRun {
+       return nil
+   }
+   ```
+
+### Priority 2: Dead code
+
+1. For each dead function flagged by dogfood, grep all `.go` files to verify
+   it's truly unused (not just its definition matching itself)
+2. If truly unused: remove the function
+3. If used by another helper: leave it (false positive)
+4. After removal, remove unused imports
+5. Delete stale files (promoted commands not registered in root.go)
+
+### Priority 3: CLI description and metadata
+
+1. Read root command `Short` in `internal/cli/root.go`
+2. If it contains boilerplate ("Reverse-engineered...", raw API title), rewrite:
+   Pattern: `"<Product> CLI with <capability-1>, <capability-2>, and <capability-3>"`
+3. Check commands for missing `Example` fields. Add realistic examples with
+   domain-specific values.
+
+### Priority 4: README
+
+If README uses template placeholders or generic examples, rewrite with:
+- Title matching CLI name
+- One-line description matching root Short
+- Install section
+- Quick start with 3-5 real usage examples
+- Command list by category
+- Output format section
+
+### Priority 5: Remaining dogfood issues
+
+- Path validity mismatches
+- Auth protocol mismatches
+- Example drift (examples referencing wrong commands)
+- Data pipeline integrity issues
+
+### After all fixes
+
+```bash
+go build -o "$CLI_NAME" ./cmd/"$CLI_NAME"
+gofmt -w .
+```
+
+## Phase 3: Re-diagnose
+
+Re-run all four diagnostic tools on the fixed CLI:
+
+```bash
+printing-press dogfood --dir "$CLI_DIR" $SPEC_FLAG 2>&1
+printing-press verify --dir "$CLI_DIR" $SPEC_FLAG --json 2>&1
+printing-press scorecard --dir "$CLI_DIR" $SPEC_FLAG 2>&1
+go vet ./... 2>&1
+```
+
+Record the after scores.
+
+## Phase 4: Return
+
+End your response with this EXACT format. The orchestrator parses it:
+
+```
+---POLISH-RESULT---
+scorecard_before: <N>
+scorecard_after: <N>
+verify_before: <N>
+verify_after: <N>
+dogfood_before: <PASS|FAIL>
+dogfood_after: <PASS|FAIL>
+govet_before: <N>
+govet_after: <N>
+fixes_applied:
+- <one-line description of each fix>
+remaining_issues:
+- <one-line description of each unfixed issue>
+ship_recommendation: <ship|ship-with-gaps|hold>
+---END-POLISH-RESULT---
+```
+
+Ship recommendation logic:
+- `ship`: verify >= 80%, scorecard >= 75, no critical failures
+- `ship-with-gaps`: verify >= 65%, scorecard >= 65, non-critical gaps remain
+- `hold`: verify < 65% or scorecard < 65 or critical failures
diff --git a/skills/printing-press-polish/SKILL.md b/skills/printing-press-polish/SKILL.md
index c2e1edba..884fc831 100644
--- a/skills/printing-press-polish/SKILL.md
+++ b/skills/printing-press-polish/SKILL.md
@@ -21,11 +21,11 @@ allowed-tools:
 
 # /printing-press-polish
 
-Fix a generated CLI so it passes verification and is ready to publish. This skill
-does the work that `/printing-press-retro` *identifies* for the machine -- but
-applied to the CLI itself.
+Polish a generated CLI so it passes verification and is ready to publish.
 
-The retro improves the generator. Polish improves the generated CLI.
+The retro improves the generator. Polish improves the generated CLI. The actual
+fix protocol lives in the `polish-worker` agent — this skill resolves the CLI,
+checks locks, dispatches the agent, and offers to publish.
 
 ```bash
 /printing-press-polish redfin
@@ -96,181 +96,33 @@ echo "Polishing: $CLI_NAME"
 echo "Location: $CLI_DIR"
 ```
 
-## Phase 1: Diagnostics
-
-Run all diagnostic tools to establish a baseline. Capture output for comparison.
+### Find spec
 
 ```bash
-cd "$CLI_DIR"
-
-# Find the spec if one exists in manuscripts
 API_SLUG="${CLI_NAME%-pp-cli}"
 SPEC_PATH=""
-for f in "$PRESS_HOME/manuscripts/$API_SLUG"/*/research/*.yaml "$PRESS_HOME/manuscripts/$API_SLUG"/*/research/*.json; do
+for f in "$PRESS_HOME/manuscripts/$API_SLUG"/*/research/*.yaml "$PRESS_HOME/manuscripts/$API_SLUG"/*/research/*.json "$PRESS_HOME/manuscripts/$CLI_NAME"/*/research/*.yaml "$PRESS_HOME/manuscripts/$CLI_NAME"/*/research/*.json; do
   if [ -f "$f" ]; then
     SPEC_PATH="$f"
     break
   fi
 done
-
-SPEC_FLAG=""
-if [ -n "$SPEC_PATH" ]; then
-  SPEC_FLAG="--spec $SPEC_PATH"
-fi
-```
-
-### 1.1 Run diagnostics
-
-```bash
-# Build the binary first
-go build -o "$CLI_NAME" ./cmd/"$CLI_NAME" 2>&1
-
-# Run all four diagnostic tools
-printing-press dogfood --dir "$CLI_DIR" $SPEC_FLAG 2>&1 | tee /tmp/polish-dogfood.txt
-printing-press verify --dir "$CLI_DIR" $SPEC_FLAG --json 2>&1 | tee /tmp/polish-verify.json
-printing-press scorecard --dir "$CLI_DIR" $SPEC_FLAG 2>&1 | tee /tmp/polish-scorecard.txt
-go vet ./... 2>&1 | tee /tmp/polish-govet.txt
-```
-
-### 1.2 Parse findings
-
-Parse the diagnostic output into categorized findings:
-
-| Category | Source | Example |
-|----------|--------|---------|
-| Verify failures | verify --json | Command "pulse" dry-run FAIL, exec FAIL |
-| Dead code | dogfood | 15 dead functions in helpers.go |
-| Dead flags | dogfood | 7 flags declared but never read |
-| Stale files | dogfood + grep | promoted_stingray.go not registered |
-| README gaps | scorecard | README score 5/10 |
-| Description issues | dogfood | Root Short is "Reverse-engineered..." |
-| Example gaps | dogfood | analyze-zips missing example |
-| Data pipeline | verify | Data pipeline FAIL |
-| Go vet issues | go vet | Unused variables, unreachable code |
-
-### 1.3 Report baseline
-
-Present the baseline clearly:
-
-```
-Baseline for <CLI_NAME>:
-  Scorecard:    XX/100 (Grade X)
-  Verify:       XX% (N/M passed)
-  Dogfood:      PASS/FAIL
-  Go vet:       N issues
-
-Findings:
-  [N] verify failures
-  [N] dead code items
-  [N] description/README issues
-  [N] other issues
 ```
 
-## Phase 2: Fix
-
-Fix everything automatically in priority order. Do not ask for approval. The user
-reviews the diff after all fixes are applied.
-
-### Priority 1: Verify failures
-
-The most common verify failure pattern is cobra `Args:` constraints that prevent
-the verify tool from testing commands with no positional args. The verify tool
-runs `<binary> <cmd> --dry-run` and `<binary> <cmd> --json` with no positional
-args.
-
-**Fix strategy:**
-
-For each command that fails verify dry-run or exec:
-
-1. Read the command file (e.g., `internal/cli/pulse.go`)
-2. Find `Args: cobra.ExactArgs(N)` or similar constraint in the cobra.Command struct
-3. Remove the `Args:` field entirely
-4. Add at the top of `RunE`:
-   ```go
-   if len(args) == 0 {
-       return cmd.Help()
-   }
-   ```
-5. For commands needing 2+ args (like `compare-hoods`), use `if len(args) < 2`
-6. For commands that use only flags (no positional args), ensure they show help
-   and exit 0 when required flags are missing
-
-Also check for dry-run nil-data crashes:
-- If a command makes API calls and the dry-run response is nil, add a guard:
-  ```go
-  if flags.dryRun {
-      return nil
-  }
-  ```
-
-### Priority 2: Dead code
-
-For each dead function flagged by dogfood:
-
-1. Grep all `.go` files to verify the function is truly unused (not just its
-   definition matching itself)
-2. If truly unused: remove the function
-3. If used internally by another helper: leave it (dogfood false positive)
-4. After removal, check for unused imports and remove them
-5. Delete any stale files (e.g., promoted commands that are no longer registered
-   in root.go)
-
-### Priority 3: CLI description and metadata
-
-1. Read the root command's `Short` field in `internal/cli/root.go`
-2. If it contains generator boilerplate (e.g., "Reverse-engineered...", raw API
-   title), rewrite it to be user-friendly:
-   - Pattern: `"<Product> CLI with <key-capability-1>, <key-capability-2>, and <key-capability-3>"`
-   - Example: `"Redfin real estate CLI with offline search, market analysis, and portfolio tracking"`
-3. Check all commands for missing `Example` fields. Add realistic examples with
-   domain-specific values.
-
-### Priority 4: README
-
-1. Read the current README.md
-2. If it uses the generator's template with placeholder names or generic examples,
-   rewrite it:
-   - Title: CLI name
-   - One-line description matching the root Short
-   - Install section with `go install` command
-   - Quick start with 3-5 real usage examples
-   - Command list organized by category (from `--help` output)
-   - Output format section showing `--json`, `--select`, `--dry-run`
-   - Configuration section
-3. Use actual command names and realistic example values from the API domain
-
-### Priority 5: Remaining dogfood issues
-
-Address any remaining issues flagged by dogfood:
-- Path validity mismatches
-- Auth protocol mismatches
-- Example drift (examples that reference wrong commands)
-- Data pipeline integrity issues
-
-### After all fixes
+## Polish: Dispatch the Agent
 
-```bash
-# Rebuild
-go build -o "$CLI_NAME" ./cmd/"$CLI_NAME"
+Dispatch the `polish-worker` agent to run the full diagnostic-fix-rediagnose
+loop. The agent is autonomous and returns a structured result.
 
-# Format
-gofmt -w .
 ```
-
-## Phase 3: Re-diagnose
-
-Re-run all diagnostic tools on the fixed CLI.
-
-```bash
-printing-press dogfood --dir "$CLI_DIR" $SPEC_FLAG 2>&1 | tee /tmp/polish-dogfood-after.txt
-printing-press verify --dir "$CLI_DIR" $SPEC_FLAG --json 2>&1 | tee /tmp/polish-verify-after.json
-printing-press scorecard --dir "$CLI_DIR" $SPEC_FLAG 2>&1 | tee /tmp/polish-scorecard-after.txt
-go vet ./... 2>&1 | tee /tmp/polish-govet-after.txt
+Agent(
+  subagent_type: "cli-printing-press:polish-worker",
+  description: "Polish CLI quality",
+  prompt: "Polish this CLI.\nCLI_DIR: $CLI_DIR\nCLI_NAME: $CLI_NAME\nSPEC_PATH: $SPEC_PATH"
+)
 ```
 
-## Phase 4: Report delta
-
-Present the before/after comparison:
+The agent returns a `---POLISH-RESULT---` block. Parse it and display the delta:
 
 ```
 Polish Results for <CLI_NAME>:
@@ -278,23 +130,17 @@ Polish Results for <CLI_NAME>:
                     Before    After     Delta
   Scorecard:        XX/100    XX/100    +N
   Verify:           XX%       XX%       +N%
-  Dogfood:          FAIL      PASS
-  Go vet issues:    N         N         -N
 
 Fixes applied:
-  - Fixed N commands for no-arg handling (verify)
-  - Removed N dead functions
-  - Rewrote CLI description
-  - Updated README
-  - [other fixes]
+  - [from fixes_applied in result]
 
 Remaining issues:
-  - [any issues that couldn't be fixed automatically]
+  - [from remaining_issues in result]
 ```
 
-## Phase 5: Publish offer
+## Publish Offer
 
-If the final scorecard is >= 65 and verify is PASS (or >= 80%):
+If `scorecard_after` >= 65 and `verify_after` >= 80:
 
 Present via `AskUserQuestion`:
 
@@ -304,8 +150,7 @@ Present via `AskUserQuestion`:
 > 2. **Polish again** — run another fix pass on remaining issues
 > 3. **Done for now** — CLI is at ~/printing-press/library/<cli-name>
 
-If the verdict was `ship-with-gaps` or there are remaining issues, prepend:
-"Note: some issues remain (see above)."
+If remaining issues exist, prepend: "Note: some issues remain (see above)."
 
 ### If "Publish now"
 
@@ -314,11 +159,12 @@ Check for existing PR:
 gh pr list --repo mvanhorn/printing-press-library --head "feat/$CLI_NAME" --state open --author @me --json number,url --jq '.[0]' 2>/dev/null
 ```
 
-Then invoke `/printing-press publish <cli-name>`.
+Then invoke `/printing-press-publish <cli-name>`.
 
 ### If "Polish again"
 
-Re-run Phase 2-4. Maximum 2 additional polish passes.
+Re-dispatch the `polish-worker` agent with the same arguments. Maximum 2
+additional polish passes (3 total including the first).
 
 ### If "Done for now"
 
@@ -326,12 +172,9 @@ End normally.
 
 ## Rules
 
-- Fix everything. Do not ask for approval before fixing.
+- Fix everything. Do not ask for approval before fixing — the agent handles it.
 - Report results honestly. Show what improved and what didn't.
 - Do not add new features. Polish fixes quality issues, not feature gaps.
 - Do not re-run research or generation. Polish works with the CLI as-is.
 - Do not modify the printing-press generator. That's `/printing-press-retro`.
-- Prefer mechanical fixes over creative decisions. When a creative decision is
-  needed (like the CLI description), use the research brief from manuscripts if
-  available to inform the choice.
 - Maximum 3 total polish passes (initial + 2 retries).
diff --git a/skills/printing-press/SKILL.md b/skills/printing-press/SKILL.md
index 415f47d6..26c9e44e 100644
--- a/skills/printing-press/SKILL.md
+++ b/skills/printing-press/SKILL.md
@@ -1276,31 +1276,38 @@ Write:
 
 ## Phase 5.5: Polish
 
-**Always runs.** After shipcheck (and dogfood if it ran), do one automatic polish
-pass before promoting. Don't ask — just run it. The goal is to ship the best CLI
-possible, not the fastest.
+**Always runs.** Dispatch the `polish-worker` agent to run diagnostics, fix quality
+issues, and return a structured delta report. The agent is autonomous — no user
+input needed. The goal is to ship the best CLI possible, not the fastest.
 
-```bash
-cd "$CLI_WORK_DIR"
-go build -o "$CLI_NAME" ./cmd/"$CLI_NAME"
-gofmt -w .
+Dispatch via the Agent tool (**foreground** — must complete before promoting):
 
-printing-press dogfood  --dir "$CLI_WORK_DIR" --spec <same-spec>
-printing-press verify   --dir "$CLI_WORK_DIR" --spec <same-spec> --fix
-printing-press scorecard --dir "$CLI_WORK_DIR" --spec <same-spec>
 ```
+Agent(
+  subagent_type: "cli-printing-press:polish-worker",
+  description: "Polish CLI quality",
+  prompt: "Polish this CLI.\nCLI_DIR: $CLI_WORK_DIR\nCLI_NAME: <api>-pp-cli\nSPEC_PATH: <same-spec>"
+)
+```
+
+The agent runs the full diagnostic-fix-rediagnose loop and ends its response with
+a `---POLISH-RESULT---` block containing scorecard/verify before/after, fixes
+applied, and a ship recommendation.
 
-Fix what the tools find: dead code, verify regressions, description issues,
-README gaps. This is mechanical — no user input needed. Report the delta:
+Parse the result. Display the delta to the user:
 
 ```
 Polish pass:
   Verify:    86% → 93% (+7%)
   Scorecard: 92 → 94 (+2)
-  Fixed: removed 2 dead functions, fixed 1 verify regression
+  Fixed: [summary of fixes_applied from result]
 ```
 
-Write:
+**Verdict override:** If the agent's `ship_recommendation` is `hold` and the
+Phase 4 verdict was `ship` or `ship-with-gaps`, downgrade to `hold`. Release
+the lock without promoting.
+
+Write the agent's full response to:
 
 `$PROOFS_DIR/<stamp>-fix-<api>-pp-cli-polish.md`
 

← d509976c fix(skills): polish always runs after shipcheck, not just af  ·  back to Cli Printing Press  ·  fix(skills): polish agent reports skipped findings with reas c4befa79 →