Claude Code skills vs plugins vs subagents vs commands vs CLAUDE.md

Five ways to customize Claude Code, one decision rule. What each mechanism loads, when it loads, what it costs, and how skills now absorb commands and can fork into subagents. With a table for every combination.

Contents

Claude Code has accumulated five customization mechanisms, and the documentation for each is good in isolation. What is missing is the side-by-side: when a piece of guidance should be a CLAUDE.md section, a skill, a command, a subagent, or a plugin. Since custom commands merged into skills and skills gained the ability to fork into subagents, the boundaries have moved, and some older advice is now wrong.

This guide gives you the decision rule first, then the mechanics of each, then every pairwise comparison in one table.

The decision rule

Ask two questions about the content:

  1. Does the agent need it on every turn? If yes, it is a CLAUDE.md fact. If no, keep going.
  2. Is it a procedure, a persona, or a package? A procedure is a skill. A persona with its own context is a subagent. A package of several things for distribution is a plugin.

Commands are no longer a separate answer; they are skills you invoke by hand.

CLAUDE.md: always-on facts

CLAUDE.md at the project root (and ~/.claude/CLAUDE.md for personal defaults, and nested CLAUDE.md files in subfolders) is loaded into context at the start of every session and stays there. Everything in it costs tokens on every message.

That makes it the right place for facts and constraints:

  • “We use pnpm. Never run npm install.”
  • “Tests live next to source as *.test.ts.”
  • “Do not touch infra/ without asking.”
  • “The API returns errors in the { error: { code, message } } envelope.”

And the wrong place for procedures. The documentation’s own guidance: create a skill when a section of CLAUDE.md has grown into a procedure rather than a fact, because a skill’s body loads only when used, so long reference material costs almost nothing until you need it.

Skills: on-demand procedures and knowledge

A skill is a folder under .claude/skills/ (project) or ~/.claude/skills/ (personal) with a SKILL.md in the open Agent Skills format:

---
name: db-migration
description: "Creates a new database migration in this repo's conventions, runs it locally, and updates the schema snapshot. Use when asked to add, create, or write a migration."
disable-model-invocation: true
allowed-tools: Bash(pnpm db:*) Read Edit
---
## Steps
1. Run `pnpm db:new $ARGUMENTS` to scaffold the file.
2. Edit the up and down functions.
3. Run `pnpm db:migrate` and `pnpm db:snapshot`.
4. Show the diff. Do not commit.

How it loads: at startup only name and description are in context. When your request matches the description, or you type /db-migration add-users-table, the body enters the conversation as a single message and stays there for later turns. $ARGUMENTS receives what you typed after the name.

The frontmatter fields that matter for this comparison:

FieldWhat it does
disable-model-invocation: trueOnly you can run it. The description is not even shown to the model. Use for side effects.
user-invocable: falseOnly Claude can run it. Hidden from the / menu. Use for background knowledge.
allowed-toolsPre-approves tools for the turn that invokes the skill. Clears on your next message.
context: forkRuns the skill as a subagent (next section).
hooksRegisters hooks for the rest of the session when the skill is invoked.

Skills also load from nested .claude/skills/ folders once Claude touches a file in that subtree, from every parent directory up to the repo root, and from directories added with --add-dir. Edits to a SKILL.md are picked up live within the session.

Skills are the only mechanism on this list that is portable: the same file loads in Cursor, Codex, GitHub Copilot, and 60+ other agents. The compatibility matrix shows which Claude fields those agents ignore.

Commands: now a kind of skill

Custom slash commands were single Markdown files in .claude/commands/. They still work. But they have been merged into skills: .claude/commands/deploy.md and .claude/skills/deploy/SKILL.md both create /deploy and behave identically, and if both exist the skill wins.

What skills add over the old command files:

  • A folder for scripts/, references/, and assets/.
  • Frontmatter to control who invokes them.
  • Automatic loading when the task matches, unless you opt out with disable-model-invocation.

So the question “skill or command?” has one answer. Write a skill. If you want the old command behavior (you trigger it, Claude never does), set disable-model-invocation: true. The command name is the folder name.

Subagents: separate context, separate worker

A subagent is defined in .claude/agents/<name>.md with its own system prompt, tools, and optionally its own model. When Claude delegates to it, the subagent runs in a fresh context window, does the work, and returns a summary. Your main conversation never sees the intermediate noise.

Use a subagent when:

  • The task would flood your main context with exploratory output (searching a large codebase, reading twenty web pages).
  • You want several independent tasks running in parallel.
  • You want a persona with a restricted toolset (a reviewer that can read but not edit).

Skills and subagents connect in two directions:

Skill as subagent. Add context: fork to a skill’s frontmatter and the skill body becomes the prompt that drives a subagent of the type named in agent. By default it runs in the background; background: false waits for the result. The built-in Explore and Plan agent types skip CLAUDE.md to keep context small, so a forked skill using agent: Explore sees only the skill content and the agent’s own system prompt. This only makes sense for skills that contain a task, not guidelines; a forked skill full of “use these conventions” has nothing to do and returns empty.

Subagent that preloads skills. A custom subagent definition can list skills to load as reference material, the inverse arrangement.

The rule: a skill is what to do; a subagent is who does it and in what context.

Plugins: distribution

A plugin is a folder with .claude-plugin/plugin.json that bundles skills, agents, hooks, MCP server definitions, and output styles. Plugins install from marketplaces or a repo and are enabled per user or per project in settings.

Their skills load namespaced: my-plugin/skills/deploy/SKILL.md becomes /my-plugin:deploy and coexists with a project deploy skill. Any skill folder can become a plugin by adding .claude-plugin/plugin.json to it; in a project’s .claude/skills/ that requires accepting the workspace trust dialog first.

Choose a plugin when you are distributing a workflow to other people and it needs more than a skill: an MCP server the skill depends on, a hook that enforces something deterministically, or a subagent the skill forks into. If it is just a skill, publish the skill. Registries like SkillMD list single skills and multi-skill plugins side by side, with a safety review on each, and install either with one command or through the hosted MCP server:

claude mcp add skillmds -- npx -y skillmds

claude.ai-synced skills

A sixth source worth knowing: skills you enable on claude.ai sync into Claude Code. In Cowork and cloud sessions they are the only personal skills available, because those sessions do not read ~/.claude/skills/ on your machine. Locally, setting CLAUDE_CODE_SYNC_SKILLS in a non-interactive run downloads them to ~/.claude/skills/synced/. A project skill with the same name beats a synced skill.

The catch: claude.ai uploads accept only the six spec frontmatter fields (name, description, license, compatibility, metadata, allowed-tools) and reject Claude Code extras like context: fork with an error. A skill meant for both needs to be spec-clean.

Precedence when names collide

CollisionWinner
Personal ~/.claude/skills/deploy vs project .claude/skills/deployPersonal
Project code-review vs bundled /code-reviewProject (but the bundled alias /review never runs yours)
Plugin deploy vs project deployBoth: plugin is /my-plugin:deploy
.claude/commands/deploy.md vs .claude/skills/deploy/SKILL.mdSkill
claude.ai-synced deploy vs project deployProject
Root deploy vs nested apps/web/.claude/skills/deployBoth: nested is /apps/web:deploy

Every pairwise comparison

Loads whenContext costWho triggersPortableBest for
CLAUDE.mdSession start, alwaysEvery messageNobody; it is always thereNoFacts, constraints, conventions
SkillDescription match or /name~100 tokens idle; body when usedClaude or you (configurable)Yes, 60+ agentsProcedures, reference material, house style
Command (legacy)/nameBody when usedYouNoSuperseded by manual-only skills
SubagentWhen delegatedSeparate context windowClaude, or a forked skillNoIsolation, parallelism, restricted personas
PluginWhen enabledSum of its partsDepends on contentsNo (but its skills are)Distributing skills + hooks + MCP together
claude.ai synced skillSession start (cloud) or sync run (local)Same as a skillSame as a skillSpec-clean by requirementSkills that must follow you into cloud sessions

Worked example: one workflow, five mechanisms

Say your team has a release process.

  • CLAUDE.md gets one line: “Releases are cut from main with /release; never tag by hand.”
  • A release skill with disable-model-invocation: true holds the twelve-step procedure, with allowed-tools: Bash(pnpm release:*) so the scripted steps do not prompt.
  • A changelog skill with context: fork and agent: Explore reads every merged PR since the last tag and drafts notes, without dumping two hundred PR bodies into your main context.
  • A release-guard hook, registered from the release skill’s hooks field, blocks any git push --tags outside the skill’s turn.
  • A plugin bundles all of the above with your GitHub MCP server config so a new teammate installs the whole thing at once.

Each piece is doing the one job it is good at. Nothing is duplicated, nothing is always-on that does not need to be, and the two skills work in Cursor and Codex too, minus the Claude-specific forking and hooks.

Further reading

Frequently asked questions

What is the difference between a Claude Code skill and a slash command?

They have merged. A file at .claude/commands/deploy.md and a skill at .claude/skills/deploy/SKILL.md both create /deploy and behave the same way. Skills add a folder for supporting files, frontmatter to control who can invoke them, and automatic loading when the task matches. If both exist, the skill wins.

What is the difference between a skill and a subagent in Claude Code?

A skill is instructions injected into the current conversation. A subagent is a separate worker with its own context window and system prompt. A skill can become a subagent by setting context: fork in its frontmatter, which uses the SKILL.md content as the subagent's task.

What is a Claude Code plugin?

A distribution bundle. A plugin folder with .claude-plugin/plugin.json can ship skills, agents, hooks, and MCP server definitions together. Its skills appear namespaced as /plugin-name:skill-name and coexist with project skills of the same name.

When should something go in CLAUDE.md instead of a skill?

CLAUDE.md is always in context, so it should hold facts and constraints the agent needs on every turn: stack, conventions, safety rules. When a section grows into a multi-step procedure, move it to a skill, which costs nothing until it is used.

Do Claude Code skills work in other agents?

Yes, when they use spec fields. Skills follow the open Agent Skills format read by Cursor, Codex, GitHub Copilot, and 60+ others. Claude-specific frontmatter such as context: fork, hooks, and allowed-tools is ignored elsewhere. Plugins, subagents, and CLAUDE.md are Claude Code-only.