Skip to content
Agentmart
Submit a tool

call-behaviorist

Use when ai-badger's own machinery needs to be observed — "did that hook even run?", "enable debug logging", "why is the drift notice silent?", "turn on the…

Skill by Arasz

IndexedMIT★ 3
Write a review

Install

Works with Claude Code, Claude apps, Codex, Cursor, Gemini CLI, GitHub Copilot, VS Code, OpenCode, Goose, Windsurf. Read the repository before you give any tool access to your data.

npx agentmarket install skill/arasz-call-behaviorist

Asks which of your tools to add it to (Claude Code, Codex, Cursor, VS Code, Windsurf, Gemini CLI, Claude Desktop) and shows the change first. See https://agentmart.dev/cli.

Get the weekly diff

The weekly diff: one email a week with new agent tools, notable updates and grade changes, plus security alerts for tools you follow. Double opt-in, one-click unsubscribe.

We use your email only for this newsletter. Privacy

About

Use when ai-badger's own machinery needs to be observed — "did that hook even run?", "enable debug logging", "why is the drift notice silent?", "turn on the audit log", "what did the hooks do?" — or to check, tail, or switch off that logging. Records which hook ran, in which project, under which version, to an append-only log.

Use cases: security

No reviews yet. Installed it? Reviews come from verified installers only. How reviews work

Permissions

What this skill can do and what it asks for, from its SKILL.md and code. Checked Oct 26, 2026.

Tools
No tools found
Secrets
None asked for
Install scripts
None found
Runs as
Python package

Network hosts it talks to 1

  • codeload.github.com · found in install command

Files it touches

  • ~/.claude/skills/call-behaviorist
  • Your home directory (~)
  • ~/.ai-badger
  • ~/.ai-badger/ai-badger.db
  • ~/.hermes/plugins/ai-badger/.ai-badger

What's inside

Skill name
call-behaviorist
Description
Use when ai-badger's own machinery needs to be observed — "did that hook even run?", "enable debug logging", "why is the drift notice silent?", "turn on the audit log", "what did the hooks do?" — or to check, tail, or switch off that logging. Records which hook ran, in which project, under which version, to an append-only log.
License
MIT
Instructions
188 lines in SKILL.md · view on GitHub

Before installing

  • Ships executable scripts

Files (6)

  • SKILL.md
  • findings.md · references/
  • record-format.md · references/
  • badger_store.py · scripts/
  • behaviorist.py · scripts/
  • debug_log.py · scripts/

SKILL.md (first lines)

# call-behaviorist

Named for observing behaviour rather than asserting it. ai-badger is normally silent about its
own machinery, so "did that hook fire?" has no answer short of adding print statements and
re-scaffolding. This turns the machinery's own behaviour into a record.

**Off by default.** Nothing is written, and no directory is created, until you switch it on.

## Commands

All via `python3 .ai-badger/skills/call-behaviorist/scripts/behaviorist.py`:

| Command | Effect |
|---|---|
| `on [DURATION]` | Enable for **every project** (default 4h). Grammar: `4h`, `90m`, `1h30m`, or a bare number of hours — capped at 24h. `forever` (or `never`/`always`) means no expiry: on until `off`. |
| `on [DURATION] --project` | Enable for the current directory only |
| `off` | Disable |
| `status` | Mode, scope, expiry, record count |
| `tail [N]` | Last N records, one line each (default 20) |
| `analyze [--project DIR] [--json]` | Health state and findings for a project |
| `clear` | Truncate the log, recording the truncation |

`AI_BADGER_DEBUG=1` in the environment forces logging on regardless of stored state, for a
one-off run where editing state is inconvenient.

## What a record holds

`tail` renders records readably:

```
2026-07-27T09:22:56+00:00  ai_badger_hooks/session_start  skip  v0.30.0  project=/repo scaffold_version=0.30.0 framework_version=0.30.0
```

> Field-by-field record and event semantics: read references/record-format.md when interpreting `tail` or `analyze` output.

- **`version` is on every record** — it is the VERSION of the *copy of the code that ran*. This
  is what makes a stale plugin running against a newer scaffold visible rather than something
  you have to deduce.
- `event` distinguishes `start` from `skip`, so a hook that fired and exited early is
  distinguishable from one that never fired. That distinction is the whole point.
- `project` is recorded whenever it can be determined.

No tool input or file content is ever recorded. The one exception is the MCP-retrieval `query`
field below, which is recorded by default and has its own opt-out — see "Retrieval telemetry".

## Retrieval telemetry

The MCP tool index's retrieval path (`_find_relevant_tools` / `_extract_query_tags`, consumed by
`pre_llm_inject_context`) and its post-call tool-index check both log under the
`ai_badger_hooks/mcp_retrieval` component:

### The query field, and redacting it

`q` is the one field carrying user content — indispensable for diagnosing a miss or turning a
record into an eval fixture, and the one thing someone may not want recorded. It is recorded by
default. Setting `AI_BADGER_DEBUG_REDACT` in the environment drops that field only from every
record written afterward, leaving every other field intact so the log stays useful for counting.
The drop happens inside `debug_log.log_event` itself, at the point of writing — a redacted
record never contains the text, so there is nothing to scrub after the fact.

## Where things live

| Store | Purpose |
|---|---|
| `hook_state` KV in `~/.ai-badger/debug/audit.db` | Whether logging is on, its scope and expiry |
| `hook_audit` table in the same DB | The records, one JSON payload per row |

The audit DB is user-level and `0600` — the log says where you work and what ran, so it never
lands in a project directory or in git. `AI_BADGER_DEBUG_DIR` moves the whole sink. Records
older than 60 days are pruned, so disk stays bounded whatever the duration.

## Reading the log

`tail [N]` is for a quick look. For anything more, each `hook_audit` payload is one JSON
object:

```bash
python3 .ai-badger/skills/call-behaviorist/scripts/behaviorist.py tail 20
sqlite3 ~/.ai-badger/debug/audit.db "SELECT payload FROM hook_audit ORDER BY id DESC LIMIT 20"
```

The `sqlite3` query is the useful one when several copies of ai-badger are installed: it shows
which version each component actually ran at.

## Producing a health report

`analyze` compares what a project **registers** against what was **observed**, and hands you
findings rather than a verdict. Run it with `--json` and write the report yourself.

```bash
python3 .ai-badger/skills/call-behaviorist/scripts/behaviorist.py analyze --json
```

### Where the expected components come from

Hooks run from what is **registered** with the agent, so that is what is audited — in order,
`.claude/settings.json`, `.claude/settings.local.json`, then `.ai-badger/hooks/hooks.json`.
The last is ai-badger's own declaration and the only project-level record in a deployment that
registers hooks elsewhere (Hermes, Copilot), so it never stops counting. A script registered in
more than one of them is one component.

Components are named by their **project-relative path**, not their filename: several skills
ship a `user_prompt_hook.py`, and merging them lets one hook's silence hide behind another's
excuse. A hook ai-badger did not wire is still listed — someone else's hook is information, and
it lands in `not_instrumented` because it cannot report on itself. A hook whose command runs no
`.py` script (an installed binary, a shell one-liner) has nothing to inspect and is not listed.

> Finding meanings and health verdict rules: read references/findings.md when interpreting `analyze` output.

### What the log says about a *skill*

`hook_activity(project)` (a library call, not a subcommand) rolls the same records up per skill,
for the reader deciding what to prune: `{skill: {hooks, instrumented, records}}` over the
hook-shipping skills only, plus the project's total record count. den-refresh consumes it
(#172). The asymmetry is the point — records prove a skill is doing work here, and silence
proves nothing at all, because a skill that wires no hook can never appear in this log. Anything
built on it must never read absence as disuse.

**A record that names no project belongs to no project.** The log is user-wide, and a hook that

From Arasz/ai-badger, MIT.

More from Arasz/ai-badger

Signals

Stars
3
Forks
0
Open issues
9
Last commit (this folder)
Oct 18, 2026 (11 days ago)

From GitHub (fetched Oct 24, 2026).

Details

License
MIT
First seen
Oct 24, 2026
Last checked
Oct 24, 2026

More from Arasz

Cite this page

call-behaviorist skill. Agent Mart. https://agentmart.dev/skills/arasz-call-behaviorist (last updated 2026-10-24)