mirror of
https://github.com/mattpocock/skills.git
synced 2026-07-29 02:52:42 +07:00
Add a Claude Code plugin marketplace so the promoted skills can be installed as a managed, read-only bundle (subscribe rather than fork), alongside the existing skills.sh installer. - Enrich .claude-plugin/plugin.json with marketplace metadata (version, description, author, license, keywords); keep the curated promoted-only skills array. - Add .claude-plugin/marketplace.json making the repo its own single-plugin marketplace (mattpocock-skills@mattpocock). - README: document /plugin install alongside skills.sh, and the subscribe-vs-fork tradeoff. - CLAUDE.md: extend the promoted-set invariant to cover marketplace.json and plugin.json/package.json version sync. - ADR 0002: record why Claude ships now and a native Codex plugin is deferred (Codex skills field is single-path + drops symlinks, which can't express a curated subset of a bucketed repo without a restructure). Verified: 'claude plugin validate . --strict' passes, and marketplace add -> install resolves all 21 promoted skills at v1.2.0. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
29 lines
3.8 KiB
Markdown
29 lines
3.8 KiB
Markdown
# Ship the skill set as a native Claude Code plugin; defer a native Codex plugin
|
|
|
|
These skills have always been installable via [skills.sh](https://skills.sh/mattpocock/skills) (`npx skills add mattpocock/skills`), which copies editable skill files into a user's project across Claude Code, Codex, and other Agent-Skills-standard harnesses. A recurring request is a **plug-and-play** distribution: subscribe to the set as a read-only, always-current bundle you don't edit, rather than a fork you own. That is exactly what native plugin systems provide.
|
|
|
|
We ship a native **Claude Code plugin** and, for now, **defer** a native **Codex plugin**. The split is forced by how each ecosystem's plugin manifest selects skills, against this repo's bucketed layout.
|
|
|
|
## The constraint: bucketed skills vs. single-path selection
|
|
|
|
Skills live in bucket folders under `skills/` — `engineering/` and `productivity/` are **promoted** (shipped); `misc/`, `personal/`, `in-progress/`, and `deprecated/` are **not**. A plugin must expose only the promoted set, which spans two of those bucket folders.
|
|
|
|
- **Claude Code** — `.claude-plugin/plugin.json` accepts `skills` as an **array of explicit skill-directory paths**. We list the promoted skills one by one, exclude everything else with zero ambiguity, and add `.claude-plugin/marketplace.json` so the repo is its own single-plugin marketplace. Verified end to end: `claude plugin validate . --strict` passes, and `marketplace add` → `install` resolves all promoted skills.
|
|
|
|
- **Codex** — `.codex-plugin/plugin.json` accepts `skills` only as a **single path string** (arrays are rejected with `missing or invalid plugin.json`), and Codex discovers `SKILL.md` files recursively under it. There is no way to name two bucket folders, or to curate a subset, from one path. Two escape hatches were tested and rejected:
|
|
- Pointing at `./skills/` would also ship `deprecated/`, `in-progress/`, `personal/`, and `misc/` — retired, draft, and personal skills we deliberately don't promote.
|
|
- A curated flat directory of **symlinks** into the buckets does not survive install: Codex copies the plugin tree into its cache and **drops symlinks**, so the skills arrive empty.
|
|
|
|
The only robust ways to give Codex a single promoted-only path are (a) **restructure** so `skills/` contains only promoted skills (moving the non-promoted buckets out — a large blast radius across `CLAUDE.md`, `scripts/link-skills.sh`, the bucket READMEs, and the local dev workflow that relies on `in-progress/` and `personal/`), or (b) **commit duplicate copies** of promoted skills into a flat directory (a sync burden and a second source of truth). Both are structural decisions, not something to bundle into shipping the Claude plugin. This is very likely the original, half-remembered reason a plugin wasn't shipped earlier: the manifest formats didn't cleanly express a curated subset of a bucketed repo.
|
|
|
|
## Decision
|
|
|
|
- Ship the **Claude Code plugin** now (`.claude-plugin/plugin.json` + `.claude-plugin/marketplace.json`), curated to the promoted set, as the headline v1.2 deliverable.
|
|
- Keep **skills.sh** as the universal installer — it already serves Codex and other harnesses today, so no Codex user is left without an install path.
|
|
- **Defer** the native Codex plugin until we decide between restructuring `skills/` to promoted-only vs. committing a generated flat copy. Revisit when Codex either supports a `skills` array / include-list or preserves symlinks on install.
|
|
|
|
## Invariants this creates
|
|
|
|
- Every promoted skill has an entry in `.claude-plugin/plugin.json`'s `skills` array (this already stood as a `CLAUDE.md` rule; it now also gates the plugin's contents).
|
|
- `.claude-plugin/plugin.json`'s `version` tracks `package.json`'s version — bump both together on release. Claude uses the plugin `version` to decide when installed users see an update.
|