Skip to content
Development
Hook

Hooks

What no-numb runs automatically, and when. A hook is a command Claude Code fires at a fixed moment, without you asking for it.

From plugin
no-numb
331 skill1 hook

Claude Code

> /plugin marketplace add Ciucky/no-numb
> /plugin install no-numb@no-numb

What fires, and when

Stop

  • ${CLAUDE_PLUGIN_ROOT}/hooks/gate.sh
Read hooks/hooks.json

Where it lives

  • hooks/gate.shRunsGitHub
    Read the script
    #!/usr/bin/env bash
    #
    # no-numb gate — runs on the Claude Code Stop hook.
    #
    # Job: a "doorbell," nothing more. Did Claude edit a file this run, and have we
    # not already quizzed for it? If so, block the stop and tell Claude to run the
    # quiz-me skill. ALL judgement (what/whether/how to quiz) lives in the skill.
    #
    # Requires: jq.  See SPEC.md §5.3 for the design and the stop_hook_active trap.
    
    input="$(cat)"
    
    # Helper: read a field from the hook's stdin JSON. Falls back to empty on error.
    field() { printf '%s' "$input" | jq -r "$1" 2>/dev/null; }
    
    # 1) Already quizzed this cycle → let Claude stop.
    #    When we block, the quiz runs as a CONTINUATION of the same run, so the
    #    edits are still "this run" when Claude tries to stop again. Without this
    #    guard the hook would re-block forever (pass quiz → re-quiz → forever).
    #    Claude Code sets stop_hook_active=true on that continuation.
    [ "$(field '.stop_hook_active // false')" = "true" ] && exit 0
    
    # 2) Ensure the config exists with defaults — created once, on first run. It
    #    lives in the home dir (not the plugin cache, which is wiped on update) so
    #    it's a stable, discoverable, editable location.
    config="${HOME}/.no-numb/config.json"
    if [ ! -f "$config" ]; then
      mkdir -p "${HOME}/.no-numb" 2>/dev/null \
        && printf '{\n  "enabled": true,\n  "depth": "standard"\n}\n' > "$config" 2>/dev/null || true
    fi
    
    # 3) Off switch. Test `.enabled == false` explicitly — jq's `//` treats false as
    #    "use default", so `.enabled // true` would wrongly read false back as true.
    #    Missing/unreadable config or key → enabled (default on).
    if [ "$(jq -r '.enabled == false' "$config" 2>/dev/null)" = "true" ]; then
      exit 0
    fi
    
    # 4) Doorbell: did Claude Edit/Write/MultiEdit/NotebookEdit any file since the
    #    user's last prompt (i.e. during this run)? No transcript → fail open (no
    #    quiz), because trapping the user on a parse error is worse than missing one.
    transcript="$(field '.transcript_path // empty')"
    [ -n "$transcript" ] && [ -f "$transcript" ] || exit 0
    
    edited="$(jq -s '
      # Content can be nested as .message.content (common) or .content; handle both.
      def blocks: (.message.content // .content // []);
    
      # A genuine user prompt: a user line carrying real text (string content, or an
      # array with a text block) — as opposed to a user line that is only tool_result.
      def is_prompt:
        .type == "user"
        and (
          ((blocks | type) == "string" and (blocks | length) > 0)
          or ((blocks | type) == "array" and (blocks | any(.[]?; .type == "text")))
        );
    
      # An assistant turn that edited a file.
      def is_edit:
        .type == "assistant"
        and (blocks | type) == "array"
        and (blocks | any(.[]?;
              .type == "tool_use"
              and (.name == "Edit" or .name == "Write"
                   or .name == "MultiEdit" or .name == "NotebookEdit")));
    
      . as $arr
      | (([ range(0; ($arr | length)) | select($arr[.] | is_prompt) ] | last) // -1) as $start
      | [ $arr[($start + 1):][] | select(is_edit) ] | length > 0
    ' "$transcript" 2>/dev/null || echo false)"
    
    if [ "$edited" = "true" ]; then
      jq -n '{
        decision: "block",
        reason: ("You edited files this turn. Before finishing, run the no-numb quiz-me skill: "
          + "quiz the user with multiple-choice questions via AskUserQuestion (honoring the depth "
          + "in ~/.no-numb/config.json) on what you just did, and do not end your turn until they pass. "
          + "If the change was genuinely cosmetic (formatting, a rename, a color, a typo), say so in "
          + "one line instead of quizzing.")
      }'
    fi
    
    exit 0
    

Read the script before you install anything that runs on your machine. This is the one part of a plugin that acts without being asked.

Stats
33
Stars
0
Forks
Maintained
Maintenance
Shell
Language
Last commit
Created

Repo: Ciucky/no-numb

@ciucky
Ships withno-numb

Build with Claude Code without your brain going numb. No-Numb quizzes you on the code Claude just wrote — and, by default, blocks the session from continuing until you pass. The middle ground: built fast like an agent, understood like you wrote it yourself.

Stars on GitHub

Momentum

stars in total
33
Star history of Ciucky/no-numb on GitHub, a chart by star-history.com

More plugins that ship hooks.

superpowers

superpowers

A development methodology for coding agents that makes the agent brainstorm before building, follow plans, run parallel work and finish branches in a disciplined way. You get fewer skipped steps and more consistent results from your coding assistant.

15 skills1 hook318k
@obra@obra
Install Plugin
ponytail

ponytail

A Claude Code plugin with skills for auditing a whole repo, reviewing a change, listing deferred shortcut comments, and showing measured savings and a quick command reference.

6 skills10 hooks191k
@dietrichgebert@dietrichgebert
Install Plugin
agent-skills

agent-skills

Walks a software change from a written spec through design, testing, code review, CI/CD, and release, applying the matching engineering skill at each stage. Useful for developers using Claude Code on full development workflows.

25 skills+3117k
@addyosmani@addyosmani
Install Plugin
planning-with-files

planning-with-files

Persistent file-based planning for AI coding agents on long-running, multi-step tasks. It keeps task_plan.md, findings.md and progress.md on disk, so work can resume after /clear or context compaction.

6 skills+228k
@othmanadi@othmanadi
Install Plugin
gsd-core

gsd-core

A spec-driven development workflow for Claude Code that guides a project through planning, phases, milestone audits and fixes. Includes skills to generate tests from UAT criteria and to audit completed work.

72 skills+312k
@open-gsd@open-gsd
Install Plugin
superpowers-zh

superpowers-zh

Chinese-language skill pack for Claude Code that adds workflow guidance for brainstorming, TDD, debugging, and code review, plus Chinese conventions for commits, documentation, and domestic Git platforms like Gitee and Coding.net.

21 skills1 hook8.5k
@jnmetacode@jnmetacode
Install Plugin
socraticode

socraticode

Gives Claude Code semantic search, dependency graph and architecture context over a codebase, so an AI assistant can explore and understand a project's code. Includes skills for indexing a project and managing its file watching.

2 skills+33.4k
@giancarloerra@giancarloerra
Install Plugin
cocoindex-code

cocoindex-code

A lightweight code search engine that uses AST-based semantic search with local embeddings and incremental indexing. It helps Claude Code users find code faster and more efficiently.

1 skill1 MCP+13k
@cocoindex-io@cocoindex-io
Install Plugin

Questions about the hooks in no-numb.

Which coding agents can use the hooks in no-numb?
The hooks in no-numb install in Claude Code and Cursor: each runs Claude Code hooks from .claude/settings.json, so copy the hooks there.