You need Claude to run tests before every commit. Where do you put that rule?
Option A: Add "Always run tests before committing" to your CLAUDE.md. Option B: Create a skill called /pre-commit that runs the test suite. Option C: Write a hook that fires on the PreCommit event and actually executes npm test. Option D: Build an MCP server that... no, that doesn't make sense here. Right?
If you've spent more than five minutes trying to figure out where things go in Claude's extension system, you're not alone. Between CLAUDE.md, Skills, Hooks, MCP Servers, Connectors, Claude Apps, and Plugins, there are seven different mechanisms for extending Claude's behavior. Some of them sound similar. Some have overlapping capabilities. And the documentation, while thorough, doesn't always make it obvious when to reach for which.
Here's the answer to the test question, by the way: Option C. A Hook. Because running tests before a commit isn't a suggestion — it's a requirement. And that distinction between "should" and "must" is the key to understanding the entire extension stack.
This is Part 1 of a four-part series on Claude's extension ecosystem. We'll build the mental model here, then go deep on each mechanism in Part 2 (CLAUDE.md, Hooks, Skills), Part 3 (MCP Servers, Connectors, Claude Apps), and Part 4 (composing a real production stack).
The 7 extension points at a glance
Seven mechanisms, seven different jobs. Three shape how Claude thinks (CLAUDE.md, Skills, Hooks). Three expand what Claude can access (MCP Servers, Connectors, Claude Apps). One bundles them together (Plugins). Here's the full landscape.
| # | Extension Point | What It Does | Where It Lives | When It Runs |
|---|---|---|---|---|
| 1 | CLAUDE.md | Project conventions, coding standards, architectural context | .claude/ directory in your repo | Every conversation (always loaded) |
| 2 | Skills | Procedural workflows — step-by-step playbooks Claude can invoke | .claude/commands/ as markdown files | On demand (when Claude decides to, or when you invoke /skill-name) |
| 3 | Hooks | Shell scripts that fire on specific events | .claude/hooks/ or settings.json | Deterministically, on every matching event |
| 4 | MCP Servers | External tool connections — APIs, databases, custom tooling | claude_desktop_config.json or .mcp.json | When Claude calls a tool the server provides |
| 5 | Connectors | Managed MCP integrations with built-in auth for SaaS tools | Claude.ai settings | When Claude needs data from a connected service |
| 6 | Claude Apps | Connectors + interactive UI rendered inside the conversation | Claude.ai via MCP Apps extension | When a tool returns UI components alongside data |
| 7 | Plugins | Shareable bundles of skills, hooks, MCP configs, and commands | Installable packages (like npm for Claude) | When installed, their contents activate per their own type |
Seven mechanisms. It looks like a lot. But here's the thing: they aren't seven competing approaches to the same problem. They're organized along two clear axes, and once you see those axes, the whole system snaps into focus.
Why does it matter whether a rule is deterministic or probabilistic?
Because that single distinction resolves 80% of the confusion about where things should go. Deterministic means it always happens, no exceptions. Probabilistic means Claude uses judgment about when and how to apply it. If you internalize nothing else from this article, internalize this.
Deterministic means the mechanism runs regardless of what Claude decides. It doesn't matter if Claude is confused, distracted by a complex prompt, or in the middle of a 50-step workflow. The mechanism fires. Every time.
Probabilistic means Claude reads the instruction and uses judgment about how to apply it. Most of the time it follows through. But context length, competing instructions, ambiguous situations, and sheer complexity can cause it to skip or misapply a rule.
Here's how the seven extension points break down:
Here's what this means in practice:
Hooks are deterministic. When you configure a PreCommit hook, it runs before every commit. Claude doesn't decide whether to run it. The system executes the shell script, checks the exit code, and blocks the commit if it fails. Claude could be in the middle of writing a sonnet — the hook still fires.
MCP Servers are deterministic in execution. Once Claude decides to call an MCP tool, the server executes deterministically. The tool runs, returns a result, and that result enters Claude's context. There's no "oh, I'll skip the API call this time." However, whether Claude decides to call the tool is probabilistic — it depends on Claude's judgment about whether the tool is relevant.
CLAUDE.md is probabilistic. Claude reads your project rules and genuinely tries to follow them. But CLAUDE.md competes with everything else in the context window: the user's prompt, conversation history, tool results, and the system prompt. With ~150-200 instructions being the practical ceiling for reliable adherence, a 500-line CLAUDE.md means rules near the bottom get less attention than rules near the top.
Skills are probabilistic with an opt-in shortcut. When Claude loads a skill, it follows the procedure. But Claude decides when to load a skill based on what seems relevant. You can force it with /skill-name, which is why slash commands exist — they bypass Claude's judgment and say "load this, now."
This isn't a flaw. It's a design. You want Claude to use judgment about when to apply a coding convention or which workflow to follow. You don't want Claude using judgment about whether to run your security checks.
What's the difference between "brain" and "nervous system" extensions?
Three extension points shape how Claude thinks (its knowledge, procedures, and guardrails). Three others expand what Claude can reach (databases, APIs, SaaS tools). Plugins span both. Knowing which half your problem falls in narrows seven choices down to three.
The Internal Brain (CLAUDE.md + Skills + Hooks) controls Claude's behavior within your project:
- CLAUDE.md is foundational knowledge: "This is a NestJS monorepo. We use pnpm. We never use
doc.save()— alwaysfindByIdAndUpdate()." It's the project wiki that Claude internalizes. - Skills are procedural knowledge: "When deploying to staging, first run the test suite, then build the Docker image, then push to Fly.io, then verify the health endpoint." They're runbooks that Claude can execute step by step.
- Hooks are behavioral guardrails: "Before any commit, run lint. After any file edit, check for secrets. Before any destructive command, require confirmation." They're the safety nets that catch mistakes regardless of what Claude is thinking.
The External Nervous System (MCP Servers + Connectors + Claude Apps) extends Claude's reach into the outside world:
- MCP Servers are custom connections you build: a server that queries your production database, an integration with your internal deployment pipeline, a bridge to your company's proprietary API.
- Connectors are turnkey connections Anthropic maintains: Jira, Notion, Salesforce, GitHub, Slack — 200+ integrations with managed authentication.
- Claude Apps are Connectors with a visual layer: when a Figma connector returns a design, Claude Apps render it as an interactive preview inside the conversation instead of dumping JSON.
The mental shortcut: if your question is "How should Claude behave?" the answer is in the Brain (CLAUDE.md, Skills, Hooks). If your question is "What should Claude access?" the answer is in the Nervous System (MCP, Connectors, Apps).
Most real-world setups need both halves working together. A deployment skill (Brain) calls your CI/CD MCP server (Nervous System). A code review hook (Brain) checks against a linting MCP tool (Nervous System). The Brain knows the procedures and rules; the Nervous System provides the tools and data.
Which extension point should you use?
Ask three questions in order: Must it never be violated? (Hook.) Does it teach a multi-step procedure? (Skill.) Does it need external data? (MCP or Connector.) Everything else is CLAUDE.md. Here's the full decision tree.
Some real examples:
"Never commit without running tests" — Must never be violated? Yes. Hook. Configure a PreCommit hook that runs your test suite. If the tests fail (non-zero exit), the commit is blocked. Claude doesn't get a vote.
"When I say /deploy, run the staging deployment pipeline" — Multi-step procedure? Yes. Skill. Write a markdown skill that outlines each step: run tests, build image, deploy to Fly.io, verify health, post to Slack. Claude follows the steps in order.
"We use NestJS with MongoDB, never use doc.save()" — Sets project conventions? Yes. CLAUDE.md. This is foundational context that Claude should always know. It influences every code generation decision without needing a specific trigger. (If you're curious about the broader challenge of managing prompt-level instructions for AI agents, that article covers the techniques that apply here too.)
"Look up customer data from our Postgres database" — Needs external data access? Yes. Custom system? Yes. MCP Server. Build a server that exposes a query_customer tool, and Claude can call it whenever relevant. (Our guide on building your own agent tool system walks through this pattern end to end.)
"Pull the latest Jira tickets for my sprint" — Needs external data? Yes. Common SaaS tool? Yes. Connector. Jira has a managed connector in Claude.ai. One-click setup, Anthropic handles the auth.
"Show me the Figma design for this component and let me annotate it" — Interactive UI? Yes. Claude App. The Figma integration renders designs as interactive previews, not just JSON payloads.
"Share our team's deployment workflow with other teams" — Distributing a combination of skills, hooks, and MCP configs? Plugin. Package it up so other teams can install it in one command.
What does each extension point actually look like?
Each mechanism maps to a specific file or configuration you can see, edit, and version control. Here's the structure for all seven — enough to get oriented before we go deep in Parts 2 and 3.
CLAUDE.md
Your project's root-level instruction file. Claude reads it at the start of every conversation:
# CLAUDE.md
## Project: acme-platform
- Tech stack: NestJS + MongoDB + pnpm workspaces
- Port: 3100
- All workflows go through Makefile targets
## Hard Rules
- NEVER use doc.save() — always findByIdAndUpdate()
- NEVER push to main — always create a PR
- All API responses wrap in { success, data }
## Architecture
- services/ contains microservices
- packages/ contains shared libraries
- apps/ contains frontend applicationsKeep it focused. The ~150 instruction ceiling is real. Everything in CLAUDE.md competes for the same attention budget — the same challenge teams face with prompt management at scale.
Skills
Markdown files in .claude/commands/ that Claude can invoke:
.claude/
commands/
deploy.md # /deploy — staging deployment procedure
review.md # /review — code review workflow
test.md # /test — run tests with coverageA skill file looks like this:
# Deploy to Staging
Run the following steps in order:
1. Run the full test suite: `make test-all`
2. If tests fail, stop and report failures
3. Build the Docker image: `make docker-build`
4. Deploy to staging: `make deploy-staging`
5. Wait 30 seconds, then check health: `make health-check-staging`
6. Post results to #deploys channelEach skill costs 30-50 tokens to load. They're lightweight by design — you can have dozens of them without impacting performance. Claude loads them on demand, which is the critical difference from CLAUDE.md (always loaded).
Hooks
Shell scripts that fire on specific lifecycle events:
{
"hooks": {
"PreCommit": [
{
"command": "npm test",
"description": "Run tests before commit",
"blocking": true
}
],
"PreToolCall": [
{
"command": ".claude/hooks/check-file-permissions.sh",
"description": "Block edits to protected files",
"blocking": true
}
],
"PostToolCall": [
{
"command": ".claude/hooks/log-tool-usage.sh",
"description": "Audit trail for tool calls",
"blocking": false
}
]
}
}The hook script receives event context via stdin and environment variables. A non-zero exit code blocks the action (if blocking: true). This is the only mechanism that gives you programmatic enforcement — not a polite suggestion, but a hard stop.
MCP Servers
A configuration pointing Claude at your custom tool server:
{
"mcpServers": {
"acme-db": {
"command": "node",
"args": ["./mcp-servers/database/index.js"],
"env": {
"DATABASE_URL": "postgresql://..."
}
},
"deploy-tools": {
"url": "https://mcp.internal.acme.com/deploy",
"headers": {
"Authorization": "Bearer ${DEPLOY_TOKEN}"
}
}
}
}The MCP server exposes tools that Claude discovers at runtime through the Model Context Protocol. Local servers run via stdio, remote servers connect over Streamable HTTP. If you've built an MCP server before (we have a full tutorial in this series), this configuration is all it takes to wire it into Claude.
Connectors and Claude Apps
Connectors are configured through the Claude.ai interface — no code required. You authenticate once, and Claude can access the service:
Jira, Notion, Salesforce, GitHub, Slack, Linear, Asana — over 200 integrations available. Connectors use the MCP protocol under the hood, but Anthropic manages the server, the auth, and the updates.
Claude Apps extend connectors with interactive UI. When a Figma connector returns a design, Claude Apps render it as something you can view, annotate, and interact with inside the conversation window. These launched in January 2026 as the MCP Apps extension to the protocol.
Plugins
Plugins bundle multiple extension types into a shareable, installable package:
my-team-plugin/
skills/
deploy.md
review.md
hooks/
pre-commit.sh
mcp/
config.json
manifest.jsonThink of plugins as npm packages for Claude configuration. Instead of telling every new developer to "copy these five files into your .claude/ directory," you publish a plugin they can install in one command. The plugin's manifest declares which skills, hooks, and MCP configs it provides.
What are the most common setup mistakes?
Every mistake below comes from misunderstanding the deterministic/probabilistic line. The number one offender: putting safety rules in CLAUDE.md instead of Hooks. Once you internalize the mental model above, these become obvious — but almost everyone hits at least one.
Mistake 1: safety rules in CLAUDE.md
The problem: You add "NEVER push to main" or "ALWAYS run tests before commit" to CLAUDE.md. Claude follows it 90% of the time. The other 10% — usually during a complex, multi-step operation when context is full — it pushes directly to main.
Why it happens: CLAUDE.md is probabilistic. Claude genuinely tries to follow every instruction, but attention is finite. Safety-critical rules buried among 200 other instructions don't get 100% compliance.
The fix: Move hard safety rules to Hooks. A PreCommit hook that checks the branch name and rejects commits to main fires every single time. A PreToolCall hook that blocks git push when the target is main is absolute. Use CLAUDE.md for conventions, Hooks for enforcement.
Mistake 2: building MCP Servers for internal procedures
The problem: Someone builds an MCP server with a run_deployment tool because they want Claude to follow a deployment procedure. The server becomes a wrapper around shell scripts that Claude could run directly.
Why it happens: MCP servers are exciting, and "give Claude a tool" feels like the right abstraction. But if the tool is just "run these shell commands in order," you've added a network hop, a server to maintain, and a protocol layer for no benefit.
The fix: Use a Skill. A deploy skill that walks Claude through make test && make build && make deploy is simpler, cheaper, and easier to maintain. Save MCP servers for external system access — databases, APIs, third-party services — where you need Claude to reach outside its own machine.
Mistake 3: overloading CLAUDE.md
The problem: CLAUDE.md grows to 500+ lines. It includes coding standards, architectural decisions, deployment procedures, API documentation, team conventions, and a section on how to make coffee. Claude starts quietly dropping rules from the bottom of the file.
Why it happens: CLAUDE.md is the first extension mechanism developers discover. It's easy to edit. Everything feels important. So everything goes in.
The fix: CLAUDE.md is for foundational project context — the stuff Claude needs in every conversation. Move procedural knowledge to Skills (on-demand loading, 30-50 tokens each). Move enforcement rules to Hooks. Move reference documentation to files Claude can read when needed. A lean, focused CLAUDE.md of 50-100 lines is more effective than a sprawling 500-line encyclopedia.
Mistake 4: Connectors where MCP Servers belong (and vice versa)
The problem: A team tries to use a Connector for their custom internal API, or builds a full MCP server to integrate with Jira.
Why it happens: The MCP/Connector boundary isn't immediately obvious. Both connect Claude to external services. Both use the MCP protocol.
The fix: Simple heuristic: if Anthropic already maintains a connector for the service (Jira, GitHub, Slack, Notion, etc.), use the Connector. It has managed auth, automatic updates, and zero maintenance. If it's your own internal system, database, or proprietary API, build an MCP server. The effort of building a server is justified by the customization you need.
Mistake 5: skipping Hooks entirely
The problem: A team uses only CLAUDE.md and Skills. They have no Hooks. Claude occasionally edits files it shouldn't, makes commits without running tests, or calls dangerous commands without confirmation.
Why it happens: Hooks require writing shell scripts and understanding the event lifecycle. It's the least discoverable mechanism. Many developers don't realize Hooks exist until they've been bitten by a probabilistic rule failure.
The fix: Start with three hooks that cover the most common risks: a PreCommit hook that runs lint and tests, a PreToolCall hook that blocks writes to protected files (production configs, migration files, vendored code), and a PostToolCall hook that logs file edits for audit. You can add more as you discover new failure modes, but these three catch the majority of problems.
How do these extensions compose together?
You don't pick one mechanism — you layer them. CLAUDE.md is the foundation, Skills add procedures, Hooks add guardrails, MCP adds external reach, and Connectors plug in SaaS. Each layer handles what it's best at. Start small and add layers as your project grows.
Layer 1: CLAUDE.md (Foundation)
Start here. Every project needs foundational context: tech stack, project structure, coding conventions, key architectural decisions. This is the minimum viable Claude configuration. It costs nothing to maintain and gives Claude the context it needs to be useful from conversation one.
Layer 2: Skills (Procedures)
Once Claude knows your project, teach it your workflows. Deployment procedures, PR review checklists, testing patterns, data migration steps. Skills are cheap (30-50 tokens each, loaded on demand) and powerful — they turn Claude from a code assistant into a workflow partner.
Layer 3: Hooks (Guardrails)
After you've caught Claude making a mistake you never want repeated — pushing to main, editing a production config, committing without tests — add a Hook. Hooks are reactive: you add them when you discover a failure mode. Start with the big three (pre-commit testing, file protection, dangerous command blocking) and grow from there.
Layer 4: MCP Servers (External Reach)
When Claude needs to access systems outside your codebase — databases, APIs, monitoring dashboards, deployment pipelines — build an MCP server. Each server is a focused integration point. At Chanl, our agents connect to customer databases, knowledge bases, and external APIs through MCP — the same protocol Claude Code uses.
Layer 5: Connectors and Apps (SaaS Ecosystem)
For standard SaaS tools, plug in a Connector instead of building from scratch. When you need visual interaction (design tools, dashboards, document editors), Claude Apps bridge the gap between data and UI.
The beauty of this layering is that you don't need to set up everything on day one. Start with CLAUDE.md. Add skills as you document workflows. Add hooks when something goes wrong. Add MCP servers when you need external data. The system grows organically with your needs. (If you're building multi-agent systems, each agent can have its own extension stack — orchestrator agents with different CLAUDE.md files, hooks, and MCP connections than the specialist agents they coordinate.)
A Real .claude/ Directory
Here's what a production Claude Code setup looks like. This isn't theoretical — it's a simplified version of what we use at Chanl for our platform backend:
.claude/
CLAUDE.md # Project conventions (~80 lines)
settings.json # Hook configurations
commands/ # Skills (slash commands)
deploy.md # /deploy — staging/prod pipeline
review.md # /review — PR review workflow
plan.md # /plan — TDD session planning
commit.md # /commit — review + commit + push
test.md # /test — run use case tests
rules/ # Scoped rules (load based on file globs)
backend-services.md # Loads when editing services/**/*.ts
frontend-apps.md # Loads when editing apps/**/*.tsx
sdk-cli.md # Loads when editing packages/sdk/**
api-contracts.md # Loads when editing *.controller.ts
deploy-infra.md # Loads when editing Dockerfile, fly.toml
hooks/
pre-commit.sh # Runs lint + tests
check-permissions.sh # Blocks edits to protected files
log-edits.sh # Audit trail for file changes
.mcp.json # MCP server configurationsNotice the scoped rules in .claude/rules/. These are a feature of CLAUDE.md that addresses the "too many instructions" problem. Instead of cramming 400 lines of rules into the root CLAUDE.md, you split them into topic-specific files with globs: frontmatter. Backend rules only load when you're editing backend files. Frontend rules only load when you're editing components. This keeps each conversation's instruction count manageable while still giving Claude deep context for whatever area you're working in.
What's coming in parts 2, 3, and 4
This article gave you the mental model. The next three go deep on each mechanism with real code, real configurations, and production patterns.
Part 2: CLAUDE.md, Hooks, and Skills — Claude's Internal Brain covers the three mechanisms that shape Claude's behavior. You'll learn how to structure CLAUDE.md for maximum retention, write hooks that catch real failure modes, and build skills that encode complex workflows. We'll look at scoped rules, hook event types, and the difference between team-level and project-level configuration.
Part 3: MCP Servers, Connectors, and Claude Apps — The External Nervous System dives into external integrations. We'll build an MCP server from scratch, walk through Connector setup, and explore Claude Apps with interactive UI. If you've read our MCP tutorial, Part 3 picks up where it left off — focusing on how MCP fits into the broader extension ecosystem rather than the protocol itself.
Part 4: Composing a Production Stack is the payoff. We'll walk through a real-world setup — a team building production AI agents — and show how CLAUDE.md, Skills, Hooks, MCP Servers, and Plugins compose into a system that handles everything from code generation to deployment to monitoring. This is where the mental model from Part 1 meets real engineering.
The extension ecosystem is growing fast. MCP moved to the Linux Foundation. Connectors passed 200 integrations. Claude Apps launched in January 2026. Plugins are making configurations shareable across teams. The foundation you build now — understanding which mechanism handles which job — will pay off as new capabilities arrive.
Start with CLAUDE.md. Add skills for your first workflow. Add a hook the first time something goes wrong. Build from there. The layering strategy means you're never locked in — you're always adding capability on top of a solid foundation.
Build AI agents that actually work
Chanl gives your agents tools, knowledge, and memory — then tests them before customers do.
Get started freeCo-founder
Building the platform for AI agents at Chanl — tools, testing, and observability for customer experience.
Learn Agentic AI
One lesson a week — practical techniques for building, testing, and shipping AI agents. From prompt engineering to production monitoring. Learn by doing.



