diff --git a/.claude/skills/pixellab-cli-animation/SKILL.md b/.claude/skills/pixellab-cli-animation/SKILL.md index 50672cf..397c0cf 100644 --- a/.claude/skills/pixellab-cli-animation/SKILL.md +++ b/.claude/skills/pixellab-cli-animation/SKILL.md @@ -12,6 +12,10 @@ arrives, paid for, and looks off. `pixellab-cli-characters`; this skill starts after that. Read `pixellab-cli-assets` for the spending rule: every paid line below needs its own `--yes`. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## The order **One state per motion, and animate the state itself.** Not the base character with the diff --git a/.claude/skills/pixellab-cli-assets/SKILL.md b/.claude/skills/pixellab-cli-assets/SKILL.md index 7e99a43..6bb2ad6 100644 --- a/.claude/skills/pixellab-cli-assets/SKILL.md +++ b/.claude/skills/pixellab-cli-assets/SKILL.md @@ -151,6 +151,27 @@ in their shell history, which is the one thing this command exists to avoid. a commit or a message. Do not scan `.env` files or shell history looking for one. The person sets the variable; you never see it. +## `--help` before you name an option + +**Run the command's own help before you tell anyone what it takes, and before you tell +anyone it cannot do something.** It is free, instant, local, needs no credential and +reaches no provider: + +```bash +pixellab-cli --help +pixellab-cli --help # character animate, art concept, ui new +``` + +The option lists in these skills are what was true when they were written. The installed +version is what runs, and it is a release or several ahead — so a flag these pages do +not mention may well be there. `art concept --transparent` was in the tool long before +anybody read it off the help. + +The asymmetry is the whole reason: missing a flag that exists costs a generation spent +on the wrong thing, or a flat wrong answer to the person. Reading the help costs +nothing. So read it, then use these pages for *when* to reach for each option, which is +the part the help does not say. + ## Do not name a route, do not guess a limit The tool picks between overlapping routes by size and by what you gave it, and says which diff --git a/.claude/skills/pixellab-cli-characters/SKILL.md b/.claude/skills/pixellab-cli-characters/SKILL.md index afa7862..3cabc2d 100644 --- a/.claude/skills/pixellab-cli-characters/SKILL.md +++ b/.claude/skills/pixellab-cli-characters/SKILL.md @@ -9,6 +9,10 @@ below: one bad reference becomes eight bad rotations becomes eight bad animation Read `pixellab-cli-assets` first for the spending rule and the credentials. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## The order, and it is not a suggestion ``` diff --git a/.claude/skills/pixellab-cli-editing/SKILL.md b/.claude/skills/pixellab-cli-editing/SKILL.md index b64795d..cf6e79f 100644 --- a/.claude/skills/pixellab-cli-editing/SKILL.md +++ b/.claude/skills/pixellab-cli-editing/SKILL.md @@ -7,6 +7,10 @@ Changing art that exists, and the cleanup that should happen between every paid Read `pixellab-cli-assets` first for the spending rule and the credentials. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## An instruction, anywhere in the image ``` diff --git a/.claude/skills/pixellab-cli-images/SKILL.md b/.claude/skills/pixellab-cli-images/SKILL.md index b5b51d3..8132c42 100644 --- a/.claude/skills/pixellab-cli-images/SKILL.md +++ b/.claude/skills/pixellab-cli-images/SKILL.md @@ -7,6 +7,10 @@ One image at a time, and the one trick that turns one image into a matching set. Read `pixellab-cli-assets` first for the spending rule and the credentials. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## One sprite ``` diff --git a/.claude/skills/pixellab-cli-interface/SKILL.md b/.claude/skills/pixellab-cli-interface/SKILL.md index f9022c4..3f5c599 100644 --- a/.claude/skills/pixellab-cli-interface/SKILL.md +++ b/.claude/skills/pixellab-cli-interface/SKILL.md @@ -7,6 +7,10 @@ What a player reads rather than what they move. Read `pixellab-cli-assets` first for the spending rule and the credentials. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## A panel ``` diff --git a/.claude/skills/pixellab-cli-scenes/SKILL.md b/.claude/skills/pixellab-cli-scenes/SKILL.md index 3728600..cf1c1fa 100644 --- a/.claude/skills/pixellab-cli-scenes/SKILL.md +++ b/.claude/skills/pixellab-cli-scenes/SKILL.md @@ -8,6 +8,10 @@ help: the work is seam geometry, which a picture of grass has no opinion about. Read `pixellab-cli-assets` first for the spending rule and the credentials. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## Terrain that connects ``` diff --git a/docs/notes.md b/docs/notes.md index 67c23ef..67343c0 100644 --- a/docs/notes.md +++ b/docs/notes.md @@ -96,3 +96,4 @@ over this file answers with the example above as well as with the notes. --> - n-0056 2026-09-20 #gotcha @src/pixellab_cli/pixellab.py — ui-assets/{id} returns image_url and no base64, so a completed job with no bytes is fetched from its address in _await rather than in _decode_images - n-0057 2026-09-20 #gotcha @src/pixellab_cli/run.py — approve gates on the estimate, not the route, so a reported zero passes and an absent estimate still asks - n-0058 2026-09-20 #gotcha @src/pixellab_cli/pixellab.py — a path parameter is refused in _split_path when it holds a separator or a dot segment, so no route has to remember the check +- n-0059 2026-09-20 #gotcha @tests/test_skill.py — the skill tests walk a hand-written CATEGORY_SKILLS tuple, so a packaged skill missing from it is tested by nothing; TestNothingShipsUntested binds it to harness.packaged_skills diff --git a/specs/agent-skill/design.md b/specs/agent-skill/design.md index afa9959..3c8771d 100644 --- a/specs/agent-skill/design.md +++ b/specs/agent-skill/design.md @@ -100,3 +100,23 @@ so it names one path rather than six. Endpoint names, enum spellings and size ceilings (R1.2). The CLI validates all three and its errors name what would have worked, so an agent that guesses wrong is corrected for free. Duplicating them in the skill would create a second copy to drift. + +## The help is the current list, and the skill is not + +A skill is written once and read for as long as it is installed. The options it names +are the options that existed the day it was written, and every release since has been +free to add one — so an agent that reads only the skill answers "the tool cannot do +that" about a flag that has been there for three versions. That happened: `art concept` +has carried `--transparent` for as long as it has existed, and it took a live check to +establish it rather than a read. + +The failure is asymmetric, which is why it is worth a rule. Missing a flag that exists +costs a generation spent on the wrong thing, or an answer that is simply wrong. Reading +the help costs nothing: it is local, it is instant, it needs no credential and it +reaches no provider. So the skill says to run it — before naming a command's options, +and before telling anyone an option does not exist. + +The skill keeps its option lists. They are what makes it useful to read at all, and a +list nobody wrote is not an improvement on a list that is a version behind. They are +framed as what the skill knows rather than as what the tool accepts, and the command's +own `--help` is named as the list that is current. diff --git a/specs/agent-skill/requirements.md b/specs/agent-skill/requirements.md index 088eb88..52da43d 100644 --- a/specs/agent-skill/requirements.md +++ b/specs/agent-skill/requirements.md @@ -1,9 +1,9 @@ --- autonomy: auto ci: wait -branch: feat/the-pose-must-suit-the-action -delivery: merged -pr: 66 +branch: docs/the-help-is-the-current-list +delivery: in-review +pr: 80 --- # Agent skill — requirements @@ -55,6 +55,8 @@ the person did not agree to. - **R5.11** (ADDED) The agent skill shall give animating a character that exists its own category skill, separate from creating one, carrying the order its steps are taken in. +- **R5.12** (ADDED) The agent skill shall direct an agent to read a command's own help before naming that command's options, and shall state that the help costs nothing and is what the installed version accepts. + ## Out of scope - Teaching PixelLab's or fal's APIs. The skill teaches the CLI; the CLI owns the APIs. diff --git a/specs/agent-skill/tasks.md b/specs/agent-skill/tasks.md index e70593e..dabaa43 100644 --- a/specs/agent-skill/tasks.md +++ b/specs/agent-skill/tasks.md @@ -40,3 +40,8 @@ - [x] 2.3 (TDD) Report an installed skill this tool no longer ships — R5.6 _Depends 2.2_ _Reason installing six skills is not installing one six times_ + +## 6 · The help is the current list +- [x] 6.1 (Unit) Send the agent to a command's own help before naming options — R5.12 + _Reason a flag that existed was reported as missing_ + diff --git a/src/pixellab_cli/harness.py b/src/pixellab_cli/harness.py index a861d8d..40c8323 100644 --- a/src/pixellab_cli/harness.py +++ b/src/pixellab_cli/harness.py @@ -280,6 +280,11 @@ def block_body(references: Path | None) -> str: whenever the enhancer is unavailable — write the motion out yourself. Never fall back to the bare action. +**Run `--help` before you name an option.** `pixellab-cli --help` is free, +local and instant, and it is what the installed version accepts — the skills list the +options that existed when they were written. Check it before telling the person a +command takes something, and before telling them it cannot do something at all. + **Read the entity before reaching for an identifier.** `pixellab-cli inspect ` is free and local: every character, every pose made from it, which pose each animation started from, and what the subject has cost. A `--start-pose` from the wrong character diff --git a/src/pixellab_cli/skill/pixellab-cli-animation/SKILL.md b/src/pixellab_cli/skill/pixellab-cli-animation/SKILL.md index 50672cf..397c0cf 100644 --- a/src/pixellab_cli/skill/pixellab-cli-animation/SKILL.md +++ b/src/pixellab_cli/skill/pixellab-cli-animation/SKILL.md @@ -12,6 +12,10 @@ arrives, paid for, and looks off. `pixellab-cli-characters`; this skill starts after that. Read `pixellab-cli-assets` for the spending rule: every paid line below needs its own `--yes`. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## The order **One state per motion, and animate the state itself.** Not the base character with the diff --git a/src/pixellab_cli/skill/pixellab-cli-assets/SKILL.md b/src/pixellab_cli/skill/pixellab-cli-assets/SKILL.md index 7e99a43..6bb2ad6 100644 --- a/src/pixellab_cli/skill/pixellab-cli-assets/SKILL.md +++ b/src/pixellab_cli/skill/pixellab-cli-assets/SKILL.md @@ -151,6 +151,27 @@ in their shell history, which is the one thing this command exists to avoid. a commit or a message. Do not scan `.env` files or shell history looking for one. The person sets the variable; you never see it. +## `--help` before you name an option + +**Run the command's own help before you tell anyone what it takes, and before you tell +anyone it cannot do something.** It is free, instant, local, needs no credential and +reaches no provider: + +```bash +pixellab-cli --help +pixellab-cli --help # character animate, art concept, ui new +``` + +The option lists in these skills are what was true when they were written. The installed +version is what runs, and it is a release or several ahead — so a flag these pages do +not mention may well be there. `art concept --transparent` was in the tool long before +anybody read it off the help. + +The asymmetry is the whole reason: missing a flag that exists costs a generation spent +on the wrong thing, or a flat wrong answer to the person. Reading the help costs +nothing. So read it, then use these pages for *when* to reach for each option, which is +the part the help does not say. + ## Do not name a route, do not guess a limit The tool picks between overlapping routes by size and by what you gave it, and says which diff --git a/src/pixellab_cli/skill/pixellab-cli-characters/SKILL.md b/src/pixellab_cli/skill/pixellab-cli-characters/SKILL.md index afa7862..3cabc2d 100644 --- a/src/pixellab_cli/skill/pixellab-cli-characters/SKILL.md +++ b/src/pixellab_cli/skill/pixellab-cli-characters/SKILL.md @@ -9,6 +9,10 @@ below: one bad reference becomes eight bad rotations becomes eight bad animation Read `pixellab-cli-assets` first for the spending rule and the credentials. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## The order, and it is not a suggestion ``` diff --git a/src/pixellab_cli/skill/pixellab-cli-editing/SKILL.md b/src/pixellab_cli/skill/pixellab-cli-editing/SKILL.md index b64795d..cf6e79f 100644 --- a/src/pixellab_cli/skill/pixellab-cli-editing/SKILL.md +++ b/src/pixellab_cli/skill/pixellab-cli-editing/SKILL.md @@ -7,6 +7,10 @@ Changing art that exists, and the cleanup that should happen between every paid Read `pixellab-cli-assets` first for the spending rule and the credentials. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## An instruction, anywhere in the image ``` diff --git a/src/pixellab_cli/skill/pixellab-cli-images/SKILL.md b/src/pixellab_cli/skill/pixellab-cli-images/SKILL.md index b5b51d3..8132c42 100644 --- a/src/pixellab_cli/skill/pixellab-cli-images/SKILL.md +++ b/src/pixellab_cli/skill/pixellab-cli-images/SKILL.md @@ -7,6 +7,10 @@ One image at a time, and the one trick that turns one image into a matching set. Read `pixellab-cli-assets` first for the spending rule and the credentials. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## One sprite ``` diff --git a/src/pixellab_cli/skill/pixellab-cli-interface/SKILL.md b/src/pixellab_cli/skill/pixellab-cli-interface/SKILL.md index f9022c4..3f5c599 100644 --- a/src/pixellab_cli/skill/pixellab-cli-interface/SKILL.md +++ b/src/pixellab_cli/skill/pixellab-cli-interface/SKILL.md @@ -7,6 +7,10 @@ What a player reads rather than what they move. Read `pixellab-cli-assets` first for the spending rule and the credentials. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## A panel ``` diff --git a/src/pixellab_cli/skill/pixellab-cli-scenes/SKILL.md b/src/pixellab_cli/skill/pixellab-cli-scenes/SKILL.md index 3728600..cf1c1fa 100644 --- a/src/pixellab_cli/skill/pixellab-cli-scenes/SKILL.md +++ b/src/pixellab_cli/skill/pixellab-cli-scenes/SKILL.md @@ -8,6 +8,10 @@ help: the work is seam geometry, which a picture of grass has no opinion about. Read `pixellab-cli-assets` first for the spending rule and the credentials. +The options below are what this page knows. `pixellab-cli --help` is what +the installed version accepts, it is free, and it is the list to check before you +name an option or say there is none. + ## Terrain that connects ``` diff --git a/tests/test_skill.py b/tests/test_skill.py index 232b7cc..3f02ca2 100644 --- a/tests/test_skill.py +++ b/tests/test_skill.py @@ -25,9 +25,13 @@ PACKAGED = Path(__file__).resolve().parents[1] / "src" / "pixellab_cli" / "skill" +# Every category skill `harness.packaged_skills` ships, and the list is checked against +# it below: one missing from here is a skill nothing in this file tests, which is how +# the animation skill went five releases without being checked at all. CATEGORY_SKILLS = ( "pixellab-cli-images", "pixellab-cli-characters", + "pixellab-cli-animation", "pixellab-cli-editing", "pixellab-cli-scenes", "pixellab-cli-interface", @@ -239,3 +243,40 @@ def test_every_packaged_file_is_installed_unchanged(self, name): } assert installed == packaged + + +class TestTheHelpIsTheCurrentList: + """R5.12. A skill is written once and read for as long as it is installed, so the + options it names are a version behind from the first release after it. The help is + free, local and current — `art concept --transparent` was in the tool long before + anybody read it off a page.""" + + def test_the_entry_sends_the_agent_to_the_help(self): + body = entry_text() + + assert "--help" in body + assert "free" in body.lower() + + @pytest.mark.parametrize("name", CATEGORY_SKILLS) + def test_every_category_skill_names_the_help(self, name): + """A category skill is where the options are listed, which is where the + reminder has to be: an agent that loaded only this one still gets it.""" + assert "--help" in skill_body(name) + + def test_the_harness_block_carries_it_too(self): + """An agent whose harness loads a skill only when it judges it relevant reads + this block every session and may never load a skill at all.""" + from pixellab_cli.harness import block_body + + assert "--help" in block_body(None) + + +class TestNothingShipsUntested: + """The animation skill was packaged and installed for five releases while every + test in this file walked past it, because the list above is written by hand and + the shipped set is not. One missing name is a whole skill nobody checks.""" + + def test_every_packaged_skill_is_named_here(self): + from pixellab_cli.harness import packaged_skills + + assert set(packaged_skills()) == set(ALL_SKILLS)