Skip to content

tenon v0.5.0

Choose a tag to compare

@tenon-code-eu tenon-code-eu released this 19 Oct 20:36
· 283 commits to main since this release

Hooks

tenon now runs hooks: commands, or checks by the model, that tenon runs at fixed points of a session. The format is the one of Claude Code (the hooks key of settings.json): a hook written for Claude Code works without change.

  • Sources: ~/.config/tenon/hooks.json, always. ~/.claude/settings.json only with [hooks] claude_settings = true in the global configuration. Hooks of a project (.claude/settings.json, .tenon/hooks.json) are never run: tenon shows a notice.
  • Events: PreToolUse, PostToolUse, UserPromptSubmit, Stop, SubagentStop, SessionStart, SessionEnd, PreCompact, Notification.
  • Types: command (a shell command), prompt (a check by the session model), agent (a read-only sub-agent).
  • What a hook can do: block a tool call or a prompt, ask for your approval, rewrite the input of a tool, give feedback to the model, add context, continue a turn that would stop.
  • Claude Code compatibility: tool names (Bash, Edit, Write…) and arguments (file_path…) are translated both ways; exit code 2 and the JSON output work as in Claude Code.
  • Security:
    • A hook allow lifts only what a global allow rule could lift. It never lifts a deny rule, a forced approval for a non-EU tool, an access outside the project or to a sensitive file, or an ask rule of the project.
    • A rewritten input is checked again, and the permission rules apply to the new input.
    • An invalid hooks file stops tenon at startup.
    • Each hook run is in the audit chain (HookStarted, HookCompleted).
    • Text that a hook sends to the model is masked and goes through the jurisdiction check.
    • command hooks get the unmasked input and run with your rights: what they do with it is your responsibility.
  • Interface: tenon hooks and /hooks list the hooks. The banner shows hooks: N (claude: M). A hook that blocks, asks or fails shows a line in the interface. In -p mode with text output, the same messages go to stderr.

See Hooks and security.

Other changes

  • New key [hooks] in the global configuration (claude_settings, disabled). It is refused in .tenon/config.toml.
  • tenon config check also checks the hooks files.
  • The help text (tenon -h) now lists tenon agents and tenon hooks.

Install

brew install tenon-code-eu/tap/tenon
# or
curl -fsSL https://raw.githubusercontent.com/tenon-code-eu/tenon/main/install.sh | sh

Verify a manual download:

minisign -Vm SHA256SUMS -P RWR+vfCWjGO42uRKOxNSrKz5afZPCWJf8iJPO04kFdkhLldZHhxo532F
sha256sum -c SHA256SUMS --ignore-missing   # macOS: shasum -a 256 -c SHA256SUMS --ignore-missing

Version 0.x: configuration, options and session/audit formats may still change. License: EUPL-1.2.