Hook Chain

Architecture Skills vs MCP vs mods vs everything else

Which extension point?

Claude Code has about ten ways to change how it behaves. They overlap, and the names don't make the difference obvious. The short version: text that teaches Claude goes in CLAUDE.md or a skill, new abilities come from MCP, a separate worker is a subagent, a script on an event is a settings hook, and code inside the loop is a mod. A plugin is the box they ship in.

A cutaway workshop like a dollhouse. Labelled rooms: a shelf of binders marked SKILLS, a wall of pinned notes marked CLAUDE.MD, a loading dock marked MCP where a delivery truck plugs in a cable, a shed outside marked SETTINGS HOOKS where a person with a clipboard answers a doorbell, an assembly line of robot helpers marked MODS, a side room of apprentice robots at desks marked SUBAGENTS, and a wooden crate at the front door marked PLUGIN holding all of them.
The same kitchen as the five-year-old's version, drawn as a building. Everything in the house can be packed into the crate at the door.

The whole map in one table

Extension pointWhat it isWho decides it runsWhat it can changeContext cost
CLAUDE.md (and AGENTS.md)Markdown instructions loaded into every conversationAlways onWhat Claude knows and tends to do. Advisory: Claude can still choose otherwise.Every request
SkillA folder with SKILL.md, plus optional scripts and referencesClaude, from the description, or you by nameWhat Claude knows and does for one kind of taskThe description always; the body when used
Custom slash commandA Markdown prompt you invoke as /nameYouThe prompt Claude receives. It still starts a Claude turn.When invoked
SubagentAn agent definition (agents/*.md) with its own prompt, tools and modelClaude delegates, or you askWho does a piece of work, in a fresh contextIts own context; the result comes back as text
Output styleA system-prompt variant for tone and formatYou pick itHow Claude writesEvery request
MCP serverAn external process or service that offers tools, resources and promptsClaude calls its toolsWhich tools Claude has: databases, APIs, browsersTool names; schemas load through tool search
Permission rulesallow, ask and deny patterns in settingsEvery tool callWhether a call runs, asks or is refused. Declarative, so it can't inspect content beyond the pattern.None
Settings hook ("classic")A shell command, HTTP call, prompt, agent or MCP tool run on a lifecycle event, JSON in and outThe eventBlock, allow or annotate a tool call or prompt. Rewrite a call's input or result. Add context.Only what it adds
Status lineA script whose output is shown under the promptEach redrawOne line of the screenNone
ModTS or JS functions running inside Claude Code, chained on 46 engine eventsThe eventTool calls, prompts, the system prompt, model requests, subagents, commands, compaction, stored rows, and what the interface drawsNone unless it adds text
PluginA package of any of the above, installed from a marketplaceYou install itWhatever it carriesThe sum of its parts

Two more sit outside the box: the Agent SDK, for running Claude Code inside your own program, and managed settings, which an organization uses to decide which of all the above may load.

Mods next to their neighbours

The four most often confused are mods, settings hooks, skills and MCP servers. This expands the official comparison:

ModSettings hookSkillMCP server
RunsIn Claude Code's process (a worker thread), loaded once, keeps stateSpawned per event: shell, HTTP, prompt, agent or MCP toolNot at all. Claude reads it.A separate process or remote service
Several at onceA sequential, ordered chain. Each one sees what the one before passed on.Run in parallel. The most restrictive decision wins. Input rewrites are last-writer-wins.Claude picksAll tools available
Can drawPanes, a band, restyled rows, spinner, dialogsNoNoNo
Adds commandsYes: code that runs with no Claude turn, even mid-turnNoYes: a prompt that starts a turnMCP prompts appear as commands
Adds toolsYes ($.tool.register), served by its own hookNoNo (it can tell Claude to run scripts)Yes, that's the point
Can fail openYes: a hook that throws or overruns is skipped unless it has .catchDepends on exit code and confign/aA failed tool is an error result
LanguageTypeScript or JavaScriptAnything that reads stdinMarkdownAnything
Reviewable before installclaude plugin validate lists hooks and callsRead the scriptRead the MarkdownRead the server

One job, five ways: "never run rm -rf"

The clearest way to feel the differences is to try the same job with each one and ask what it actually guarantees.

ApproachWhat it looks likeWhat it guarantees
CLAUDE.md"Never run rm -rf; ask me instead."Nothing. It's advice. Claude usually follows it, and a long session or an odd prompt can drift.
SkillA "safe cleanup" skill that explains alternativesNothing, and it only loads when the task looks like cleanup. The wrong tool for a prohibition.
Permission rule"deny": ["Bash(rm -rf:*)"]That pattern is refused. It's declarative and fast, and it misses rm -fr, rm -r -f and find … -delete.
Settings hookA PreToolUse script that parses the command and exits with a blockWhatever your script checks, in any language. It runs in parallel with other hooks and can't show UI. A managed one runs before any mod.
ModA tool.call guard with .catch, or one that holds the call and asks with $.ui.askWhatever your code checks, in a known order, with UI. It fails open without .catch. A worker crash loop unloads it.

In practice: the deny rule for the obvious spelling, a hook or mod for the rest, and a CLAUDE.md line so Claude doesn't try in the first place. Layers, not a winner.

Pick one

What do you need?

Tick everything that applies. The recommendation updates as you go.

Tick a box to see a recommendation.

Rules of thumb

  1. Start with text. If you keep pasting the same instructions, write a CLAUDE.md line (always relevant) or a skill (relevant to one kind of task). It's cheap, readable and easy to change.
  2. Need a new ability? MCP. If Claude must reach a system it can't reach today, that's a tool, and tools come from MCP servers. A mod can register a tool too, which is handy when the tool needs session state the mod already has.
  3. Need isolation? A subagent. A separate context for a big search or a review, possibly on a cheaper model. A mod can pin which model a subagent uses (agent.spawn) or hide an agent type (agent.offer).
  4. Need a guarantee? Rules first, then hooks or mods. Permission rules for patterns. A settings hook if you already have the script, or if you need it to run before any mod (managed). A mod if you need order, state, UI or to rewrite the event.
  5. Need to draw, or to run code on a command with no Claude turn? Only a mod can.
  6. Shipping several? A plugin. One install can bring a skill, an MCP server, a subagent and a mod that work together.

Where a decision model fits

Our sister site, Decision Tier, studies decision models: fast, typed judgments such as "is this command destructive?" with a probability attached. A decision model is a callee, not an extension point. In Decision Tier's words, mods and hooks call decision models; skills and CLAUDE.md teach Claude when to trust them.