You probably have already run npx skills add. One line, no configuration, nothing to learn and all you need is Node, and it works across seventy-five-plus agents.
The install path is the most finished thing in the agent tooling ecosystem right now. The removal path is the least and you may need to intervene manually.
A skill is smaller than you think
An agent skill is a folder with a SKILL.md file in it. Markdown instructions, YAML frontmatter, a name, a description. That is pretty much it. No runtime, no manifest format, no registration step. A valid folder in the right place simply is a skill, and the agent picks it up on the next run.
Which is why the ecosystem moved this fast. The barrier to publishing one is a README file, simple!

The install path, properly walked
To use skills the prerequisite is Node. There is no global install of the tool itself, because it is designed to run through npx every time.
Find it. npx skills find searches the public directory at skills.sh, with a keyword if you have one. Worth doing even when you already know which repo you want.
Trial it. npx skills use owner/repo@skill-name resolves the source exactly as an install would, writes the files to a temporary directory, and prints the generated prompt to stdout. Pipe it into your agent, or pass --agent claude-code to launch one interactively. Nothing touches your project. This is the most underused command in the tool and the one that will save you the most grief.
Install it. npx skills add <source>, where source is owner/repo shorthand, a full GitHub or GitLab URL, a raw git URL, a link to a single skill inside a repo, or a local path. Four flags carry most of the weight:
-a, --agentnames the target, so-a claude-code -a codexinstalls to both.-g, --globalwrites to your home directory rather than your project. Project is the default.-s, --skilltakes one skill from a repo instead of all of them. Pair it with--listto see what is in there first.-y, --yesskips every prompt, which is what you want in CI.
When the installer asks whether to symlink or copy, take the symlink. It puts one canonical copy in .agents/skills/ and points each agent’s directory at it, so an update lands everywhere at once. Remember that answer, because it matters again shortly.
npx skills list reports what is on disk. npx skills update re-resolves installed skills against their sources. And if the CLI behaves in a way the documentation does not describe, npx has served you a cached older build: pin it with npx skills@latest.
That is a very good tool. It took package manager ergonomics and gave them to agent tooling on day one, without the fifteen years of arguments it took npm to get there.
A description is never free
Inside SKILL.md there is a split: the body only loads when the skill triggers, but the description is read on every single turn, because that is how the agent decides whether this thing is relevant to what you just asked for.
So a skill you never use is not dormant. It is a small, permanent charge against the attention budget of every request you make. Fifty of them is not a library. It is a Tribble problem: individually harmless, collectively a hull breach.
Which makes removal a performance feature rather than housekeeping. And removal is where this comes apart.
The warning: deleting the folder does not remove the skill
The CLI does not just move files around. It keeps a lockfile, and almost nobody looks at it.
Project-scope installs write skills-lock.json to your project root, at schema version one. Global installs write .skill-lock.json into a dot-agents folder in your home directory, at schema version three. Note what is absent from both of those paths: anything resembling .claude. Go hunting for this state next to your agent’s own configuration and you will not find it. So you may conclude there isn’t any, and move on. That would be most likely be wrong.
Each entry records the source, the source type, the skill path and a content hash. That file powers skills update, and it is what npx skills experimental_install replays when a colleague clones your repo. Let’s just stop there for a sec: installing is a polished one-liner with a directory site behind it, while restoring what you installed still ships with the word experimental in it, and at the time of writing it reads the project lockfile only. Nobody hid that asymmetry. It is right there in the command surface.
So here is what happens when you reach for the obvious shortcut: Install a skill into a project. Delete the folder by hand with rm -rf. The agent stops seeing it immediately, which feels like success. Run skills list and it reports no project skills found, which feels like confirmation.
However, the lockfile still contains the entire entry. Source, path, hash, intact.
And if you took the symlink option at install, as recommended, you have not deleted the skill at all. You have deleted a pointer to it. The canonical copy is still sitting in .agents/skills/, and any other agent still linked to it is still reading that description on every turn.
So you have a skill with no presence where you looked, a live copy where you did not, and a persistent record inside the tool that installed it. The CLI will not show you any of that, because it reports what exists rather than what it has promised to restore. Anyone running a restore from that lockfile gets the skill back on a machine that never asked for it, with no idea why it appeared.
Use npx skills remove instead, and use it retroactively on anything you have already deleted by hand. Removing an already-deleted skill reports that it found zero installed skills and then that it successfully removed one. That reads as a contradiction and is precisely right: nothing where it looked, one entry in the ledger, both now handled.
Deletion is a blunt instrument, and reaching for it first is usually a category error. Plenty of skills are useful but noisy, and the main problem with them is not that they exist but that they keep volunteering.
Claude Code has a lighter mechanism in its own settings for exactly that: a skillOverrides block where you set a skill to off, or to name-only, so it stays in your menu while being withheld from the model. Same skill, different exposure.
One thing to remember is that the lockfile asks what did I install and from where. Settings asks what am I allowed to see and use. SKILL.md asks what should the agent actually do. Conflating the first two is how people end up deleting a skill they only needed to mute.
One thing you can do is, and unfortunately it is a manual step is to clean the lock file. Say you wanted to get clear all the entries for google-agents-cli you can do this as follows:
cd ~/.agents
cp .skill-lock.json .skill-lock.json.bak
jq '.skills |= with_entries(select(.key | startswith("google-agents-cli-") | not))' \
.skill-lock.json > .skill-lock.tmp && mv .skill-lock.tmp .skill-lock.json
Bear in mind that you are manually changing a file, so handle it with care. This issue is not a reason to avoid the tool. It is a reason to treat a skill library the way you would treat a dependency tree, which is to say with a pruning habit rather than a collecting habit.
Every mature package ecosystem eventually grew a removal story, an audit story and a pruning story, and every one of them grew it late, after the pain arrived. Agent skills are at that stage now, and you can watch it happening in a command name. The difference is that a bloated dependency tree costs you disk, which is cheap. A bloated skill library costs you the model’s attention on every turn, which is the one budget you cannot buy more of.
In systems where attention is the budget, curation is the capability.
RogueLoop. Where AI meets real-world innovation.