{"slug": "show-hn-shook-a-hook-for-asd-simplified-english", "title": "Show HN: SHOOK - A Hook for ASD Simplified English", "summary": "Viktorinkov released SHOOK, a plugin that enforces ASD-STE100 Simplified Technical English across every Claude Code reply, with hooks that load rules at session start, remind on each prompt, and lint-gate failed replies for rewrite. The plugin, which requires the AminBlg/SimpleEnglish plugin, adds a /ste command and a status line badge showing [STE] or [STE:STRICT x.x], and also supports Codex CLI and Antigravity CLI.", "body_md": "**SHOOK, a Simple English hook. Claude picks the replies that get the Simple English skill. Most replies never qualify.This plugin applies it to every reply.**\n\nThree Claude Code hooks that make [AminBlg/SimpleEnglish](https://github.com/AminBlg/SimpleEnglish) always on:\n\nthe rules at session start, a reminder on every prompt, and a lint gate that sends a failed reply back for a rewrite.\n\nThe status line shows the mode the whole time: `[STE]`\n\nor `[STE:STRICT x.x]`\n\n.\n\nThis plugin is a companion to ** AminBlg/SimpleEnglish**, the simple-english plugin. That plugin brings ASD-STE100 Simplified Technical English to Claude Code and other agents. It is a prerequisite. The full rule set and the linter\n\n`ste_lint.py`\n\ncome from it at run time. This plugin adds the hooks, the `/ste`\n\ncommand, and the status line badge.Quick start (Claude Code) Installs both [Simple English](https://github.com/AminBlg/SimpleEnglish) and its Shook integration plugin:\n\n```\nclaude plugin marketplace add AminBlg/SimpleEnglish && claude plugin install simple-english@simple-english && claude plugin marketplace add viktorinkov/shook && claude plugin install simple-english-hook@simple-english-hook\n```\n\nThen start a new session and type `/ste strict`\n\n. For the status line badge:\n\n- Ask Claude: Install the STE status line badge.\n- Or install manually:\n**Run the script from the plugin cache.**\n\n```\nbash \"$(ls -d ~/.claude/plugins/cache/simple-english-hook/simple-english-hook/*/ | tail -1)statusline-install.sh\"\n```\n\nThe status line then shows `[STE]`\n\nor `[STE:STRICT x.x]`\n\nthe whole time.\n\n**Claude Code**\n\n**1. Prerequisite**\n\nInstall the [simple-english plugin](https://github.com/AminBlg/SimpleEnglish#-install). The rules and the linter come from it.\n\n```\nclaude plugin marketplace add AminBlg/SimpleEnglish\nclaude plugin install simple-english@simple-english\n```\n\n**2. Install SHOOK**\n\n```\nclaude plugin marketplace add viktorinkov/shook\nclaude plugin install simple-english-hook@simple-english-hook\n```\n\n**3. Enable**\n\nStart a new session and type the mode.\n\n```\n/ste strict\n```\n\nToggle: `/ste on`\n\n, `/ste strict`\n\n, `/ste off`\n\n, or `/ste status`\n\n.\n\nStatus line badge (optional):\n\n- Ask Claude: Install the STE status line badge.\n- Or install manually: Run the script from the plugin cache.\n\n```\nbash \"$(ls -d ~/.claude/plugins/cache/simple-english-hook/simple-english-hook/*/ | tail -1)statusline-install.sh\"\n```\n\nThe script adds one line to your status line script. If you have no status line script, it creates one. The badge shows `[STE]`\n\nin `on`\n\nmode and `[STE:STRICT x.x]`\n\nin `strict`\n\nmode.\n\n**Codex CLI**\n\n**1. Prerequisite**\n\nCodex does not install the [simple-english plugin](https://github.com/AminBlg/SimpleEnglish#-install). Clone it and point `STE_PLUGIN_DIR`\n\nat the clone. Put the `export`\n\nline in your shell profile.\n\n```\ngit clone https://github.com/AminBlg/SimpleEnglish ~/SimpleEnglish\nexport STE_PLUGIN_DIR=~/SimpleEnglish\n```\n\n**2. Install SHOOK**\n\n```\ncodex plugin marketplace add viktorinkov/shook\ncodex plugin add simple-english-hook@simple-english-hook\n```\n\n**3. Enable**\n\nStart Codex in a project. At the first start, Codex asks you to review the hooks. Choose `Review hooks`\n\nand trust the `simple-english-hook`\n\nentry in each event. The `/hooks`\n\npanel shows the same list at any time. Then type the mode. The `$`\n\nopens the Codex skill picker.\n\n```\n$ste strict\n```\n\nToggle: `$ste on`\n\n, `$ste strict`\n\n, `$ste off`\n\n, or `$ste status`\n\n.\n\n- Works:\n`on`\n\nand`strict`\n\n. The rules load at session start, each prompt gets the reminder, and the Stop hook sends a failed reply back once. - Does not work: the status line badge. Codex has no status line. The mode shows as a system message at session start and after each toggle.\n\nSee [Codex CLI](/viktorinkov/shook/blob/main/docs/other-harnesses.md#codex-cli) in the harness docs.\n\n**Antigravity CLI**\n\n**1. Prerequisite**\n\nAntigravity does not install the [simple-english plugin](https://github.com/AminBlg/SimpleEnglish#-install). Clone it and point `STE_PLUGIN_DIR`\n\nat the clone. Put the `export`\n\nline in your shell profile.\n\n```\ngit clone https://github.com/AminBlg/SimpleEnglish ~/SimpleEnglish\nexport STE_PLUGIN_DIR=~/SimpleEnglish\n```\n\n**2. Install SHOOK**\n\nThe command also takes the path of a local clone.\n\n```\nagy plugin install https://github.com/viktorinkov/shook\n```\n\n**3. Enable**\n\nStart a new `agy`\n\nsession and type the mode.\n\n```\n/ste strict\n```\n\nToggle: `/ste on`\n\n, `/ste strict`\n\n, `/ste off`\n\n, or `/ste status`\n\n.\n\n- Works:\n`on`\n\nand`strict`\n\n. The rules load at session start, each model call gets the reminder, and the Stop hook lints the reply from the transcript. - Does not work: the badge. In print mode (\n`agy -p`\n\n) outside a project, the hooks do not read the per-repo file. Use the global flag or`STE_MODE`\n\n.\n\nSee [Antigravity CLI](/viktorinkov/shook/blob/main/docs/other-harnesses.md#antigravity-cli) in the harness docs.\n\n**Copilot CLI**\n\n**1. Prerequisite**\n\nCopilot does not install the [simple-english plugin](https://github.com/AminBlg/SimpleEnglish#-install). Clone it and point `STE_PLUGIN_DIR`\n\nat the clone. Put the `export`\n\nline in your shell profile.\n\n```\ngit clone https://github.com/AminBlg/SimpleEnglish ~/SimpleEnglish\nexport STE_PLUGIN_DIR=~/SimpleEnglish\n```\n\n**2. Install SHOOK**\n\n```\ncopilot plugin marketplace add viktorinkov/shook\ncopilot plugin install simple-english-hook@simple-english-hook\n```\n\n**3. Enable**\n\nStart a new Copilot session and type the mode. The new mode applies at the next session start.\n\n```\n/simple-english-hook:ste on\n```\n\nToggle: `/simple-english-hook:ste on`\n\nor `/simple-english-hook:ste off`\n\n. To set the mode for one session, start Copilot with `STE_MODE=on copilot`\n\n.\n\n- Works:\n`on`\n\n. The rules load at session start. - Does not work: the reminder on each prompt,\n`strict`\n\n, and the badge. Copilot sends no reply text to its stop hook, so the hooks treat`strict`\n\nas`on`\n\n.\n\nSee [GitHub Copilot CLI](/viktorinkov/shook/blob/main/docs/other-harnesses.md#github-copilot-cli) in the harness docs.\n\n**Cursor**\n\n**1. Prerequisite**\n\nCursor does not install the [simple-english plugin](https://github.com/AminBlg/SimpleEnglish#-install). Clone it and point `STE_PLUGIN_DIR`\n\nat the clone. Put the `export`\n\nline in your shell profile.\n\n```\ngit clone https://github.com/AminBlg/SimpleEnglish ~/SimpleEnglish\nexport STE_PLUGIN_DIR=~/SimpleEnglish\n```\n\n**2. Install SHOOK**\n\nClone this repo. The hooks run from the clone, so keep it.\n\n```\ngit clone https://github.com/viktorinkov/shook ~/shook\n```\n\n**3. Enable**\n\nRun the install script in your project with a mode. It writes the rule file and the hooks into the project.\n\n```\ncd <your-project>\nbash ~/shook/cursor-install.sh strict\n```\n\nToggle: `/ste on`\n\n, `/ste strict`\n\n, `/ste off`\n\n, or `/ste status`\n\nin the Agent chat. Or run `bash ~/shook/cursor-install.sh <mode>`\n\nfrom the shell.\n\n- Works:\n`on`\n\nand`strict`\n\n. The rule file applies the rules to every request, and the`stop`\n\nhook sends a failed reply back once. - Does not work: the badge, a reminder injected on each prompt, an\n`ste`\n\nskill, and cloud agents. The always-on rule file replaces the reminder.\n\nDetails: [Cursor](/viktorinkov/shook/blob/main/docs/other-harnesses.md#cursor) in the harness docs.\n\n| Command | What it does |\n|---|---|\n`/ste on` |\nLoads the rules at session start and adds the reminder on every prompt. |\n`/ste strict` |\nSame as `on` , plus the lint gate on every reply. |\n`/ste off` |\nStops the hooks. |\n`/ste status` |\nShows the current mode and its source. |\n`/ste project <mode>` |\nSets `on` , `strict` , or `off` for the current repo only. `/ste project clear` removes it. |\n`/ste config` |\nShows every lint gate setting, its value, and its source. |\n`/ste set <key> <value>` |\nWrites a lint gate setting. See\n|\n\n`/ste uninstall`\n\nThe commands above are the Claude Code spelling. Each block in [Installation](#-installation) gives the spelling for its harness.\n\nThe hooks enforce the mode, so the badge is how you see that the mode is on and how strict it is.\n\n| Badge | Meaning |\n|---|---|\n`[STE]` |\nMode `on` . |\n`[STE:STRICT x.x]` |\nMode `strict` . `x.x` is the lint score of the last reply: rule violations per 100 words. Lower is better. |\n| nothing | Mode `off` . |\n\n- Ask Claude: Install the STE status line badge.\n- Or install manually: Run\n`statusline-install.sh`\n\nfrom this plugin's folder.\n\nThe hooks run in every repo. The **mode** decides what they do. The mode has three scopes.\n\n| Scope | How to set it | Where it lives |\n|---|---|---|\n| Global | `/ste on` , `/ste strict` , `/ste off` |\n`~/.claude/.simple-english-active` |\n| One repo | `/ste project on` , `/ste project strict` , `/ste project off` , `/ste project clear` |\n`<repo>/.claude/ste-mode` |\n| Fixed | `STE_MODE=strict` in the environment, or `\"env\": {\"STE_MODE\": \"strict\"}` in `<repo>/.claude/settings.json` |\nenvironment |\n\nOrder of precedence: environment, then the repo file, then the global flag, then off. Each harness keeps its own global flag. The repo file and `STE_MODE`\n\napply to all harnesses.\n\nTo use it in a team repo, type `/ste project strict`\n\nand commit `.claude/ste-mode`\n\n. Each team member installs both plugins once.\n\nThis plugin only changes how often the rules apply, so the comparison that matters is the simple-english skill alone against the hook. The benchmark runs on several Claude models in Claude Code and on GPT models in Codex CLI.\n\nThe benchmark sends the same 50 writing prompts (docs, code reviews, error messages, commit messages, incident reports, runbooks) through each arm, one run per prompt. The simple-english plugin's own linter, `ste_lint.py`\n\n, counts the rule violations in every reply. Method, full tables, and all raw replies: [ evals/results/RESULTS.md](/viktorinkov/shook/blob/main/evals/results/RESULTS.md).\n\n`v/100w`\n\nis the linter's count of rule violations per 100 words, so lower is better.\n\n| Model | n prompts | skill alone (v/100w) | hook on (v/100w) | hook strict (v/100w) | reduction (strict vs skill) |\n|---|---|---|---|---|---|\n`claude-fable-5` (claude) |\n50 | 2.41 | 0.51 | 0.22 | 91% |\n`claude-opus-5` (claude) |\n50 | 2.68 | 0.41 | 0.45 | 83% |\n`claude-sonnet-5` (claude) |\n50 | 2.38 | 0.47 | 0.32 | 87% |\n`claude-haiku-4-5-20251001` (claude) |\n50 | 2.74 | 0.97 | 0.71 | 74% |\n`gpt-5.6-sol` (codex) |\n50 | 0.94 | 0.59 | 0.34 | 64% |\n`gpt-5.4-mini` (codex) |\n50 | 1.66 | 0.51 | 0.63 | 62% |\n\nThe per-model table for Claude Fable 5 shows the three-row shape:\n\n| Arm | Skill fired | Violations / 100 words | Replies with 0 violations | Output tokens per reply |\n|---|---|---|---|---|\n| skill | 27/50 | 2.41 | 10% | 1224 |\n| hook-on | 19/50 | 0.51 | 38% | 1020 |\n| hook-strict | 20/50 | 0.22 | 60% | 1361 |\n\nHow to read it: Claude alone decides whether the skill fires. On Fable 5, it fired in 27 of 50 replies. The hook applies the rules on every reply. Strict mode adds the gate, blocked 6 of 50 replies on Fable 5, and cut the violations by 91%.\n\nRead the tables with care. The linter is a regex pass. It undercounts and it cannot judge meaning. The numbers compare arms against each other. They are not a compliance score. No tool can certify ASD-STE100 compliance.\n\nReproduce: `python3 evals/bench.py`\n\nfor Claude Code, and `python3 evals/codex_bench.py`\n\nfor Codex.\n\n| Hook | Event | Action |\n|---|---|---|\n`SessionStart` |\nNew session, resume, clear, compact | Loads the full rule set from the simple-english plugin as context. |\n`UserPromptSubmit` |\nEvery prompt | Adds a 74-word STE reminder. Handles `/ste` commands. |\n`Stop` |\nEnd of every reply, `strict` mode only |\nRuns the simple-english linter `ste_lint.py` on the reply. If the reply fails, Claude must rewrite it once. |\n| Status line (optional) | Always | Shows `[STE]` in `on` mode, or `[STE:STRICT x.x]` with the last lint score in `strict` mode. Shows nothing in `off` mode. |\n\nIn strict mode, a failed reply goes back to Claude with a message like this one from the benchmark:\n\n```\nSTE LINT FAILED (8 violations in 234 words, 3.42 per 100 words; longest sentence 35 words).\nFound: sentence_over_limit=2, contraction=4, trailing_condition=2. Rewrite your whole last reply ...\n```\n\nClaude rewrites the reply once per turn.\n\nThe reminder on every prompt is the part that an output style cannot do. A system prompt is read once. A reminder sits next to the newest message, every turn.\n\nWhen all three conditions are true, the gate blocks a reply:\n\n- The reply has at least\n`min-words`\n\nwords. - The reply has at least\n`min-total`\n\nviolations. - The density is above\n`max-per-100w`\n\nviolations per 100 words.\n\nA tight gate makes Claude rewrite short, correct replies. A loose gate lets slop through. The gate runs at most one rewrite per turn.\n\n| Key | What it sets | Default | Env variable |\n|---|---|---|---|\n`min-words` |\nShortest reply the gate checks, in words. | 40 | `STE_MIN_WORDS` |\n`min-total` |\nFewest violations that can block a reply. | 2 | `STE_MIN_TOTAL` |\n`max-per-100w` |\nHighest violation density the gate allows, per 100 words. | 1.0 | `STE_MAX_PER_100W` |\n`lint-type` |\nRule set the linter uses: `descriptive` or `procedural` . |\n`descriptive` |\n`STE_LINT_TYPE` |\n\nUse the env variables for CI and scripts.\n\n| Command | What it does |\n|---|---|\n`/ste config` |\nShows every setting, its value, and its source (env, project, global, default). |\n`/ste set <key> <value>` |\nWrites the global setting. |\n`/ste project set <key> <value>` |\nWrites the setting for the current repo. |\n`/ste unset <key>` , `/ste project unset <key>` |\nRemoves one setting. |\n\nThe gate reads each key from the first place that has it:\n\n- Env variable\n- Repo file:\n`<repo>/.claude/ste-config.json`\n\n. Safe to commit. - Global file:\n`~/.claude/simple-english-hook.json`\n\n- Default\n\n- Code blocks, identifiers, file paths, CLI commands, and quoted error messages. The rules and the linter skip them.\n- Code that Claude writes. The rules apply to prose only.\n- Marketing copy or brand voice that you ask for.\n- Any repo with\n`/ste project off`\n\n. Any session with`/ste off`\n\n.\n\nSTE is flat by design. Use it for docs, reviews, runbooks, error messages, and explanations. Turn it off for a blog post.\n\n**Why not just call the skill?** You can. A call applies the rules to that one reply. The next reply forgets them. Left to itself, the skill fired in 27 of 50 replies on Fable 5. This plugin runs every turn and needs no call.\n\n**Why not the simple-english output style?** The output style is a good one-shot. It has no reminder per turn and no gate.\n\n```\nclaude plugin marketplace update simple-english-hook\nclaude plugin update simple-english-hook@simple-english-hook\n```\n\n- Type\n`/ste uninstall`\n\n. It removes the status line badge, the state files, and the mode and config files in the current repo. - Run\n`claude plugin uninstall simple-english-hook@simple-english-hook`\n\n.\n\nIf other repos have a `.claude/ste-mode`\n\nor `.claude/ste-config.json`\n\nfile, delete those by hand. To remove the [simple-english plugin](https://github.com/AminBlg/SimpleEnglish) too, follow the steps in its README. For Codex, Antigravity, Copilot, and Cursor, see the uninstall steps in [docs/other-harnesses.md](/viktorinkov/shook/blob/main/docs/other-harnesses.md).\n\nMIT. Not affiliated with ASD or STEMG. ASD-STE100 is a registered trademark of ASD.", "url": "https://wpnews.pro/news/show-hn-shook-a-hook-for-asd-simplified-english", "canonical_source": "https://github.com/viktorinkov/shook", "published_at": "2026-08-29 16:22:36+00:00", "updated_at": "2026-08-29 16:48:54.371763+00:00", "lang": "en", "topics": ["developer-tools", "ai-tools"], "entities": ["Viktorinkov", "SHOOK", "AminBlg/SimpleEnglish", "Claude Code", "Codex CLI", "Antigravity CLI", "ASD-STE100"], "alternates": {"html": "https://wpnews.pro/news/show-hn-shook-a-hook-for-asd-simplified-english", "markdown": "https://wpnews.pro/news/show-hn-shook-a-hook-for-asd-simplified-english.md", "text": "https://wpnews.pro/news/show-hn-shook-a-hook-for-asd-simplified-english.txt", "jsonld": "https://wpnews.pro/news/show-hn-shook-a-hook-for-asd-simplified-english.jsonld"}}