pbakaus/impeccable · error

Unknown action: {}. Use 'pin' or 'unpin'.

Error message

Unknown action: {}. Use 'pin' or 'unpin'.

What it means

The pin subcommand accepts exactly two actions: `pin` and `unpin`. Any other first argument triggers this error, which then exits 1 after printing the valid options. It is a CLI argument validation guarding the action enum.

Source

Thrown at crates/context/src/pin.rs:223

    if let Some(dir) = &provider.skill_dir {
        let p = jsp::join(&[dir, "scripts", "command-metadata.json"]);
        if let Some(v) = read_json(&p) {
            return v;
        }
    }
    serde_json::from_str(COMMAND_METADATA_JSON).unwrap_or(serde_json::Value::Object(Default::default()))
}

pub fn run(args: &[String], io: &mut Io) -> i32 {
    let action = args.first().cloned();
    let command = args.get(1).cloned();
    let (Some(action), Some(command)) = (action.filter(|a| !a.is_empty()), command.filter(|c| !c.is_empty())) else {
        io.out("Usage: impeccable pin <pin|unpin> <command>\n");
        io.out(&format!("\nAvailable commands: {}\n", VALID_COMMANDS.join(", ")));
        return 1;
    };
    if action != "pin" && action != "unpin" {
        io.err(&format!("Unknown action: {}. Use 'pin' or 'unpin'.\n", action));
        return 1;
    }
    if !VALID_COMMANDS.contains(&command.as_str()) {
        io.err(&format!("Unknown command: {}\n", command));
        io.err(&format!("Available commands: {}\n", VALID_COMMANDS.join(", ")));
        return 1;
    }
    let cwd = io.cwd.to_string_lossy().into_owned();
    let root = find_project_root(&cwd);
    if action == "pin" {
        let metadata = load_metadata(io);
        let harness_dirs = find_harness_dirs(&root);
        let opencode_commands_dirs = find_opencode_commands_dirs(&root, io, false);
        if harness_dirs.is_empty() && opencode_commands_dirs.is_empty() {
            io.out("No harness directories with impeccable installed found.\n");
            return 0;
        }
        let mut created = 0;

View on GitHub (pinned to 2bc2879276)

Solutions

  1. Use `impeccable pin <command>` to pin or `impeccable unpin <command>` to unpin — the action must be literally "pin" or "unpin".
  2. Check the printed usage line and the Available commands list for exact spelling.
  3. Fix typos in scripts (e.g. `pinned` → `pin`, `rm` → `unpin`).
  4. If you intended to list pinned commands, look for a separate list/show subcommand rather than a pin action.
  5. Run `impeccable pin` with no args to see the usage help.

Example fix

// before
impeccable pin add review
// Unknown action: add. Use 'pin' or 'unpin'.
// after
impeccable pin review
Defensive patterns

Strategy: validation

Validate before calling

const VALID_ACTIONS = ["pin", "unpin"];
if (!VALID_ACTIONS.includes(action)) {
  throw new Error(`pin action must be 'pin' or 'unpin', got: ${action}`);
}

Try / catch

const r = spawnSync("impeccable", ["pin", action, cmd], { encoding: "utf8" });
if (r.status !== 0 && /Unknown action:/.test(r.stderr)) {
  console.error(`invalid pin action '${action}' — use pin|unpin`);
}

Prevention

When it happens

Trigger: Running `impeccable pin <action> <command>` where action is anything other than "pin" or "unpin" — e.g. `impeccable pin add ...`, `impeccable pin remove ...`, `impeccable pin list`, or a misspelled variant like `pinned`.

Common situations: Guessing at verb names by analogy with other CLIs (add/remove/toggle); typos; scripts written against an imagined API; confusion between the pin command and other subcommands that list or manage pinned commands.

Understand the failure class

Background: Invalid enum value errors: "Unknown type", "Invalid scope", "must be one of" — when a string is not on the library's allowed list — this error's family across 23 libraries.

Related errors


AI-assisted analysis of pbakaus/impeccable@2bc2879276 (2026-09-08). Data as JSON: /api/errors/21dbeaef584cfb88. Report an issue: GitHub.