The building blocks

An agent like Claude Code is extended with three kinds of thing that sound related but do very different jobs - skills, MCP connections, and hooks - plus plugins, which bundle them for sharing. Get them straight and the whole extension model clicks; blur them together and you will reach for the wrong one.

The short version:

  • Skills are instructions, not code - files that teach the model how to do a task. The model reads and follows them.
  • MCP connections are live links to external tools and data. This is how the model actually reads and writes things beyond itself.
  • Hooks are automated guardrails that run outside the model's judgment - a script that fires every time at a fixed point, whatever the model decides.
  • Plugins bundle the other three (and optionally agents) into one installable unit - how a whole team gets the same setup in a single command.

The one distinction that matters most runs underneath the first three: skills and MCP are things the model chooses to use; hooks run whether it chooses to or not. Plugins sit on top - not a fourth kind of capability, but the package that ships the other three together. Keep those lines in mind and the rest follows.

Skills - the know-how

Skills are instruction files that teach the model how to do a specific task - "retrieve and validate a data extract," "write a release note in our house style," "triage an incoming bug." They are instructions, not running code: the model reads them and follows them, the same way a new hire reads a runbook.

A skill is a folder whose entry point is a SKILL.md file. Frontmatter describes what the skill is for and when to load it; the body is plain-language guidance the model consults on demand, when the task in front of it matches.

MARKDOWN skills/build-report/SKILL.md
--- description: Retrieve, validate, and summarise a data extract into a review-ready report. Use when asked to build the monthly report. --- 1. Pull the latest extract from the data source. 2. Validate: missing rows, out-of-range values, duplicates. 3. Summarise the findings and flag anomalies for review.

Because a skill is just a folder of text (plus any reference material), it is portable and version-controlled - the smallest unit at which "how we do this" travels across projects and teammates. What a skill never does is reach outside the model on its own; for that, it leans on the next block.

MCP - the live connection

Model Context Protocol connections are live links to external tools and data - a database, a document store, an issue tracker, a filesystem. This is how the model actually reads and writes data outside itself. A skill can say "pull the latest extract"; an MCP connection is what makes that pull real.

You point the agent at MCP servers with a small config. Each server exposes tools (functions the model can call), and the model decides when to call them.

JSON .mcp.json
{ "mcpServers": { "database": { "command": "db-mcp", "args": ["--readonly"] }, "docs": { "command": "docstore-mcp" } } }

The key point: MCP is the standardized way to expose and call the outside world, but it is still the model that chooses to reach for it, turn by turn. Like a skill, it is discretionary - the model uses it when the task calls for it. That discretion is exactly what the third block exists to constrain. For the full picture of MCP, and how it relates to plain function calling, see Functions, MCP, and Skills.

Hooks - the guardrails

Hooks are automated guardrails that run outside the model's judgment. They fire at fixed points - before or after a tool runs - and execute a script every time, regardless of what the model decides. Where skills guide and MCP connects, hooks enforce.

Typical uses are exactly the things you never want left to a model's discretion: stop after a set number of retries, force a human review step before a risky action, run a linter on every file the agent edits, block a write to a protected path.

JSON hooks/hooks.json
{ "hooks": { "PreToolUse": [ { "matcher": "Bash", "hooks": [{ "type": "command", "command": "./guard/retry-cap.sh" }] } ], "PostToolUse": [ { "matcher": "Write|Edit", "hooks": [{ "type": "command", "command": "./guard/require-review.sh" }] } ] } }

A hook is ordinary code - a script that receives context on standard input and can allow, block, or annotate the action. Because it runs deterministically, it is the right home for policy: the rules that must hold no matter how the model reasons on a given turn.

The line that separates them

The three blur together until you sort them on one axis: does the model decide, or does the rule?

  Skills MCP Hooks
What it is Instructions the model reads Live links to tools and data Scripts at fixed points
Made of Text (a folder) Config + a running server Code (a script)
Who decides The model (reads when relevant) The model (calls when needed) The rule (runs every time)
Answers How do I do this? How do I reach that system? What must always happen?
Good for Workflows, house style Databases, trackers, files Safety, policy, compliance

Skills and MCP are discretionary - the model reaches for them when the task fits. Hooks are deterministic - they run on schedule at their trigger point, model or no model. That is the whole distinction, and it is why hooks are where safety and compliance live: you never want "stop after ten retries" to depend on the model remembering to.

A worked example

Picture a reporting agent that builds a monthly summary. All three blocks show up, each doing its own job:

  • Skill - a build-report folder holds the runbook: pull the extract, validate it, summarise, flag anomalies. It is how the agent knows the shape of the work.
  • MCP - two connections make the work real: one to the database the extract comes from, one to the document store the report lands in. Without them the skill is just prose.
  • Hooks - two guardrails keep it safe: a PreToolUse hook stops the run after ten failed attempts, and a PostToolUse hook forces a human review step before the finished report is published.

Change the workflow and only the skill changes. Swap the database and only the MCP config changes. Tighten the policy and only the hook changes. Each block moves on its own schedule - which is exactly why they are separate.

When to reach for which

  • Reach for a skill when you keep pasting the same instructions, examples, or house style into prompts - that workflow is portable enough to live in a folder.
  • Reach for MCP when the model needs to touch a real system - read a table, open a ticket, write a file - especially when more than one agent or host needs the same connection.
  • Reach for a hook when something must happen every time, no exceptions - a safety check, an approval gate, a lint pass, a hard limit. If it cannot be left to the model's judgment, it belongs in a hook.

Plugins - the bundle

On their own, each block is useful. Bundled, they become a capability you can hand to a whole team in one step - which is exactly what a Claude Code plugin is: a package of skills, MCP connections, and hooks (and optionally agents) installed as a single unit. The reporting agent above, wrapped as a plugin, gives every teammate the same runbook, the same connections, and the same guardrails at once.

So the mental model is layered: skills tell the agent how, MCP lets it reach the systems, and hooks decide what must always hold. Keep the "who decides" line clear - model for the first two, the rule for the third - and you will always know which block a given problem belongs in.