Skip to content

Move Claude Code hook registration into code-trace setup - #11

Closed
winjer wants to merge 1 commit into
mainfrom
setup-subcommand-hook-registration
Closed

Move Claude Code hook registration into code-trace setup#11
winjer wants to merge 1 commit into
mainfrom
setup-subcommand-hook-registration

Conversation

@winjer

@winjer winjer commented Jul 20, 2026

Copy link
Copy Markdown
Contributor

First slice of the installer-slimming direction we discussed: move the fragile, growing logic out of install.sh and into the binary, starting with the highest fragility-per-line piece — the Claude Code Stop-hook registration, which was an embedded python3 program.

What changed

  • src/setup.rs — a pure register_stop_hook(Value) -> Value transform (migrate legacy ~/.claude/hooks/code-trace, absolute-path, and with-args hooks to the canonical bare code-trace command; dedup; preserve unrelated settings and unrelated Stop hooks; reset malformed hooks/Stop shapes), plus file IO that treats a missing file as empty and refuses to overwrite invalid JSON. Exposed as code-trace setup --register-hook [--settings-file <path>].
  • install.shregister_claude_code_hook now delegates to the binary, dropping the installer's only python3 dependency. The installer no longer needs an interpreter.
  • Tests — hook-registration coverage moves from the python-based tests/install_hook_test.sh (deleted) to Rust: 14 unit tests on the transform + 7 integration tests driving the real built binary (CARGO_BIN_EXE_code-trace), including a new invalid-JSON-refusal case.

Behaviour parity

Identical to the old python logic across all previously-covered cases (verified end to end through the sourced install.sh wrapper), with one cosmetic difference: serde_json sorts JSON keys alphabetically vs python's insertion order. Functionally identical — Claude Code reads it as JSON.

Why

The python3 heredoc was an untested mini-program and a hidden dependency (the only thing in the project needing python). In Rust it's type-checked, unit-tested, and interpreter-free. This also establishes the setup subcommand pattern for migrating the remaining install steps (config write, prompts, plugin copy) incrementally.

cargo test (all suites) and cargo clippy --all-targets are clean.

🤖 Generated with Claude Code

First slice of shrinking install.sh toward a thin bootstrap: the Stop
hook registration that lived in install.sh as an embedded python3 program
now ships in the binary as `code-trace setup --register-hook`.

- New src/setup.rs: a pure register_stop_hook(Value) -> Value transform
  (migrate legacy/absolute/args code-trace hooks to the canonical bare
  command, dedup, preserve unrelated settings and hooks, reset malformed
  shapes) plus file IO that refuses to overwrite invalid JSON, wired to a
  `setup` subcommand.
- install.sh delegates to the binary, dropping its only python3
  dependency; the installer now needs no interpreter.
- Hook-registration coverage moves from the python-based
  tests/install_hook_test.sh (deleted) to Rust: 14 unit tests on the
  transform plus 7 integration tests driving the real binary, including
  the invalid-JSON refusal.

Behaviour is unchanged except JSON key ordering (serde_json sorts keys
vs python's insertion order) — cosmetic and functionally identical.

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

winjer commented Jul 20, 2026

Copy link
Copy Markdown
Contributor Author

Superseded by #14, which collapses #11#13 into a single commit against main (and fixes the harness Docker build to copy plugin/ for the new include_str!).

@winjer winjer closed this Jul 20, 2026
@winjer
winjer deleted the setup-subcommand-hook-registration branch July 20, 2026 15:46
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