Merge feature/superpowers-vendored into develop

This commit is contained in:
bastien
2026-09-28 15:08:58 +02:00
35 changed files with 695 additions and 145 deletions
+10
View File
@@ -127,6 +127,7 @@ rules:
| BDR-103 | 2026-09-27 | 6-repo review: 5 verdicts, 3 criteria (grep-verified coverage, per-session cost, doctrine conflict); stars decided nothing | accepted |
| BDR-104 | 2026-09-28 | MengTo motion pack: vendor 5 scroll skills pinned via shared lib/vendor-skills.sh + build personal skill site-motion; 17 skipped | accepted |
| BDR-105 | 2026-09-28 | skill-catalog prune: 9 gstack out via GSTACK_REMOVED, full ⊇ every profile, max = everything, brightdata + frontend-design plugin off, security-guidance Stop review off, design gate asks `21st login` and waits | accepted |
| BDR-106 | 2026-09-28 | superpowers: 7 wired skills vendored at v6.4.1 via lib/vendor-skills.sh (always_on lock class), plugin + marketplace dropped, citers by bare name, doctrine map for the 4 non-vendored refs | accepted |
---
@@ -1319,3 +1320,12 @@ Branch feature/user-writing-web-rules, UNMERGED (human gate).
- **Alternatives rejected**: rm symlinks by hand (set/reset re-materialize, `gstack on` restores everything → denylist instead); per-skill toggles inside ui-ux-pro-max (all-or-nothing, unverified); drop superpowers in the same run (7 skills wired in ship-feature/init-project → tier 2, own branch); keep the 21st trio in design profiles (redundant with impeccable + ui-ux-pro-max, CLI signed out); raise `SLASH_COMMAND_TOOL_CHAR_BUDGET` (costs context, the opposite goal); keep the official frontend-design plugin and drop the copy (copy is profile-managed and gate-checked); shared 21st auth helper across 3 scripts (breaks 4 fixture suites, changes installer semantics — [[LRN-178]]); in-session `export TWENTYFIRST_TOKEN` remedy (env does not persist across tool calls).
- **Caveats**: kept gstack skills still route to removed names in their upstream prose (Skill call fails, doctrine applies); helper tree links every top-level submodule entry (no SKILL.md exposed, asserted); security-guidance commit review quota unmeasured; doctor constants rebased on 2026-09-28 measures; `apply` is additive → other machines run `set full`, not `apply`.
- **Reference**: f83f8f7 02b62f7 4c86d6d 729d715 (prune), bd3e525 132bcdf (21st gate); contracts `2026-09-28-skill-catalog-prune-0554` (18 criteria, oracles in `.oracles/`) and `2026-09-28-21st-signin-gate-1215` (7); plans r4 / r3 after 3 challengers + 1 confirmation each; GATE 0 MET, verifiers CONFORME (iter 2 / iter 1), security PASS ×2; 42 suites green minus 2 pre-existing T16a. Links [[BDR-030]] [[BDR-101]] [[BDR-093]] [[BDR-095]] [[BDR-080]] [[BDR-025]] [[BDR-070]] [[LRN-175]] [[LRN-176]] [[LRN-177]] [[LRN-178]] [[BLK-023]] [[EVAL-034]].
## BDR-106 — superpowers: 7 skills vendored at v6.4.1, plugin dropped
- **Date**: 2026-09-28
- **Status**: accepted, feature/superpowers-vendored, UNMERGED (human gate)
- **Decision**: (1) plugins.lock.json `superpowers` entry (obra/superpowers @ 5bf4e78 = tag v6.4.1, path `skills`, per-skill file lists, `always_on: true`), fetched byte-for-byte by lib/vendor-skills.sh: brainstorming, writing-plans, subagent-driven-development, test-driven-development, requesting-code-review, using-git-worktrees, writing-skills; STEP 8e vendors, update-all refreshes at the pin, link.sh links, .gitignore ignores. (2) Plugin + marketplace uninstalled (one shot by hand after the fetch proved byte-identical), settings.json keys removed by hand, PROTECTED_PLUGINS = security-guidance only; `detect_superpowers` = `[ -f ~/.claude/skills/brainstorming/SKILL.md ]`, no plugin fallback; doctor/session-start no longer charge the injection. (3) doctor-vendored `always_on` class: third lock column, `_dv_check_link` 5th param — always-on externals are link-checked, never "parked". (4) Citers call the bare names; CLAUDE.global.md maps the four non-vendored skills the vendored text still references (executing-plans → SDD, finishing-a-development-branch → gitflow finish, systematic-debugging → bugfix, verification-before-completion → verifier gates). Vendored text never edited (BDR-104 rule).
- **Why**: 7 skills wired (ship-feature, init-project, writing-skills TDD), 8 duplicate personal flows; SessionStart injection 3.6 KB per start/clear/compact + a competing router ("1 % → MUST invoke", BDR-080 conflict); 15 descriptions → 7. Tier 2 of [[BDR-105]].
- **Alternatives rejected**: shared auth/detect helpers sourced at top level (break the fixture `cp` suites, [[LRN-178]]); installer-side uninstall (plugin gone before the fetch on a network failure; precedent = comment only, one-shot by hand); detect with plugin-cache fallback (the marketplace dir matches `*superpowers*` → "vendored" on a plugin-only machine, fail-open); rewriting vendored text to fix cross-refs; vendoring all 15; map text spelling the colon form or wrapping identifiers (criteria 3/7 grep line by line — both caught by challengers).
- **Caveats**: upstream cross-refs to the plugin prefix and the 8 dropped skills remain in the vendored text (a call on a dropped name fails, doctrine map applies); no upstream auto-update (bump the pin deliberately); the harness hot-loaded the 7 bare names in the running session after link.sh, the plugin names leave at restart; `superpowers-marketplace` cache dir may linger empty; other machines: `make plugin` (vendors) + `make link`, then uninstall the cached plugin by hand (CHANGELOG).
- **Reference**: 18f8c89 (wiring), ddea411 (citers/docs/settings); contract `2026-09-28-superpowers-vendored-1357` (12 criteria, oracles in `.oracles/`), plan r3 after 3 challengers (simplicity CONCERNS(2), robustness CONCERNS(3), correctness FATAL(5)) + confirmation CONCERNS(1); executors 2/2 DONE first pass; GATE 0 MET, verifier CONFORME 12/12, security PASS; catalog 82 skills, plugin passive cost 670 t (ui-ux-pro-max only). Links [[BDR-105]] [[BDR-102]] [[BDR-104]] [[BDR-065]] [[LRN-178]] [[EVAL-034]].
+1
View File
@@ -538,3 +538,4 @@ rules:
- Skill-catalog audit (user: "tour des skills, doublons, économiser tokens"): 5 analyzers over 150 skills / 53.5k chars desc; 78 listed name-only this session (listing budget ≈1 % ctx, least-invoked lose desc → gain = routing quality + no broken 100 KB body invoked, not listing chars). Found: frontend-design plugin byte-dup of managed copy; brightdata 21 skills keyless + hostile WebFetch routing; gstack ship trunk-based (origin/HEAD=main), land-and-deploy auto-merge+deploy, autoplan/make-pdf/diagram/careful/guard/freeze dead paths (only bin + browse/dist linked); security-guidance = Opus call per code turn + agentic commit review, 0 findings/6 days; doctor.sh undercount ×6. User go: tier 1, superpowers vendor-7 (tier 2 later), 21st trio parked (CLI `Not logged in`), rule "full ⊇ every profile, max = everything". Live: brightdata disabled, frontend-design plugin uninstalled, `set full` → 75 skills (was 89).
- /feat by hand on feature/skill-catalog-prune: contract 18 criteria; plan r1→r4 (3 challengers, confirmation FATAL(4): nested SKILL.md in browser-skills/openclaw/node_modules, ./setup global symlink, update-all 3rd copy); 4 feater parallel DONE; GATE 0 UNMET(4) = MY heredoc CHECKs (gates.sh single-line) → oracles to `<contract>.oracles/*.py` → MET; verifier ECARTS(1) = floor-guard `xit(` false-positive on `sys.exit(` → restructure → CONFORME; security PASS. 41 suites green minus 2 pre-existing T16a, shellcheck clean. UNMERGED — human gate. Registries pending user approval.
- User: "quand on détecte qu'on a besoin de 21st, on demande de log si c'est pas fait et on attend". /feat by hand on the same branch: design gate gains exit 12 `SIGN-IN REQUIRED` (three-state whoami probe, unknown → 11 with diagnostic, explicit "proceed without 21st" only skip); challenge round dropped my shared-helper idea (would break 4 fixture suites + change installer semantics) and my in-session `export TWENTYFIRST_TOKEN` remedy (env does not persist across tool calls). Executor DONE first pass, GATE 0 MET, verifier CONFORME 7/7, security PASS, 8/8 hermetic. Gate now exits 12 live here until `21st login`.
- User go "merge le tout, écris les registres, fais le tier 2": tier 1 registries (BDR-105, LRN-175..178, BLK-023, EVAL-034) written, feature/skill-catalog-prune finished → develop c39c0e1. Tier 2 on feature/superpowers-vendored: 7 superpowers skills vendored at v6.4.1 through lib/vendor-skills.sh (`always_on` lock class for doctor-vendored), plugin + marketplace uninstalled, settings.json hand-edited, citers by bare name, doctrine map. Challenge round: correctness FATAL(5) caught my map text containing the forbidden `superpowers` colon form; confirmation caught an identifier wrapped across lines (grep is line-based). Executors 2/2 DONE, GATE 0 MET, verifier CONFORME 12/12, security PASS. Catalog 82 skills, passive plugin cost 670 t, injection gone; harness hot-loaded the bare names in-session. 18f8c89 ddea411. UNMERGED — human gate. [[BDR-106]]
+20
View File
@@ -1,5 +1,25 @@
# TODO
## 2026-09-28 — tier 2: vendor 7 superpowers skills, drop the plugin (feature/superpowers-vendored)
User go "fais le tier 2" (decision 2026-09-28, batch 1). Contract
`.claude/tasks/contracts/2026-09-28-superpowers-vendored-1357.md`.
- [x] V1 plugins.lock.json `superpowers` entry (obra/superpowers @ 5bf4e78 = v6.4.1,
path skills, dict of 7 file lists); install-plugins.sh STEP 5 stops installing
the plugin, STEP 8e vendors it; update-all.sh refresh; link.sh EXTERNAL_SKILLS;
.gitignore; profile.sh PROTECTED_PLUGINS; detect-plugins/session-start/doctor
read the vendored dir, injection cost gone.
- [x] V2 citers: `superpowers:<x>` → `<x>` in ship-feature, init-project, tour, deploy,
audit-delta, lib/analyze-before-plan, plugin-advisor; finishing-a-development-
branch prose in capitalize-commit/doc-commit/gitflow; CLAUDE.global.md routing
map for the 8 dropped skills; README/USAGE/plugin-advisor/profile SKILL.md;
CHANGELOG.
- [x] V3 plan r1→r3 (3 challengers + confirmation), 2 feater DONE, live vendor + link
(VENDORED_LINKED), settings.json hand-edited, plugin + marketplace uninstalled,
GATE 0 MET 10/10, verifier CONFORME 12/12, security PASS; 18f8c89 ddea411; BDR-106.
Catalog 82 skills, passive plugins 670 t. UNMERGED — human gate. Other machines:
`make plugin` + `make link`, uninstall the cached plugin by hand. User: remove
`/tmp/tmp.PKDTRyaCw8` `/tmp/tmp.99Fu0dm8ll` (executor fixtures, rm refused).
## 2026-09-28 — design gate asks for `21st login` and waits (feature/skill-catalog-prune)
User: "si on veut l'utiliser, on demande à l'utilisateur de se log, plus simple que
dire c'est pas logged on utilise pas… on demande de log si c'est pas fait et on
@@ -0,0 +1,69 @@
# CONTRACT — superpowers-vendored
- date: 2026-09-28 | flow: feat (ad-hoc dispatch, /feat gates replayed by the orchestrator, 2 parallel feater executors) | branch: feature/superpowers-vendored
- status: active
## REQUEST (verbatim — IMMUTABLE)
> ok merge le tout et écris les registres puis fais le tier 2
Tier 2 as decided 2026-09-28 (batch 1, option "Vendoriser 7, retirer le plugin (Recommended)"): vendor brainstorming, writing-plans, subagent-driven-development, test-driven-development, requesting-code-review, using-git-worktrees, writing-skills from obra/superpowers at the v6.4.1 commit via `lib/vendor-skills.sh`, drop the superpowers plugin (its 8 other skills and its session-start injection), rename the `superpowers:` citers.
## CLARIFICATIONS
- Pass A: none — request complete (the decision batch fixed scope and outcome).
- Pass B: no visible / public-name choice left open — the vendored skills keep their upstream names (bare, no `superpowers:` prefix; renaming would break their internal cross-references), the lock key is `superpowers`, the always-on status is inherited (not in MANAGED_EXTERNALS, like darwin-skill). Proceeds silently.
- Byte-for-byte upstream text (BDR-104 convention): the vendored files are never edited, so their internal `superpowers:<x>` mentions and references to the 8 dropped skills (executing-plans, finishing-a-development-branch, systematic-debugging, verification-before-completion, dispatching-parallel-agents, receiving-code-review, using-superpowers, diagnosing-superpowers) stay in the text; CLAUDE.global.md carries the routing map (bare names; executing-plans → subagent-driven-development; finishing-a-development-branch → `gitflow finish` on a human signal; systematic-debugging → bugfix; verification-before-completion → the verifier gates). Known residual, documented.
- Scripts inside the vendored skills are invoked as `bash scripts/<x>` upstream: no exec bit needed after curl.
- `docs/superpowers/{specs,plans}` stays the transient path (brainstorming/writing-plans still write there; gitflow purge unchanged, BDR-065).
- Live steps are the orchestrator's: criterion 2 runs the vendor helper (network) + link.sh; the plugin uninstall (`claude plugin uninstall superpowers@superpowers-marketplace`) runs AFTER the 7 skills are linked, then criterion 8 checks the catalog. Executors never run `claude plugin …`, the vendor helper against the network, link.sh, `profile.sh set`, never commit.
- [challenge 2026-09-28, 3 lenses: simplicity CONCERNS(2), robustness CONCERNS(3), correctness FATAL(5); every BLOCKER/MAJOR closed by a named plan change, r2] (a) CLAUDE.global.md map never spells the colon form; (b) `always_on` lock field + doctor-vendored always-on class, test case; (c) no uninstall code in the installer, one-shot by the orchestrator after criterion 2, marketplace removed too, rollback step; (d) settings.json hand-edited (enabledPlugins key + marketplace block) and committed; (e) detect_superpowers = file test on the linked skill, no fallback, negative control in criterion 5; (f) map trimmed, lock note trimmed, session-start line deleted plainly.
- [confirmation pass 2026-09-28, correctness CONCERNS(1), all closed by named changes, r3] map identifiers kept whole per line (grep is line-based); `always_on` mechanism pinned (third lock column, 5th `_dv_check_link` param, headers); settings.json edited by the orchestrator only after criterion 2 is green; stale installer edge case removed; doctor pass line worded on what it proves.
- Functions ≤ 25 logic lines, 80-char lines, shellcheck clean.
## ACCEPTANCE CRITERIA
1. plugins.lock.json carries the `superpowers` entry: obra/superpowers, commit 5bf4e78011075bcfc0dc295f0724994cd123ee71 (v6.4.1), path `skills`, dict of exactly the 7 skills with every upstream file listed (SKILL.md each; SDD scripts, code-reviewer.md, anthropic-best-practices.md included).
CHECK: python3 .claude/tasks/contracts/2026-09-28-superpowers-vendored-1357.oracles/c1.py
EXPECT: LOCK_OK
EVIDENCE: MET exit=0 marker-found :: LOCK_OK
2. Vendored + linked live: every listed file is under skills-external/<skill>/, byte-identical to the plugin cache copy, and the 7 symlinks resolve under ~/.claude/skills.
CHECK: bash -c 'source lib/vendor-skills.sh; vendor_pinned_skills superpowers' >/dev/null 2>&1; bash link.sh >/dev/null 2>&1; python3 .claude/tasks/contracts/2026-09-28-superpowers-vendored-1357.oracles/c2.py
EXPECT: VENDORED_LINKED
EVIDENCE: MET exit=0 marker-found :: VENDORED_LINKED
3. No `superpowers:` prefix remains in the personal catalog, agents, lib, hooks or doctrine (fixtures excluded; positive control first).
CHECK: echo 'x superpowers:brainstorming' | grep -q 'superpowers:' || exit 1; if git grep -n 'superpowers:' -- skills agents lib hooks CLAUDE.global.md ':!lib/tests/fixtures' | grep -v '^skills/synced'; then exit 1; fi; echo NO_PREFIX
EXPECT: NO_PREFIX
EVIDENCE: MET exit=0 marker-found :: NO_PREFIX
4. Installers and link wired: install-plugins.sh no longer installs/enables the plugin and vendors `superpowers` in STEP 8e; update-all.sh refreshes it; link.sh EXTERNAL_SKILLS lists the 7; .gitignore ignores the 7 skill symlinks and the 7 skills-external dirs.
CHECK: ! grep -qE 'install_plugin +"superpowers"|enable_plugin +"superpowers"' install-plugins.sh && grep -q 'vendor_pinned_skills superpowers' install-plugins.sh && grep -q 'vendor_pinned_skills superpowers refresh' update-all.sh && for s in brainstorming writing-plans subagent-driven-development test-driven-development requesting-code-review using-git-worktrees writing-skills; do grep -qE "^skills/$s\$" .gitignore || { echo "gitignore skills/$s"; exit 1; }; grep -qE "^skills-external/$s/\$" .gitignore || { echo "gitignore ext $s"; exit 1; }; sed -n '/^EXTERNAL_SKILLS=(/,/)/p' link.sh | grep -qw "$s" || { echo "link $s"; exit 1; }; done && echo WIRED
EXPECT: WIRED
EVIDENCE: MET exit=0 marker-found :: WIRED
5. profile.sh no longer protects the plugin; detect_superpowers is true on the linked vendored skill alone and false under an empty HOME (no plugin-cache glob, no claude call). [challenge r2]
CHECK: ! grep -q 'superpowers@superpowers-marketplace' lib/profile.sh && bash -c 'source lib/detect-plugins.sh; detect_superpowers' && E=$(mktemp -d) && ! HOME="$E" bash -c 'source lib/detect-plugins.sh; detect_superpowers' && rmdir "$E" && ! grep -qE 'compgen.*superpowers|plugin list.*superpowers' lib/detect-plugins.sh && echo DETECT_OK
EXPECT: DETECT_OK
EVIDENCE: MET exit=0 marker-found :: DETECT_OK
6. Suites and shellcheck: vendor-skills, doctor-vendored (with the new ALWAYS_ON_LINK_CHECKED case), doctrine-citers, skill-routing-census (live catalog with the 7), profile-default, profile-set-managed green; shellcheck clean on every touched shell file. [challenge r2]
CHECK: shellcheck install-plugins.sh update-all.sh link.sh lib/profile.sh lib/detect-plugins.sh hooks/session-start.sh doctor.sh lib/doctor-vendored.sh lib/vendor-skills.sh lib/tests/doctor-vendored.test.sh && out=$(make test suite=lib/tests/doctor-vendored.test.sh 2>&1) && echo "$out" | grep -q 'PASS ALWAYS_ON_LINK_CHECKED' && for s in vendor-skills doctor-vendored doctrine-citers skill-routing-census profile-default profile-set-managed; do out=$(make test suite=lib/tests/$s.test.sh 2>&1) || { echo "$s rc"; exit 1; }; echo "$out" | grep -qE 'FAIL=[1-9]|^FAIL ' && { echo "$s FAIL"; exit 1; }; done; echo SUITES_OK
EXPECT: SUITES_OK
EVIDENCE: MET exit=0 marker-found :: SUITES_OK
7. CLAUDE.global.md Skill routing carries the map for the dropped skills and says the seven are vendored, bare names.
CHECK: grep -q 'finishing-a-development-branch' CLAUDE.global.md && grep -q 'executing-plans' CLAUDE.global.md && grep -q 'systematic-debugging' CLAUDE.global.md && grep -qi 'vendored' CLAUDE.global.md && echo ROUTING_OK
EXPECT: ROUTING_OK
EVIDENCE: MET exit=0 marker-found :: ROUTING_OK
8. Live after the orchestrator's uninstall + marketplace removal: no superpowers plugin installed, no enabledPlugins key, no extraKnownMarketplaces block, the 7 skills still resolve, `make doctor` reports superpowers as vendored, not failed. [challenge r2]
CHECK: ! claude plugin list 2>/dev/null | grep -q 'superpowers@superpowers-marketplace' && python3 -c "import json,sys;d=json.load(open('settings.json'));assert 'superpowers@superpowers-marketplace' not in d['enabledPlugins'];assert 'superpowers-marketplace' not in d.get('extraKnownMarketplaces',{})" && for s in brainstorming writing-plans subagent-driven-development test-driven-development requesting-code-review using-git-worktrees writing-skills; do [ -f "$HOME/.claude/skills/$s/SKILL.md" ] || { echo "missing $s"; exit 1; }; done && bash doctor.sh 2>/dev/null | grep -qi 'superpowers.*vendored' && ! bash doctor.sh 2>/dev/null | grep -qi 'Superpowers not detected' && echo PLUGIN_GONE
EXPECT: PLUGIN_GONE
EVIDENCE: MET exit=0 marker-found :: PLUGIN_GONE
9. doctor.sh and session-start.sh stop charging the plugin injection (no `+ 1500` / `+ 800` superpowers constant; doctor message names the vendored skills).
CHECK: ! grep -qE 'detect_superpowers.*\+ ?(1500|800)' doctor.sh hooks/session-start.sh && grep -qi 'vendored' doctor.sh && echo DOCTOR_OK
EXPECT: DOCTOR_OK
EVIDENCE: MET exit=0 marker-found :: DOCTOR_OK
10. Docs: README component table row (vendored skills, pinned v6.4.1, lock entry), USAGE.md mentions of "superpowers" as a plugin or a passive cost reworded, agents/plugin-advisor.md compatibility/recommended-set rows and the "not active → install" remedy reworded, skills/profile/SKILL.md:59 always-on sentence updated, CHANGELOG `[Unreleased]` entry (Changed: superpowers plugin → 7 vendored skills; Removed: the 8 other skills + injection; Known residual: upstream cross-references).
11. lib/capitalize-commit.md, lib/doc-commit.md, lib/analyze-before-plan.md and skills/gitflow/SKILL.md describe finishing-a-development-branch as the upstream skill this config does not vendor (gitflow finish replaces it), not as an active skill.
12. doctor-vendored treats the 7 as always-on: `bash doctor.sh` prints a pass line for each of the 7 (linked) and never "parked" for them. [challenge r2]
CHECK: out=$(bash doctor.sh 2>/dev/null); for s in brainstorming writing-plans subagent-driven-development test-driven-development requesting-code-review using-git-worktrees writing-skills; do echo "$out" | grep -qE "✓.*\b$s\b" || { echo "no pass for $s"; exit 1; }; echo "$out" | grep -qE "$s.*parked" && { echo "parked $s"; exit 1; }; done; echo ALWAYS_ON_OK
EXPECT: ALWAYS_ON_OK
EVIDENCE: MET exit=0 marker-found :: ALWAYS_ON_OK
## FILE SCOPE
- plugins.lock.json, install-plugins.sh (STEP 5 superpowers block, STEP 8e, summary lines), update-all.sh (7.3), link.sh (EXTERNAL_SKILLS), .gitignore, lib/profile.sh (PROTECTED_PLUGINS + comments), lib/detect-plugins.sh, hooks/session-start.sh, doctor.sh, lib/doctor-vendored.sh, lib/tests/doctor-vendored.test.sh, lib/vendor-skills.sh (lock-shape header comment line)
- skills/{ship-feature,init-project,tour,deploy,audit-delta,gitflow,profile}/SKILL.md, lib/{analyze-before-plan,capitalize-commit,doc-commit}.md, agents/plugin-advisor.md, CLAUDE.global.md (Skill routing lines), README.md, USAGE.md, CHANGELOG.md
- Orchestrator-only, after criterion 2: settings.json (enabledPlugins key + extraKnownMarketplaces block, hand edit), `claude plugin uninstall` + `claude plugin marketplace remove` (cache), rollback if criterion 8 fails; skills-external/<7> (gitignored, curl) and ~/.claude/skills symlinks are written by criterion 2
- Orchestrator-only: .claude/tasks/**, .claude/memory/**
@@ -0,0 +1,16 @@
import json,re
d=json.load(open('plugins.lock.json'))
e=d['superpowers']
assert e['source']=='https://github.com/obra/superpowers', e['source']
assert e['commit']=='5bf4e78011075bcfc0dc295f0724994cd123ee71', e['commit']
assert e['path']=='skills', e.get('path')
assert e.get('managed_by')=='curl'
want={'brainstorming','writing-plans','subagent-driven-development','test-driven-development','requesting-code-review','using-git-worktrees','writing-skills'}
assert set(e['skills'])==want, set(e['skills'])^want
for k,files in e['skills'].items():
assert 'SKILL.md' in files, k
for f in files: assert re.fullmatch(r'[A-Za-z0-9._/-]+',f) and '..' not in f, f
assert 'scripts/sdd-workspace' in e['skills']['subagent-driven-development']
assert 'code-reviewer.md' in e['skills']['requesting-code-review']
assert 'anthropic-best-practices.md' in e['skills']['writing-skills']
print('LOCK_OK')
@@ -0,0 +1,17 @@
import json,os,hashlib,glob
H=os.path.expanduser('~')
e=json.load(open('plugins.lock.json'))['superpowers']
cache=glob.glob(H+'/.claude/plugins/cache/superpowers-marketplace/superpowers/6.4.1/skills')
missing=[];mism=[]
for k,files in e['skills'].items():
for f in files:
p=f'skills-external/{k}/{f}'
if not os.path.isfile(p): missing.append(p); continue
if cache:
c=f'{cache[0]}/{k}/{f}'
if os.path.isfile(c) and hashlib.md5(open(p,'rb').read()).hexdigest()!=hashlib.md5(open(c,'rb').read()).hexdigest(): mism.append(p)
link=f'{H}/.claude/skills/{k}'
if not (os.path.islink(link) and os.path.isfile(link+'/SKILL.md')): missing.append(link)
assert not missing, missing
assert not mism, ('byte mismatch vs plugin cache',mism)
print('VENDORED_LINKED')
@@ -0,0 +1,271 @@
# PLAN — superpowers-vendored (feat, ad-hoc dispatch) — r3 (after confirmation pass)
- r3 closes the confirmation pass (correctness CONCERNS(1)): MAJOR 1 — the
CLAUDE.global.md map keeps every skill identifier whole on one line (grep
is line-based); MINOR 2 — `always_on` mechanism pinned: the python lock
reader emits a third column, `_dv_check_link` gets a 5th param, headers
updated, a helper extracted if `check_vendored_skills` would exceed 5
locals; MINOR 3 — stale "uninstall || true" edge case deleted; MINOR 4 —
settings.json edit moves to the orchestrator, AFTER criterion 2 is green
(a disabled plugin + a failed fetch must never coincide); MINOR 5 —
profile.sh comments located by grep, doctor pass line worded on what is
proven.
- r2 closes: correctness BLOCKER 1 (the CLAUDE.global.md map never spells the
colon form — criterion 3 greps it), MAJOR 2 (doctor-vendored gains an
always-on class driven by a lock field `always_on`, so the 7 are
link-checked instead of "parked"), MAJOR 3 + robustness MAJOR 1 (NO
uninstall code in the installer — comment only, one-shot by the
orchestrator after criterion 2 is green), MAJOR 4 + robustness MAJOR 3
(settings.json hand-edited: enabledPlugins key and
extraKnownMarketplaces.superpowers-marketplace block removed, committed),
MAJOR 5 + robustness MAJOR 2 + simplicity MAJOR 1 (detect_superpowers =
one file test on the linked skill, no plugin fallback, no new global),
simplicity MAJOR 2 (same: no installer uninstall), MINORs: session-start
line deleted plainly, map trimmed to the four referenced skills, lock note
kept to maintainer facts, summary line placement pinned, rollback step,
mixed-version rollback note.
- date: 2026-09-28 | contract: contracts/2026-09-28-superpowers-vendored-1357.md
- branch: feature/superpowers-vendored
- executors: 2 feater (sonnet-pinned), parallel, disjoint file sets
## Ground truth (verified 2026-09-28)
- Plugin superpowers 6.4.1 installed at
`~/.claude/plugins/cache/superpowers-marketplace/superpowers/6.4.1/`
(gitCommitSha 5bf4e78011075bcfc0dc295f0724994cd123ee71 = upstream tag
v6.4.1 on obra/superpowers; raw files served at
`https://raw.githubusercontent.com/obra/superpowers/<sha>/skills/<skill>/<file>`,
brainstorming/SKILL.md md5 identical local vs raw). Enabled in settings.json
(`superpowers@superpowers-marketplace: true`), PROTECTED in lib/profile.sh,
installed + enabled by install-plugins.sh STEP 5 (marketplace add,
install_plugin, enable_plugin), summary line "ALWAYS ON … superpowers".
Its hooks.json SessionStart (startup|clear|compact) injects
using-superpowers (~3.6 KB) every start.
- The 7 skills to vendor and their files (upstream layout `skills/<name>/`):
brainstorming: SKILL.md, spec-document-reviewer-prompt.md, visual-companion.md,
scripts/frame-template.html, scripts/helper.js, scripts/server.cjs,
scripts/start-server.sh, scripts/stop-server.sh
writing-plans: SKILL.md, plan-document-reviewer-prompt.md
subagent-driven-development: SKILL.md, implementer-prompt.md,
re-review-prompt.md, task-reviewer-prompt.md, scripts/review-package,
scripts/sdd-workspace, scripts/task-brief
test-driven-development: SKILL.md, writing-good-tests.md
requesting-code-review: SKILL.md, code-reviewer.md
using-git-worktrees: SKILL.md
writing-skills: SKILL.md, anthropic-best-practices.md,
examples/CLAUDE_MD_TESTING.md, graphviz-conventions.dot,
persuasion-principles.md, render-graphs.js, testing-skills-with-subagents.md
Scripts are invoked upstream as `bash scripts/<x>` (SDD lines 137, 252,
290…; brainstorming visual-companion.md) → no exec bit needed.
- Internal cross-references that will dangle (byte-for-byte text):
writing-plans → superpowers:subagent-driven-development, superpowers:executing-plans (dropped), superpowers:using-git-worktrees;
SDD → superpowers:finishing-a-development-branch ×4 (dropped), superpowers:using-git-worktrees, superpowers:requesting-code-review, executing-plans ×2;
TDD → superpowers:writing-skills; writing-skills → superpowers:test-driven-development ×4, superpowers:systematic-debugging (dropped), using-superpowers, verification-before-completion.
- `lib/vendor-skills.sh` `vendor_pinned_skills <lock-key> [refresh]`: lock
entry `{source, commit (40 hex), path, skills: {name: [files]}, managed_by}`;
files must match `[A-Za-z0-9._/-]+`, no `..`; tmp+mv; skips existing files
unless `refresh`. install-plugins.sh STEP 8e calls it for agent-skills and
mengto-skills with `EXT_SKILL_NAMES` symlink check; update-all.sh 7.3 calls
it with `refresh`. link.sh `EXTERNAL_SKILLS=(…)` symlinks
`skills-external/<name>` into `~/.claude/skills/<name>`; .gitignore lists
`skills/<name>` (symlink) and `skills-external/<name>/` (vendored text) per
external. lib/doctor-vendored.sh reads the lock + EXTERNAL_SKILLS generically.
- lib/profile.sh: `PROTECTED_PLUGINS=("security-guidance@claude-code-plugins"
"superpowers@superpowers-marketplace")`; MANAGED_EXTERNALS is the allowlist
`set` parks — the 7 are NOT added (always on, like darwin-skill).
- lib/detect-plugins.sh `detect_superpowers`: plugin cache glob then `claude
plugin list`. Consumers: hooks/session-start.sh:122 (`+ 800` passive),
doctor.sh:225-228 (pass/fail "Superpowers plugin detected / not detected —
orchestrators will fail") and :423 (`+ 1500`).
- `superpowers:` citers (personal): skills/ship-feature:103,117,176,237;
skills/init-project:71,182,215,259; skills/tour:318; skills/deploy:515;
skills/audit-delta:321; lib/analyze-before-plan.md:106;
lib/capitalize-commit.md:20 (finishing-a-development-branch);
agents/plugin-advisor.md:182. Prose mentions of
finishing-a-development-branch: lib/capitalize-commit.md:68,
lib/doc-commit.md:84, lib/analyze-before-plan.md:108, skills/gitflow:16,110.
Docs: README.md:121 (component table), USAGE.md ×19 (plugin/cost
narrative), agents/plugin-advisor.md ×19 (matrix, recommended sets, remedy
:324), skills/profile/SKILL.md:59, install-plugins.sh:1210 summary.
`docs/superpowers/` paths (CLAUDE.md, gitflow, onboard) stay: brainstorming
and writing-plans still write there.
- lib/tests: gitflow-test.sh mentions superpowers only through the purge
path (unchanged). No suite asserts PROTECTED_PLUGINS content.
## Approach
### E1 — wiring (lock, installers, link, gitignore, profile, detect, doctor)
Files: plugins.lock.json, install-plugins.sh, update-all.sh, link.sh,
.gitignore, lib/profile.sh, lib/detect-plugins.sh, hooks/session-start.sh,
doctor.sh, lib/doctor-vendored.sh, lib/tests/doctor-vendored.test.sh,
lib/vendor-skills.sh (header comment line only).
1. plugins.lock.json: new entry `"superpowers"` after `"mengto-skills"`:
source `https://github.com/obra/superpowers`, commit
`5bf4e78011075bcfc0dc295f0724994cd123ee71`, path `skills`, `skills` = the
dict above (exact file lists), managed_by `curl`, `"always_on": true`,
note (maintainer facts only, history lives in CHANGELOG/BDR-106): "Seven
superpowers skills vendored byte-for-byte at the v6.4.1 tag commit
(obra/superpowers), always on (no profile lists them). Bump the commit
deliberately. Scripts inside run as `bash scripts/<x>`, no exec bit
needed. Upstream cross-references to the plugin prefix and to the 8
non-vendored skills stay in the text; CLAUDE.global.md Skill routing maps
them."
2. install-plugins.sh STEP 5: delete the three superpowers lines (marketplace
add, install_plugin, enable_plugin) and replace with a 3-line comment
"Superpowers plugin removed 2026-09-28 (tier 2 of the skill-catalog prune):
its 7 wired skills are vendored in Step 8e (plugins.lock.json
'superpowers'); a still-cached plugin is uninstalled by hand once
(claude plugin uninstall superpowers@superpowers-marketplace), never here".
NO uninstall code in the installer (precedent: frontend-design, caveman).
Update the `enable_plugin` comment (:490) to name only security-guidance.
STEP 8e: heading/comment mention superpowers; `EXT_SKILL_NAMES` += the 7;
`vendor_pinned_skills superpowers` after mengto. Summary: replace line
~1210 ("✅ superpowers — brainstorm/plan/implement/debug workflow", ALWAYS
ON block) by "✅ superpowers skills — 7 vendored (brainstorming,
writing-plans, subagent-driven-development, test-driven-development,
requesting-code-review, using-git-worktrees, writing-skills), pinned
v6.4.1, curl → symlink, no plugin, no session injection"; add one "at:"
line right after the mengto "at:" line (~1234): "Superpowers skills at:
~/.claude/skills/{brainstorming,…}/ (symlink → skills-external)".
3. update-all.sh 7.3: `echo "── Updating superpowers skills (obra/superpowers)..."`
+ `vendor_pinned_skills superpowers refresh`; comment names it.
4. link.sh EXTERNAL_SKILLS += the 7 (keep the array multi-line ≤ 80 chars).
5. .gitignore: 7 `skills/<name>` lines next to the other external symlinks
(:65-68 block) and 7 `skills-external/<name>/` lines next to the mengto
block (:203-207), each block with a one-line comment "superpowers, vendored
(plugins.lock.json 'superpowers')".
6. lib/profile.sh: PROTECTED_PLUGINS keeps only security-guidance; every
comment naming superpowers as an always-on plugin (`grep -n superpowers
lib/profile.sh`, currently ~:22 and ~:65) reworded ("superpowers is
vendored skills now, not a plugin").
7. lib/detect-plugins.sh `detect_superpowers`: exactly
`[ -f "$HOME/.claude/skills/brainstorming/SKILL.md" ]` (the linked
vendored skill: proves vendored AND linked; no plugin cache glob, no
`claude plugin list`, no new global, no fallback). Comment: "superpowers
= 7 vendored skills since 2026-09-28; the plugin is gone". A negative
control (empty HOME) must return 1.
7b. lib/doctor-vendored.sh: lock entries may carry `"always_on": true`
(the `superpowers` entry does). Skills of such an entry are expected
LINKED whatever the active profile says (today every EXTERNAL_SKILLS name
absent from the profile is reported `parked`, link unchecked — the 7 are
in no profile by design). Mechanism: `_dv_lock_expectations` (python)
prints a THIRD column `name\tfile\t1` for skills of an `always_on` entry
(awk `$1==n {print $2}` in `_dv_check_files` keeps working unchanged);
`check_vendored_skills` reads the flag and passes it as a 5th parameter to
`_dv_check_link`, which treats `1` as "expected linked whatever the
profile says". If `check_vendored_skills` would exceed 5 locals, extract
the per-name dispatch into a helper (≤ 25 logic lines each). Update the
file header ("A name absent from the profile is reported parked" → "…
unless its lock entry is always_on") and the test header. Message
unchanged for the linked case, fail "<name>: symlink missing/wrong — run:
make link" when absent. Add a case
`ALWAYS_ON_LINK_CHECKED` to lib/tests/doctor-vendored.test.sh (fixture
entry with always_on true, name absent from the profile, link missing →
fail line, never `parked`). Document the field in lib/vendor-skills.sh's
lock-shape header comment (one line: ignored by the vendor helper, read
by doctor-vendored).
8. hooks/session-start.sh: delete line 122 (`detect_superpowers … + 800`)
outright — the banner's ALWAYS_ON list comes from detect_rtk + settings
enabledPlugins (lines ~147-160), not from this call. doctor.sh :225-228:
pass "superpowers: 7 skills vendored + linked (plugins.lock.json, v6.4.1)"
/ fail "superpowers skills not linked — run: make plugin && make link";
the pass line is worded on what `detect_superpowers` proves
("superpowers skills linked (brainstorming found); per-skill check under
Vendored skills"); :423 delete the `+ 1500` line (comment: counted by the
skill catalog stats).
9. settings.json: NOT an executor file any more — the orchestrator edits it
after criterion 2 is green (see Orchestrator steps), so a disabled plugin
never coincides with a failed fetch.
### E2 — citers, routing map, docs
Files: skills/{ship-feature,init-project,tour,deploy,audit-delta,gitflow,profile}/SKILL.md,
lib/{analyze-before-plan,capitalize-commit,doc-commit}.md,
agents/plugin-advisor.md, CLAUDE.global.md, README.md, USAGE.md, CHANGELOG.md.
1. `superpowers:<x>` → `<x>` (bare) in ship-feature ×4, init-project ×4,
tour:318, deploy:515, audit-delta:321, lib/analyze-before-plan.md:106,
agents/plugin-advisor.md:182. Wording around them: "Invoke `brainstorming`
(vendored superpowers skill)" on first mention per file, bare afterwards.
2. finishing-a-development-branch prose: lib/capitalize-commit.md:20 → "Orchestrators
that integrate via `gitflow finish` (the upstream
finishing-a-development-branch is not vendored)"; :68, lib/doc-commit.md:84,
lib/analyze-before-plan.md:108, skills/gitflow:16,110 → say "upstream
superpowers skill, not vendored here; `gitflow finish` is the only
integration path" where they present it as available.
3. CLAUDE.global.md § Skill routing, after the "Before /clear or /compact"
line, ≤ 80 chars per line, about 4 lines, and NEVER the literal
"superpowers" followed by a colon (criterion 3 greps that string):
"- superpowers skills are vendored, called by bare name; an upstream
`superpowers` prefix means the bare skill. Not vendored:
executing-plans → subagent-driven-development;
finishing-a-development-branch → `gitflow finish` (human signal);
systematic-debugging → bugfix; verification-before-completion → the
verifier gates."
Every skill identifier stays WHOLE on its line (criterion 7 greps
`finishing-a-development-branch`, `executing-plans`, `systematic-debugging`
line by line); wrap at spaces only.
4. README.md:121 row → "**Superpowers skills** | Vendored (7, always on) |
brainstorming, writing-plans, subagent-driven development, TDD, code
review request, git worktrees, writing-skills — pinned v6.4.1 in
plugins.lock.json, no plugin, no session injection | obra/superpowers".
README:208 unchanged.
5. USAGE.md: every line presenting superpowers as a plugin to keep ON/OFF or
as ~800 t passive (184-185, 589, 650, 751, 864, 959-965, 971, 995, 1018)
→ "skills superpowers (vendorisés, toujours actifs, 0 t passif)" or the
equivalent in the sentence's French; keep the narrative otherwise.
6. agents/plugin-advisor.md: rows 177-182 (compat matrix) → "superpowers
skills (vendored)" wording, drop the plugin-dev overlap row's "plugin"
framing; recommended-set table 190-198: replace "superpowers" by
"(superpowers skills always on)" in the ON column and subtract ~800 t from
each cost; :80, :146, :242, :254, :298 reword; :324 remedy → "Superpowers
skills missing → `make plugin` (vendors them) then `make link`".
7. skills/profile/SKILL.md:59: "Always-on plugins (`security-guidance`) and
the vendored superpowers skills are never toggled by a profile".
8. CHANGELOG `[Unreleased]`: Changed (superpowers plugin → 7 vendored skills,
pinned, always on; `superpowers:` citers renamed), Removed (plugin, its 8
duplicate skills, the SessionStart injection), Known residual (upstream
cross-references inside the vendored text; CLAUDE.global.md map).
## Orchestrator steps
- Criterion 2 vendors + links live (network fetch of 30 files); only when
every file is present and byte-identical (c2.py) does the next step run.
- Then the orchestrator edits settings.json by hand: remove the
`"superpowers@superpowers-marketplace": true` key from `enabledPlugins` and
the whole `extraKnownMarketplaces."superpowers-marketplace"` block, nothing
else; validate with `python3 -c 'import json;json.load(open("settings.json"))'`.
- Then, one shot by hand: `claude plugin uninstall superpowers@superpowers-marketplace`
and `claude plugin marketplace remove superpowers-marketplace`; re-check
`git diff settings.json` afterwards (the CLI must not have re-added
anything), then criterion 8.
- Rollback if criterion 8 fails: `claude plugin marketplace add
obra/superpowers-marketplace && claude plugin install superpowers@superpowers-marketplace`,
`git checkout -- settings.json`, stop and report.
- Verifier; security; commit; BDR-106 + journal.
## Edge cases
- Mid-migration machine (plugin cached, skills not yet vendored): doctor
fails "not vendored or linked — run make plugin && make link"; the user
uninstalls the plugin by hand (CHANGELOG says so). No fallback that could
print "vendored" for a plugin-only machine.
- Mixed-version rollback (an older checkout re-installs the plugin while the
7 symlinks are still linked → duplicate descriptions): CHANGELOG note
"after a rollback, delete skills/<7> symlinks or re-run the new make plugin".
- The running session keeps the plugin's `superpowers` skills until restart;
the bare names appear after `make link` + a new session.
- Fresh clone: link.sh symlinks a non-existent skills-external dir only if
present (existing `[ -d ]` guard).
- skill-routing-census live run gains 7 descriptions: brainstorming's "You
MUST use this before any creative work" vs personal descriptions — the
suite's live FAIL threshold must not trip (check by running it).
## Tests
- make test suite= vendor-skills, doctor-vendored (with the new
ALWAYS_ON_LINK_CHECKED case), doctrine-citers, skill-routing-census,
profile-default, profile-set-managed.
- shellcheck on every touched shell file.
## Disposition (RELATED MEMORY)
- honors BDR-102 / BDR-104 — vendor over plugin, shared helper, pinned commit,
byte-for-byte text.
- honors BDR-105 — tier 2 of the prune decision.
- honors BDR-065 — docs/superpowers transient path unchanged.
- honors LRN-178 — no new top-level `source`; detect-plugins reads a path.
- honors BDR-077 — requesting-code-review's reviewer dispatch keeps the
model-routing note in ship-feature/init-project.
+23
View File
@@ -74,6 +74,15 @@ skills/scroll-scrubbed-visual-sequence
skills/scroll-scrubbed-word-reveal
skills/scroll-progress-timeline
# superpowers, vendored (plugins.lock.json 'superpowers')
skills/brainstorming
skills/writing-plans
skills/subagent-driven-development
skills/test-driven-development
skills/requesting-code-review
skills/using-git-worktrees
skills/writing-skills
# Impeccable — NOT a symlink: `impeccable skills install --scope=global`
# writes the skill dir (and its ~15 MB engine binary) straight in through the
# ~/.claude/skills symlink. Machine-owned, regenerated by make plugin/update.
@@ -206,6 +215,20 @@ skills-external/scroll-scrubbed-visual-sequence/
skills-external/scroll-scrubbed-word-reveal/
skills-external/scroll-progress-timeline/
# superpowers, vendored (plugins.lock.json 'superpowers') — machine-owned,
# curl'd at the commit pinned in plugins.lock.json by install-plugins.sh
# Step 8e (when absent) and re-fetched at the SAME commit by update-all.sh,
# through the shared lib/vendor-skills.sh helper. Not vendored: this is a
# pin, not a tracked snapshot — bump the commit deliberately to pick up an
# upstream edit.
skills-external/brainstorming/
skills-external/writing-plans/
skills-external/subagent-driven-development/
skills-external/test-driven-development/
skills-external/requesting-code-review/
skills-external/using-git-worktrees/
skills-external/writing-skills/
# 21st.dev skill pack — machine-owned: `21st skills install` output, staged by
# install-plugins.sh Step 8.7 (the installer refuses to write through the
# ~/.claude/skills symlink, so it runs under a throwaway HOME and the skills
+32
View File
@@ -379,6 +379,21 @@ Format follows [Keep a Changelog](https://keepachangelog.com/).
`plugins.lock.json` pin 3.2.0 → 4.1.0 (the CLI only: the skill dist and
the engine binary have their own release tracks). `link.sh` drops
impeccable from `EXTERNAL_SKILLS`; `skills-external/impeccable/` is gone.
- **Superpowers plugin replaced by 7 vendored skills** (tier 2 of the
skill-catalog prune, BDR-105/106). `brainstorming`, `writing-plans`,
`subagent-driven-development`, `test-driven-development`,
`requesting-code-review`, `using-git-worktrees` and `writing-skills` are
curled byte-for-byte from `obra/superpowers` at the v6.4.1 commit
(`5bf4e78011075bcfc0dc295f0724994cd123ee71`) via `lib/vendor-skills.sh`
(new `superpowers` entry in `plugins.lock.json`, `always_on: true`),
linked by `link.sh` like the other externals: always on, no profile lists
them, same as `darwin-skill`. Every `superpowers:<skill>` citer across
`skills/`, `agents/` and `lib/` is renamed to the bare skill name.
`CLAUDE.global.md` Skill routing gains a map for the 4 dropped skills this
config used to reference: `executing-plans` to
`subagent-driven-development`, `finishing-a-development-branch` to
`gitflow finish`, `systematic-debugging` to `/bugfix`,
`verification-before-completion` to the verifier gates.
### Security
- **Ten secret-reader deny rules added**: `sed`, `awk`, `cut`, `tr`,
@@ -433,6 +448,15 @@ Format follows [Keep a Changelog](https://keepachangelog.com/).
with it: the 4 `mcp__magic__*` `permissions.ask` entries (BDR-059), the
`MAGIC_API_KEY` block in `.env.example`, `link.sh`'s missing-key warning,
and the dead `MAGIC_API_KEY=abc123` gitleaks allowlist regex.
- **Superpowers plugin uninstalled**: its 8 other skills
(`executing-plans`, `finishing-a-development-branch`,
`systematic-debugging`, `verification-before-completion`,
`dispatching-parallel-agents`, `receiving-code-review`,
`using-superpowers`, `diagnosing-superpowers`) and its SessionStart
injection (`using-superpowers`, ~3.6 KB every session start) are gone
with it. `lib/profile.sh` no longer protects it; `lib/detect-plugins.sh`
`detect_superpowers` now checks the linked vendored skill instead of the
plugin cache or `claude plugin list`.
### Fixed
- **gstack's shared helper tree was mostly unreachable.** gstack skills
@@ -505,6 +529,14 @@ Format follows [Keep a Changelog](https://keepachangelog.com/).
`21st-ui-build` and `21st-cli-use` still point at the now-`max`-only
21st trio. A Skill call on a parked name fails, and the doctrine
routing in `CLAUDE.global.md` applies instead.
- The 7 vendored superpowers skills are byte-for-byte upstream text, never
edited: their internal `superpowers:<x>` mentions and references to the
8 non-vendored skills stay in the prose (their own text, not ours to
patch). `CLAUDE.global.md` Skill routing carries the map for the 4 of
those this config used to reference. After a rollback that re-installs
the plugin while the 7 symlinks are still linked, delete the
`skills/<7>` symlinks or re-run `make plugin` to avoid duplicate skill
descriptions.
## [1.5.0] — 2026-09-13
+6
View File
@@ -258,6 +258,12 @@ cryptic names.
- Design / UI (build, system, audit, polish) → "Design work" below
- Architecture review → plan-eng-review
- Before /clear or /compact → capitalize; end-of-session ritual → close
- superpowers skills are vendored, called by bare name; an upstream
`superpowers` prefix names the same skill. Not vendored here:
executing-plans → subagent-driven-development
finishing-a-development-branch → `gitflow finish` (human signal)
systematic-debugging → bugfix
verification-before-completion → the verifier gates
- SEO+GEO → seo (GEO only → geo); W3C + WCAG a11y → web-validate;
security audit (secrets, CVE, OWASP) → cso
gstack OFF → its skills (investigate, qa, review, health, retro,
+1 -1
View File
@@ -118,7 +118,7 @@ ctx7 login # optional: OAuth / API key for higher rate limits
| Component | Type | Description | Docs |
|---|---|---|---|
| **Superpowers** | Plugin (required) | Brainstorming, planning, subagent-driven dev, code review, branch finishing. Required by `/init-project` and `/ship-feature`. | [obra/superpowers-marketplace](https://github.com/obra/superpowers-marketplace) |
| **Superpowers skills** | Vendored (7, always on) | brainstorming, writing-plans, subagent-driven development, TDD, code review request, git worktrees, writing-skills — pinned v6.4.1 in plugins.lock.json, no plugin, no session injection | [obra/superpowers](https://github.com/obra/superpowers) |
| **GStack** | Plugin (toggle) | Full-product workflow: UI + design + deploy + browser QA. Skip for backend/CLI projects. | [garrytan/gstack](https://github.com/garrytan/gstack) |
| **GSD v2** | External CLI | Multi-session orchestration: crash recovery, cost tracking, parallel workers, context-fresh execution. | [gsd-build/gsd-2](https://github.com/gsd-build/gsd-2) |
| **RTK** | Plugin (always on) | Code rewrite hook. Zero passive cost. | [rtk-ai/rtk](https://github.com/rtk-ai/rtk) |
+16 -15
View File
@@ -181,8 +181,8 @@ Deploy + QA browser → gstack ON
Next.js/React/Prisma → context7 ON (WARN si absent, pas BLOCK)
Multi-session (>1 jour) → gsd v2 CLI (gsd dans terminal)
Backend/CLI seulement → tout OFF sauf superpowers
Hotfix/quick fix → tout OFF sauf superpowers
Backend/CLI seulement → tout OFF (skills superpowers vendorisés, toujours actifs, 0 t passif)
Hotfix/quick fix → tout OFF (skills superpowers vendorisés, toujours actifs, 0 t passif)
```
**GSD v2** n'est pas un plugin Claude Code — c'est un CLI externe. Il ne consomme pas de tokens passifs. Tu le lances dans un terminal séparé avec `gsd`, puis `/gsd auto` pour le mode autonome.
@@ -586,7 +586,7 @@ ONBOARD COMPLETE: mycli
→ SIGNALS: none (CLI pur)
→ DISABLE: ui-ux-pro-max, gstack, context7
→ KEEP: superpowers
→ (skills superpowers vendorisés, toujours actifs, 0 t passif)
→ COST: ~800t (minimal)
→ ACTION REQUIRED? NO
```
@@ -647,7 +647,7 @@ DO NOT TOUCH:
/plugin-check "CLI Rust, convertisseur de fichiers JSON/CSV/TOML, pas de réseau, pas de frontend"
→ SIGNALS: none (CLI pur, pas de deploy, pas de frontend)
→ KEEP: superpowers
→ (skills superpowers vendorisés, toujours actifs, 0 t passif)
→ DISABLE: ui-ux-pro-max, gstack, context7
→ COST: ~800t (base seulement)
→ ACTION REQUIRED? NO
@@ -748,7 +748,7 @@ Simple à valider. L'architecture proposée est plate, pas de surprise.
**Contexte :** module `services/payment_service.py` dans un projet FastAPI existant. Écrit il y a 2 ans, jamais refactorisé. Violations connues : fonctions de 80 lignes, global state, pas de tests unitaires, logique métier mélangée avec appels HTTP.
**Setup :** projet déjà onboardé (CLAUDE.md présent), superpowers actif, plugins inutiles désactivés.
**Setup :** projet déjà onboardé (CLAUDE.md présent), skills superpowers vendorisés (toujours actifs, 0 t passif), plugins inutiles désactivés.
#### Étape 1 — Analyse avant toute modification
@@ -861,7 +861,7 @@ PROJECT STATUS
CONFIG
Version : v2.5.0
Plugins ON: superpowers, context7 (~1000t)
Plugins ON: context7 (~200t), skills superpowers vendorisés (toujours actifs, 0 t passif)
GSD v2 : installed (2.64.0)
PROJECT
@@ -956,19 +956,20 @@ GSD v2 met à jour le plan dans `.gsd/ROADMAP.md` sans perdre le travail déjà
/plugin-check "Firmware C STM32, bare-metal, pas de réseau, pas de frontend, pas de Docker"
SIGNALS: simple, CLI/embedded
COST: ~800t (superpowers seul)
COST: ~0t (skills superpowers vendorisés, toujours actifs, 0 t passif)
RECOMMENDATIONS:
OK KEEP : superpowers (peut être utile pour brainstorm initial)
DISABLE : ui-ux-pro-max, gstack, context7
NOTE : Pour un firmware vraiment simple (hotfix, modification ciblée),
même superpowers peut être désactivé → ~0t passif
NOTE : skills superpowers (brainstorming, writing-plans...) restent
disponibles par nom bare sans coût passif, même pour un
firmware minimal.
```
**Workflow minimaliste — modification d'un driver existant :**
```
# Pas de /init-project, pas de GSD, pas de superpowers
# Pas de /init-project, pas de GSD ; skills superpowers vendorisés
# (toujours actifs, 0 t passif) mais non invoqués ici
# 1. Comprendre avant de modifier
/analyze src/drivers/uart.c
@@ -992,7 +993,7 @@ OUTPUT:
/ship-feature "Corriger l'accès non-atomique au ring_buffer_head dans l'ISR"
STEP 0b — CLAUDE.md found
STEP 0 — plugin check: superpowers OK (ou désactivé si YOLO mode)
STEP 0 — plugin check: skills superpowers vendorisés (toujours actifs, 0 t passif)
STEP 1 — BRAINSTORM (rapide, contexte déjà clair depuis /analyze):
Design: protéger ring_buffer_head avec __disable_irq()/__enable_irq()
@@ -1015,7 +1016,7 @@ STEP 4 — IMPLEMENT (subagents légers, modifications chirurgicales)
```
**Points clés :**
- `/plugin-check` confirme "superpowers seulement" → aucun plugin inutile actif.
- `/plugin-check` confirme qu'aucun plugin inutile n'est actif (skills superpowers vendorisés, toujours actifs, 0 t passif).
- `/analyze` est particulièrement utile sur du code C bas-niveau : l'analyzer identifie les accès non-atomiques, les race conditions, les violations de normes, **sans proposer de fix**.
- Pour un firmware, le workflow `analyze → ship-feature` peut se réduire à `analyze → edit direct` si la modification est triviale.
- GSD v2 n'est jamais pertinent pour du firmware : les sessions sont courtes et les tâches atomiques.
@@ -1031,7 +1032,7 @@ Prisma / Supabase → context7 ON
"design élaboré" / tokens → ui-ux-pro-max ON
Docker + QA browser → gstack ON
"plusieurs semaines" → gsd v2 CLI
Rust / Python / Go / C → tout OFF sauf superpowers
Rust / Python / Go / C → tout OFF (skills superpowers vendorisés, 0t)
Mobile / Flutter / RN → gstack OFF
Hotfix / script rapide → tout OFF sauf superpowers
Hotfix / script rapide → tout OFF (skills superpowers vendorisés, 0t)
```
+23 -21
View File
@@ -77,7 +77,7 @@ Factors (weighted):
| Infra/deploy | 15% | Local only | Single deploy target | Multi-env, CI/CD, containers, monitoring |
**Score thresholds:**
- **0-30% (simple)**: superpowers only. No gstack, no gsd, no ctx7, no graphify.
- **0-30% (simple)**: superpowers skills only (vendored, always on). No gstack, no gsd, no ctx7, no graphify.
_Examples: site vitrine, landing page, script CLI, simple CRUD._
- **30-60% (moderate)**: + context7 if fast-libs. graphify only once the codebase passes 200 tracked code files (session-start banner informs, the user decides — BDR-097), never at scaffold.
_Examples: blog with auth, dashboard with charts, API with validation._
@@ -143,7 +143,7 @@ ACTION REQUIRED? YES / NO
| `fast-libs` | context7 | — | Doc freshness critical |
| `multi-agent` + `complex-arch` | gsd v2 CLI | — | GSD v2 preferred for multi-session coordination |
| `simple` / single-session | — | gsd, gstack, ui-ux-pro-max | Saves ~3000-5000t |
| `embedded` / firmware | — | all toggles; superpowers optional | workflow: /analyze → /hotfix or /bugfix or /ship-feature |
| `embedded` / firmware | — | all toggles (superpowers skills vendored, always on) | workflow: /analyze → /hotfix or /bugfix or /ship-feature |
| backend/lib/CLI only | — | ui-ux-pro-max, gstack | ~3100t saved |
| small project / hotfix | — | gstack, gsd | Use /hotfix, /bugfix, or /feat |
@@ -174,12 +174,12 @@ When the plugin-advisor detects a `simple` or `hotfix` signal, suggest the appro
| Pair | Relation | Verdict |
|---|---|---|
| gstack ↔ gsd v2 | ✅ Complementary | GStack = full-product CC workflow. GSD v2 = multi-session CLI. Different scopes, no conflict. |
| superpowers ↔ gsd v2 | ✅ Complementary | Superpowers = single-session execution. GSD v2 = multi-session CLI orchestration. No conflict. |
| superpowers ↔ gstack | ✅ Complementary | Used together in /init-project and /ship-feature. Superpowers = engine, GStack = full-product skills. |
| superpowers ↔ gsd v2 | ✅ Complementary | superpowers skills (vendored) = single-session execution. GSD v2 = multi-session CLI orchestration. No conflict. |
| superpowers ↔ gstack | ✅ Complementary | Used together in /init-project and /ship-feature. superpowers skills (vendored) = engine, GStack = full-product skills. |
| context7 ↔ any | ✅ Independent | Doc lookup CLI (ctx7), no workflow overlap. Always safe to combine. |
| plugin-dev ↔ superpowers | ⚠️ Minor overlap | Superpowers can create skills too. Keep plugin-dev only when actively building new plugins/skills. |
| plugin-dev ↔ superpowers | ⚠️ Minor overlap | superpowers skills (vendored) can create skills too (writing-skills). Keep plugin-dev only when actively building new plugins. |
| ui-ux-pro-max ↔ gstack | ✅ Complementary | GStack = deploy/QA layer; ui-ux-pro-max = UI quality layer. Different concerns. |
| pr-review-toolkit ↔ superpowers | ✅ Complementary | superpowers:requesting-code-review and /pr-review-toolkit:review-pr cover different review styles. |
| pr-review-toolkit ↔ superpowers | ✅ Complementary | `requesting-code-review` (vendored superpowers skill) and /pr-review-toolkit:review-pr cover different review styles. |
| rtk ↔ any | ✅ Independent | Hook-only token compression. Zero interaction with any plugin. |
| security-guidance ↔ any | ✅ Independent | Hooks + out-of-band LLM reviews (agentic review on commit/push; Stop diff review disabled by ENABLE_STOP_REVIEW=0). No context injection unless a regex hits. |
@@ -187,15 +187,15 @@ When the plugin-advisor detects a `simple` or `hotfix` signal, suggest the appro
| Project type | Plugins ON | OFF | Passive cost |
|---|---|---|---|
| Backend API / microservice | superpowers, context7 (if fast libs) | ui-ux-pro-max, gstack | ~800t |
| Frontend SPA / SSR | superpowers, ui-ux-pro-max, frontend-design, design-motion-principles, context7 | gstack | ~1400t |
| Full-stack SaaS | superpowers, gstack, ui-ux-pro-max, frontend-design, design-motion-principles, context7 | — | ~4200t |
| CLI tool / library | superpowers | all toggles | ~800t |
| Multi-session large feature | superpowers + gsd v2 CLI (external) | — | ~800t CC |
| Quick fix / hotfix | superpowers | all toggles | ~800t |
| Design system / component lib | superpowers, ui-ux-pro-max, frontend-design, design-motion-principles | gstack, gsd | ~1200t |
| Fast-evolving libs (Next.js etc.) | superpowers, context7 | — | ~1000t |
| Enterprise multi-agent orchestration | superpowers + gsd v2 (external) | plugin-dev | ~800t CC |
| Backend API / microservice | (superpowers skills always on), context7 (if fast libs) | ui-ux-pro-max, gstack | ~0t |
| Frontend SPA / SSR | (superpowers skills always on), ui-ux-pro-max, frontend-design, design-motion-principles, context7 | gstack | ~600t |
| Full-stack SaaS | (superpowers skills always on), gstack, ui-ux-pro-max, frontend-design, design-motion-principles, context7 | — | ~3400t |
| CLI tool / library | (superpowers skills always on) | all toggles | ~0t |
| Multi-session large feature | (superpowers skills always on) + gsd v2 CLI (external) | — | ~0t CC |
| Quick fix / hotfix | (superpowers skills always on) | all toggles | ~0t |
| Design system / component lib | (superpowers skills always on), ui-ux-pro-max, frontend-design, design-motion-principles | gstack, gsd | ~400t |
| Fast-evolving libs (Next.js etc.) | (superpowers skills always on), context7 | — | ~200t |
| Enterprise multi-agent orchestration | (superpowers skills always on) + gsd v2 (external) | plugin-dev | ~0t CC |
> rtk is always on at 0 context tokens; security-guidance is always on and
> costs quota out of band (LLM reviews), not context — both omitted from
@@ -239,8 +239,9 @@ RULE: IF "simple" OR "hotfix":
RULE: IF "embedded" signal (firmware, bare-metal, microcontroller, or Makefile+C without Node/Rust/Go):
→ Disable ALL toggles including gstack, context7, plugin-dev
→ superpowers OPTIONAL: useful for initial design brainstorm on complex drivers,
but unnecessary for single-function patches — user decides
→ superpowers skills stay on (vendored, no toggle): useful for initial
design brainstorm on complex drivers, unnecessary for single-function
patches; just don't invoke them, no disable needed
→ GSD v2 CLI: not recommended (sessions are short, tasks are atomic)
→ Recommend workflow: /analyze <file> → /hotfix (patch) or /bugfix (investigation) or /ship-feature (multi-file)
→ NOTE: print "embedded project detected — minimal plugin footprint recommended"
@@ -251,7 +252,7 @@ RULE: IF plugin-dev ON AND no `skill-creation` signal detected:
RULE: IF `skill-creation` signal:
→ plugin-dev ON (~100t)
→ superpowers ON — required for skill scaffolding
→ superpowers skills (vendored, always on): used for skill scaffolding (writing-skills)
RULE: IF `browser-qa` signal (e2e tests, Playwright/Cypress/Puppeteer in deps):
→ gstack ON — browser automation and QA
@@ -295,8 +296,9 @@ gstack + managed plugins — sessions stay focused and passive token cost drops.
`profile set <name>` actually toggles plugins (`claude plugin enable|disable`)
and external skill packs (delegates to `lib/toggle-external.sh`) — not just
advisory. No MCP server is auto-toggled today. Always-on plugins (`security-guidance`, `superpowers`)
are protected. Managed plugins that `set` may toggle:
advisory. No MCP server is auto-toggled today. Always-on plugins (`security-guidance`)
and the vendored superpowers skills are never toggled by a profile. Managed
plugins that `set` may toggle:
`ui-ux-pro-max@ui-ux-pro-max-skill`, `plugin-dev@claude-code-plugins`,
`pr-review-toolkit@claude-code-plugins`. Other plugins are never auto-toggled.
@@ -321,7 +323,7 @@ toggles the managed plugins like any `set`).
## BLOCK if
- Superpowers not active → install: `claude plugin marketplace add obra/superpowers-marketplace && claude plugin install --scope user superpowers@superpowers-marketplace`
- Superpowers skills missing → `make plugin` (vendors them) then `make link`
- Full-product (UI+deploy+QA) + gstack not installed
## WARN (no block)
+5 -5
View File
@@ -223,9 +223,9 @@ else
fi
if detect_superpowers; then
pass "Superpowers plugin detected"
pass "superpowers skills linked (brainstorming found); per-skill check under Vendored skills"
else
fail "Superpowers not detected — orchestrators (/init-project, /ship-feature) will fail"
fail "superpowers skills not linked — run: make plugin && make link"
fi
if detect_context7; then
@@ -417,10 +417,10 @@ SKILL_DESC_TOKENS=$((SKILL_DESC_CHARS / 4))
# Plugin passive cost estimates (tokens) — session-start injections and
# hook prompts that never show up as a skill description above. gstack,
# context7 (find-docs) and graphifyy dropped 2026-09-28 (skill-catalog
# prune): their skills sit under ~/.claude/skills and are already counted
# by the stats above — a separate constant here double-counted them.
# prune); superpowers dropped the same day (tier 2, vendored instead):
# their skills sit under ~/.claude/skills and are already counted by the
# stats above — a separate constant here double-counted them.
PLUGIN_TOKENS=0
if detect_superpowers 2>/dev/null; then PLUGIN_TOKENS=$((PLUGIN_TOKENS + 1500)); fi
if detect_uiux_pro_max 2>/dev/null; then PLUGIN_TOKENS=$((PLUGIN_TOKENS + 670)); fi
TOTAL_TOKENS=$((CLAUDE_MD_TOKENS + SKILL_DESC_TOKENS + PLUGIN_TOKENS))
+2 -1
View File
@@ -118,8 +118,9 @@ esac
# Quick passive token cost estimate
# Only count plugins that are ACTIVE (detected as ON), not just installed
# superpowers dropped 2026-09-28 (tier 2 of the skill-catalog prune): its
# 7 vendored skills are counted by the skill catalog, not a plugin cost.
_passive_t=0
detect_superpowers 2>/dev/null && _passive_t=$((_passive_t + 800))
# Token costs for toggle plugins — map display name to cost
declare -A _plugin_costs=(
+19 -17
View File
@@ -487,8 +487,8 @@ install_plugin() {
# copies the plugin into ~/.claude/plugins/cache — it does NOT register
# it in settings.json's enabledPlugins map. Without an explicit enable,
# the plugin sits dormant. Use this for plugins that should be ALWAYS ON
# (security-guidance, superpowers). Idempotent: skips if already
# present in enabledPlugins.
# (security-guidance). Idempotent: skips if already present in
# enabledPlugins.
enable_plugin() {
local name="$1"
local source="$2"
@@ -531,13 +531,10 @@ install_plugin "pr-review-toolkit" "claude-code-plugins"
echo ""
# Superpowers (always on)
info "Adding Superpowers marketplace..."
claude plugin marketplace add obra/superpowers-marketplace 2>/dev/null || true
install_plugin "superpowers" "superpowers-marketplace"
enable_plugin "superpowers" "superpowers-marketplace"
echo ""
# Superpowers plugin removed 2026-09-28 (tier 2 of the skill-catalog prune):
# its 7 wired skills are vendored in Step 8e (plugins.lock.json
# 'superpowers'); a still-cached plugin is uninstalled by hand once
# (claude plugin uninstall superpowers@superpowers-marketplace), never here
# UI/UX Pro Max (toggle)
info "Adding UI/UX Pro Max marketplace..."
@@ -909,21 +906,25 @@ fi
echo ""
# ── Step 8e: Agent Skills (addyosmani/agent-skills) + Mengto scroll
# skills (MengTo/Skills) — both commit-pinned, vendored the emil-design-eng
# way (curl → skills-external/<name>/, symlinked by link.sh) through the
# shared lib/vendor-skills.sh helper. Shas/paths/file-lists live in
# plugins.lock.json ("agent-skills" / "mengto-skills" entries), never
# hardcoded here.
echo "── Step 8e: Agent Skills + Mengto scroll skills (pinned commit) ──"
# skills (MengTo/Skills) + superpowers (obra/superpowers) — all
# commit-pinned, vendored the emil-design-eng way (curl →
# skills-external/<name>/, symlinked by link.sh) through the shared
# lib/vendor-skills.sh helper. Shas/paths/file-lists live in
# plugins.lock.json ("agent-skills" / "mengto-skills" / "superpowers"
# entries), never hardcoded here.
echo "── Step 8e: Agent Skills + Mengto scroll skills + superpowers (pinned commit) ──"
echo ""
# shellcheck source=lib/vendor-skills.sh disable=SC1091
source "$REPO/lib/vendor-skills.sh"
EXT_SKILL_NAMES=(observability-and-instrumentation deprecation-and-migration
ci-cd-and-automation scroll-world-storytelling build-threejs-scroll-worlds
scroll-scrubbed-visual-sequence scroll-scrubbed-word-reveal
scroll-progress-timeline)
scroll-progress-timeline brainstorming writing-plans
subagent-driven-development test-driven-development
requesting-code-review using-git-worktrees writing-skills)
vendor_pinned_skills agent-skills
vendor_pinned_skills mengto-skills
vendor_pinned_skills superpowers
for _ext_skill in "${EXT_SKILL_NAMES[@]}"; do
if [ -L "$HOME/.claude/skills/$_ext_skill" ]; then
ok "$_ext_skill symlink OK"
@@ -1207,7 +1208,7 @@ echo ""
echo " ALWAYS ON (installed at user scope):"
echo " ✅ security-guidance — regex hints on Edit/Write + out-of-band LLM reviews on commit/push (Stop review off via ENABLE_STOP_REVIEW=0; quota, not context) [claude-code-plugins]"
echo " ✅ rtk — token compression hook (0 tokens)"
echo " ✅ superpowers — brainstorm/plan/implement/debug workflow"
echo " ✅ superpowers skills — 7 vendored (brainstorming, writing-plans, subagent-driven-development, test-driven-development, requesting-code-review, using-git-worktrees, writing-skills), pinned v6.4.1, curl → symlink, no plugin, no session injection"
echo ""
echo " TOGGLE (plugin state = settings.json enabledPlugins; skills/CLIs = profiles):"
echo " 🔄 gstack — disabled by default (toggle: lib/toggle-external.sh enable gstack)"
@@ -1232,6 +1233,7 @@ echo " Frontend Design at: ~/.claude/skills/frontend-design/ (symlink → skill
echo " Design Motion Principles at: ~/.claude/skills/design-motion-principles/ (symlink → skills-external)"
echo " Agent Skills trio at: ~/.claude/skills/{observability-and-instrumentation,deprecation-and-migration,ci-cd-and-automation}/ (symlink → skills-external)"
echo " Mengto scroll skills at: ~/.claude/skills/{scroll-world-storytelling,build-threejs-scroll-worlds,scroll-scrubbed-visual-sequence,scroll-scrubbed-word-reveal,scroll-progress-timeline}/ (symlink → skills-external)"
echo " Superpowers skills at: ~/.claude/skills/{brainstorming,writing-plans,subagent-driven-development,test-driven-development,requesting-code-review,using-git-worktrees,writing-skills}/ (symlink → skills-external)"
echo " npx skills at: ~/.agents/skills/ (symlinked into ~/.claude/skills/)"
echo ""
echo " → Restart Claude Code — plugins load automatically"
+4 -3
View File
@@ -103,9 +103,10 @@ backfill, if ever wanted, is `/prune-memory` passe D — never this snippet.
## ORDERING (orchestrators only)
`superpowers:brainstorming` / `writing-plans` are external skills — we cannot make them
read our registries. So this runs BEFORE them, pre-loading the disposition into the plan
they form. Mirror of capitalize-commit running BEFORE finishing-a-development-branch: there
`brainstorming` / `writing-plans` (vendored superpowers skills) are external skills — we
cannot make them read our registries. So this runs BEFORE them, pre-loading the
disposition into the plan they form. Mirror of capitalize-commit running BEFORE
`gitflow finish` (the upstream finishing-a-development-branch is not vendored): there
the memory commit must precede integration; here the memory read must precede planning.
## NO-OP / IDEMPOTENT
+10 -8
View File
@@ -17,9 +17,10 @@ code already committed.
- Inline-commit flows (feat / hotfix / bugfix / commit-change): run it right
after writing the entries, on the current branch.
- Orchestrators that integrate via `superpowers:finishing-a-development-branch`
(ship-feature / init-project): run it BEFORE the FINISH step — otherwise the
memory commit strands outside the merge/PR. See ORDERING.
- Orchestrators that integrate via `gitflow finish` (the upstream
finishing-a-development-branch is not vendored; ship-feature / init-project):
run it BEFORE the FINISH step — otherwise the memory commit strands outside
the merge/PR. See ORDERING.
This snippet commits whatever is PENDING under `.claude/memory` + `.claude/tasks`;
it does NOT decide content. A flow whose gate wrote only a journal line yields a
@@ -65,11 +66,12 @@ no-match pathspec is filtered, not fatal).
## ORDERING (orchestrators only)
`finishing-a-development-branch` may merge-and-delete the branch or push a PR. A
memory commit created AFTER it lands outside the integrated history — stranded
on the PR path. So in ship-feature / init-project this snippet runs BEFORE
FINISH. The code commits already exist (implementation step), so the entries'
hash references are valid at this point.
`finishing-a-development-branch` (upstream superpowers skill, not vendored
here; `gitflow finish` is the only integration path) may merge-and-delete the
branch or push a PR. A memory commit created AFTER it lands outside the
integrated history — stranded on the PR path. So in ship-feature / init-project
this snippet runs BEFORE FINISH. The code commits already exist (implementation
step), so the entries' hash references are valid at this point.
## WHAT THIS DOES NOT DO
+4 -8
View File
@@ -16,14 +16,10 @@ detect_rtk() {
}
detect_superpowers() {
# Fast check: filesystem (plugin cache)
local cache_dir="$HOME/.claude/plugins/cache"
if [ -d "$cache_dir" ]; then
compgen -G "$cache_dir"/*superpowers* &>/dev/null && return 0
fi
# Slow fallback: CLI (only if fast check fails)
claude plugin list 2>/dev/null | grep -qi "superpowers" && return 0
return 1
# superpowers = 7 vendored skills since 2026-09-28; the plugin is gone.
# One file test on the linked vendored skill: proves vendored AND
# linked in one shot — no plugin cache glob, no `claude plugin list`.
[ -f "$HOME/.claude/skills/brainstorming/SKILL.md" ]
}
+5 -4
View File
@@ -81,10 +81,11 @@ do NOT bypass them:
## ORDERING (orchestrators)
`finishing-a-development-branch` merges/pushes COMMITTED history only — it never commits
working-tree changes. A doc patch left uncommitted (or committed AFTER it) never reaches
the merge/PR. So this snippet runs BEFORE FINISH: the doc commit lands on the branch FINISH
integrates. Consumption is MECHANICAL (LRN-057 case a, like the memory commit) — production
`finishing-a-development-branch` (upstream superpowers skill, not vendored here;
`gitflow finish` is the only integration path) merges/pushes COMMITTED history only — it
never commits working-tree changes. A doc patch left uncommitted (or committed AFTER it)
never reaches the merge/PR. So this snippet runs BEFORE FINISH: the doc commit lands on
the branch FINISH integrates. Consumption is MECHANICAL (LRN-057 case a, like the memory commit) — production
on the branch = consumption by the merge, automatic.
## ACKNOWLEDGMENTS (conscious, not glossed)
+53 -20
View File
@@ -5,8 +5,8 @@
# EXTERNAL_SKILLS array). doctor.sh's "GStack submodule" section only
# covers the gstack submodule — this covers the OTHER external skill
# packs (emil-design-eng, the agent-skills trio, the five Mengto scroll
# skills, and any name link.sh links with no lock entry at all, e.g.
# frontend-design, design-motion-principles).
# skills, the seven superpowers skills, and any name link.sh links with
# no lock entry at all, e.g. frontend-design, design-motion-principles).
#
# One entry point, `check_vendored_skills <repo> <claude_home>
# [profile_file]`, sourced and called by doctor.sh. Two things checked
@@ -21,7 +21,9 @@
# is passed — the "could not resolve the active profile" case),
# the <claude_home>/skills/<name> symlink points at
# <repo>/skills-external/<name>. A name absent from the profile is
# reported parked, not failed.
# reported parked, not failed — unless its lock entry is
# "always_on": true (the superpowers entry is), in which case the
# symlink is checked regardless of the profile (see _dv_check_link).
#
# Lock parsing via python3 argv (never string-spliced) — same pattern as
# lib/vendor-skills.sh's _vendor_read_lock. link.sh's EXTERNAL_SKILLS
@@ -61,11 +63,14 @@ fi
# _dv_lock_expectations <lockfile> — prints "<name>\t<file>" for every
# skill named under a plugins.lock.json entry whose "managed_by" is
# "curl": a bare list defaults each name to ["SKILL.md"]; a dict names
# its own per-skill file list; an entry with neither (the
# emil-design-eng single-file "path" shape) is itself the skill name,
# file "SKILL.md" (the literal "path" value is upstream layout, not the
# local dest — never used here). Reads the lockfile via argv only.
# "curl", plus a THIRD column "\t1" when that entry is "always_on": true
# (the superpowers entry is) — read by _dv_is_always_on, ignored by the
# $1==n {print $2} awk in _dv_check_files: a bare list defaults each name
# to ["SKILL.md"]; a dict names its own per-skill file list; an entry
# with neither (the emil-design-eng single-file "path" shape) is itself
# the skill name, file "SKILL.md" (the literal "path" value is upstream
# layout, not the local dest — never used here). Reads the lockfile via
# argv only.
# Every curl-managed entry's shape is validated ("skills" null, a list
# of str, or a dict of str -> list of str; "path" a str when present)
# BEFORE it is used, so a malformed entry is the same clean failure as
@@ -118,12 +123,13 @@ for key, entry in data.items():
sys.exit(1)
if not valid_skills(skills):
sys.exit(1)
suffix = "\t1" if entry.get("always_on") is True else ""
if skills is None:
print(f"{key}\tSKILL.md")
print(f"{key}\tSKILL.md{suffix}")
continue
for name, files in skill_files(skills).items():
for file in files:
print(f"{name}\t{file}")
print(f"{name}\t{file}{suffix}")
PY
}
@@ -196,16 +202,30 @@ allowlist — skipped"
[ "$all_ok" -eq 1 ]
}
# _dv_check_link <claude_home> <repo> <name> <profile_file> — when
# <profile_file> is non-empty and does not list <name>, reports it
# parked (info), not failed. Otherwise (listed, or no <profile_file> was
# passed — active profile could not be resolved, every external is then
# expected linked) checks the <claude_home>/skills/<name> symlink points
# at <repo>/skills-external/<name>.
# _dv_is_always_on <name> <lock_out> — true when <lock_out> (the
# "<name>\t<file>[\t1]" lines from _dv_lock_expectations) carries the
# always_on third column for <name>'s lock entry.
_dv_is_always_on() {
local name="$1" lock_out="$2"
awk -F'\t' -v n="$name" '$1 == n && $3 == 1 { found=1 } \
END { exit !found }' <<< "$lock_out"
}
# _dv_check_link <claude_home> <repo> <name> <profile_file> <always_on> —
# when <always_on> is "1" (the name's lock entry is "always_on": true),
# the symlink is checked whatever <profile_file> says — never parked.
# Otherwise, when <profile_file> is non-empty and does not list <name>,
# reports it parked (info), not failed. Otherwise (listed, always_on, or
# no <profile_file> was passed — active profile could not be resolved,
# every external is then expected linked) checks the
# <claude_home>/skills/<name> symlink points at
# <repo>/skills-external/<name>.
_dv_check_link() {
local claude_home="$1" repo="$2" name="$3" profile_file="$4"
local claude_home="$1" repo="$2" name="$3" profile_file="$4" \
always_on="$5"
local link target label
if [ -n "$profile_file" ] && ! _dv_profile_has "$profile_file" "$name"; then
if [ "$always_on" != "1" ] && [ -n "$profile_file" ] \
&& ! _dv_profile_has "$profile_file" "$name"; then
label="$(basename "$profile_file" .profile)"
info "$name: parked by profile $label"
return
@@ -220,6 +240,20 @@ lib/profile.sh apply <profile>)"
fi
}
# _dv_check_name <repo> <claude_home> <name> <profile_file> <lock_out> —
# per-name dispatch for check_vendored_skills's loop: files first (the
# link check runs only when every expected file is present, same as
# before), then the symlink, passing _dv_is_always_on's verdict as
# _dv_check_link's 5th param.
_dv_check_name() {
local repo="$1" claude_home="$2" name="$3" profile_file="$4" lock_out="$5"
local always_on=""
_dv_is_always_on "$name" "$lock_out" && always_on=1
_dv_check_files "$repo" "$name" "$lock_out" \
&& _dv_check_link "$claude_home" "$repo" "$name" "$profile_file" \
"$always_on"
}
# check_vendored_skills <repo> <claude_home> [profile_file] — see the
# file header. Either the lock or link.sh being unreadable (or a
# malformed lock entry — _dv_lock_expectations rc 1) is a warn, never a
@@ -251,7 +285,6 @@ check skipped"
item-name allowlist — skipped"
continue
fi
_dv_check_files "$repo" "$name" "$lock_out" \
&& _dv_check_link "$claude_home" "$repo" "$name" "$profile_file"
_dv_check_name "$repo" "$claude_home" "$name" "$profile_file" "$lock_out"
done <<< "$names"
}
+8 -6
View File
@@ -18,8 +18,10 @@
# and MCPs in the MANAGED_* allowlists are disabled when the profile
# does not list them — nothing outside those lists is ever auto-toggled.
#
# Always-on plugins (never toggled by `set`): security-guidance,
# superpowers + rtk hook + .claude internal. The script refuses to disable
# Always-on plugins (never toggled by `set`): security-guidance + rtk
# hook + .claude internal. superpowers is vendored skills now, not a
# plugin (never in PROTECTED_PLUGINS, never in MANAGED_EXTERNALS — same
# always-on class as darwin-skill). The script refuses to disable
# anything in PROTECTED_PLUGINS.
#
# Usage:
@@ -61,9 +63,10 @@ DEFAULT_PROFILE="full" # profile in force when none is selected (cache absent,
source "$(dirname "${BASH_SOURCE[0]}")/gstack-removed.sh"
# Plugins that are toggle-managed by `set`. Anything NOT in this list is
# never auto-disabled — protects always-on plugins (security-guidance,
# superpowers) and unrelated user plugins. Add a plugin here only when its
# enabled state is meaningfully driven by task type.
# never auto-disabled — protects always-on plugins (security-guidance;
# superpowers is vendored skills now, not a plugin) and unrelated user
# plugins. Add a plugin here only when its enabled state is meaningfully
# driven by task type.
MANAGED_PLUGINS=(
"ui-ux-pro-max@ui-ux-pro-max-skill"
"plugin-dev@claude-code-plugins"
@@ -106,7 +109,6 @@ MANAGED_MCPS=()
# MANAGED_PLUGINS allowlist.)
PROTECTED_PLUGINS=(
"security-guidance@claude-code-plugins"
"superpowers@superpowers-marketplace"
)
GREEN='\033[0;32m'; YELLOW='\033[1;33m'; RED='\033[0;31m'; BLUE='\033[0;34m'; NC='\033[0m'
+26 -7
View File
@@ -17,9 +17,11 @@
# "skills" is neither null/list/dict degrading the same way with no
# Python traceback leaking (LOCK_MALFORMED_ENTRY, rc 0), the
# profile-name allowlist rejecting a path-traversal value
# (REJECTS_BAD_PROFILE_NAME), and the item-name allowlist rejecting a
# (REJECTS_BAD_PROFILE_NAME), the item-name allowlist rejecting a
# link.sh entry with a ".." segment — warned and skipped, not failed
# (REJECTS_BAD_NAME).
# (REJECTS_BAD_NAME), and an "always_on": true lock entry's name, absent
# from the profile and with no symlink, checked (and failed) instead of
# reported parked (ALWAYS_ON_LINK_CHECKED).
set -u
ROOT="$(cd "$(dirname "$0")/../.." && pwd)"
LIB="$ROOT/lib/doctor-vendored.sh"
@@ -57,6 +59,11 @@ cat > "$REPO/plugins.lock.json" <<'JSON'
"dict-entry": {
"managed_by": "curl",
"skills": {"dict-skill": ["SKILL.md", "references/notes.md"]}
},
"always-on-entry": {
"managed_by": "curl",
"always_on": true,
"skills": ["always-on-skill"]
}
}
JSON
@@ -66,25 +73,27 @@ cat > "$REPO/link.sh" <<'SH'
#!/usr/bin/env bash
EXTERNAL_SKILLS=(ok-skill missing-skill dict-skill
active-nolink-skill active-wronglink-skill
parked-skill noprofile-skill)
parked-skill noprofile-skill always-on-skill)
SH
# ── skills-external/ tree: every name's SKILL.md present, except
# missing-skill (nothing at all) and dict-skill's references/notes.md.
# always-on-skill has its SKILL.md too — only its symlink is missing.
for n in ok-skill dict-skill active-nolink-skill active-wronglink-skill \
parked-skill noprofile-skill; do
parked-skill noprofile-skill always-on-skill; do
mkdir -p "$REPO/skills-external/$n"
echo "v1" > "$REPO/skills-external/$n/SKILL.md"
done
# ── claude_home symlinks: ok-skill correct, active-wronglink-skill
# points elsewhere, active-nolink-skill and noprofile-skill have none.
# points elsewhere, active-nolink-skill, noprofile-skill and
# always-on-skill have none.
ln -sf "$REPO/skills-external/ok-skill" "$CLAUDE_HOME/skills/ok-skill"
mkdir -p "$WORK/elsewhere"
ln -sf "$WORK/elsewhere" "$CLAUDE_HOME/skills/active-wronglink-skill"
# ── active.profile: lists everything EXCEPT parked-skill and
# noprofile-skill (both proven absent from it).
# ── active.profile: lists everything EXCEPT parked-skill,
# noprofile-skill and always-on-skill (all three proven absent from it).
cat > "$REPO/active.profile" <<'PROF'
# DESC: fixture profile
ok-skill external
@@ -132,6 +141,16 @@ check_bool SYMLINK_PARKED \
grep -qF 'parked-skill: symlink missing/wrong' \
&& echo 1 || echo 0)"
# ── always-on-skill: absent from active.profile (same as parked-skill)
# but its lock entry is "always_on": true — checked (and failed, no
# symlink) instead of reported parked.
check_bool ALWAYS_ON_LINK_CHECKED \
"$(printf '%s' "$out1" | \
grep -qF 'always-on-skill: symlink missing/wrong' \
&& ! printf '%s' "$out1" | \
grep -qF 'always-on-skill: parked by profile' \
&& echo 1 || echo 0)"
# ── No profile file passed at all: noprofile-skill (absent from
# active.profile, parked above) must now be treated as expected-linked.
out2="$(check_vendored_skills "$REPO" "$CLAUDE_HOME" 2>&1)"
+3
View File
@@ -18,6 +18,9 @@
# `skills` as a bare list defaults every named skill to `["SKILL.md"]` and
# `path` to "skills" (the agent-skills shape); `skills` as a dict carries an
# explicit per-skill file list (references/*, etc.) and `path` is required.
# `"always_on": true` (optional) is ignored by this helper (fetch is the
# same either way) — lib/doctor-vendored.sh reads it to expect the
# entry's skills linked regardless of the active profile.
#
# Raw URL: https://raw.githubusercontent.com/<owner>/<repo>/<sha>/<path>/
# <skill>/<file>. VENDOR_BASE_URL overrides the "https://…/<repo>" prefix
+3 -1
View File
@@ -79,7 +79,9 @@ EXTERNAL_SKILLS=(emil-design-eng frontend-design design-motion-principles
observability-and-instrumentation deprecation-and-migration ci-cd-and-automation
scroll-world-storytelling build-threejs-scroll-worlds
scroll-scrubbed-visual-sequence scroll-scrubbed-word-reveal
scroll-progress-timeline)
scroll-progress-timeline brainstorming writing-plans
subagent-driven-development test-driven-development
requesting-code-review using-git-worktrees writing-skills)
for _ext_skill in "${EXTERNAL_SKILLS[@]}"; do
if [ -d "$REPO/skills-external/$_ext_skill" ]; then
if [ -L "$CLAUDE/skills/$_ext_skill" ] && [ "$(readlink "$CLAUDE/skills/$_ext_skill")" = "$REPO/skills-external/$_ext_skill" ]; then
+17
View File
@@ -64,6 +64,23 @@
"managed_by": "curl",
"note": "Five scroll-choreography skills from MengTo/Skills (agent-skills/web-design), vendored the agent-skills way but with an explicit per-skill file list (SKILL.md + REFERENCES.md, or references/*.md + references/scroll-conductor.js for build-threejs-scroll-worlds) instead of the SKILL.md-only default. Never vendored: demo/, agents/, or any binary asset upstream ships alongside each skill. Text-only, byte-for-byte copies (Codex-isms in the source text stay). Bump the commit deliberately to pick up an upstream edit; install-plugins.sh Step 8e and update-all.sh 7.3 both read it from here via lib/vendor-skills.sh's vendor_pinned_skills(), never hardcoded."
},
"superpowers": {
"source": "https://github.com/obra/superpowers",
"commit": "5bf4e78011075bcfc0dc295f0724994cd123ee71",
"path": "skills",
"skills": {
"brainstorming": ["SKILL.md", "spec-document-reviewer-prompt.md", "visual-companion.md", "scripts/frame-template.html", "scripts/helper.js", "scripts/server.cjs", "scripts/start-server.sh", "scripts/stop-server.sh"],
"writing-plans": ["SKILL.md", "plan-document-reviewer-prompt.md"],
"subagent-driven-development": ["SKILL.md", "implementer-prompt.md", "re-review-prompt.md", "task-reviewer-prompt.md", "scripts/review-package", "scripts/sdd-workspace", "scripts/task-brief"],
"test-driven-development": ["SKILL.md", "writing-good-tests.md"],
"requesting-code-review": ["SKILL.md", "code-reviewer.md"],
"using-git-worktrees": ["SKILL.md"],
"writing-skills": ["SKILL.md", "anthropic-best-practices.md", "examples/CLAUDE_MD_TESTING.md", "graphviz-conventions.dot", "persuasion-principles.md", "render-graphs.js", "testing-skills-with-subagents.md"]
},
"managed_by": "curl",
"always_on": true,
"note": "Seven superpowers skills vendored byte-for-byte at the v6.4.1 tag commit (obra/superpowers), always on (no profile lists them). Bump the commit deliberately. Scripts inside run as `bash scripts/<x>`, no exec bit needed. Upstream cross-references to the plugin prefix and to the 8 non-vendored skills stay in the text; CLAUDE.global.md Skill routing maps them."
},
"impeccable": {
"source": "npm:impeccable",
"version": "4.1.0",
-7
View File
@@ -420,7 +420,6 @@
"example-skills@anthropic-agent-skills": false,
"ui-ux-pro-max@ui-ux-pro-max-skill": true,
"security-guidance@claude-code-plugins": true,
"superpowers@superpowers-marketplace": true,
"pr-review-toolkit@claude-code-plugins": false,
"brightdata-plugin@synced": false
},
@@ -431,12 +430,6 @@
"repo": "anthropics/claude-code"
}
},
"superpowers-marketplace": {
"source": {
"source": "github",
"repo": "obra/superpowers-marketplace"
}
},
"ui-ux-pro-max-skill": {
"source": {
"source": "github",
+2 -1
View File
@@ -318,7 +318,8 @@ Then offer to capitalize (per CLAUDE.md): recurring finding patterns →
## TDD note (skill itself)
Baseline-tested per superpowers:writing-skills (2026-06-11, isolated
Baseline-tested per writing-skills (vendored superpowers skill;
2026-06-11, isolated
worktree, no skill): the agent (1) guessed the boundary from the most
recent file date in `.claude/audits/` — wrong file, date-based; (2) wrote
its checkpoint as prose in a dated report — unparseable next run; (3) kept
+1 -1
View File
@@ -512,7 +512,7 @@ The deploy succeeded. Lay the oracle and close out.
## Note on this skill (authoring)
Shaped via `superpowers:writing-skills`. The **cold cross-session resume** is the
Shaped via `writing-skills` (vendored superpowers skill). The **cold cross-session resume** is the
novel form (design §10): the disk alone must carry the deploy across the
out-of-band gap, so `PENDING.json`'s presence marks the wait and STEP 0 resumes
from it without conversation memory — the `audit-delta` "state file is the only
+5 -3
View File
@@ -13,8 +13,10 @@ fan-out, init, `.gitignore` reconcile, the protected-base predicate — are in
and bulletproofs the single judgment call: **`finish` merges only on an explicit
human signal.**
Replaces `finishing-a-development-branch` for gitflow flows — that skill is
single-target and cannot do the directed / fan-out merges below.
Replaces `finishing-a-development-branch` (upstream superpowers skill, not
vendored here; `gitflow finish` is the only integration path) for gitflow
flows — that skill is single-target and cannot do the directed / fan-out
merges below.
## When to Use
@@ -107,7 +109,7 @@ stays human-gated.
## Common Mistakes
- Using `finishing-a-development-branch` for a gitflow merge → it can't do directed/fan-out merges. Use `gitflow finish`.
- Using `finishing-a-development-branch` (upstream superpowers skill, not vendored here) for a gitflow merge → it can't do directed/fan-out merges anyway. Use `gitflow finish`, the only integration path.
- Hand-writing `git merge` instead of `gitflow finish` → loses fan-out, branch delete, base sync.
- Calling `finish` because the work *looks* done → see the gate.
- `git branch -d`/`-D` by hand → denied; a branch the lib refuses to delete still holds work. Keep it, say so.
+4 -4
View File
@@ -68,7 +68,7 @@ contract.
Load `$HOME/.claude/agents/analyzer.md`. Analyze BRIEF: existing code, stack constraints, infra risks, open decisions. Produce ANALYSIS REPORT.
## STEP 3 — DESIGN
Invoke `superpowers:brainstorming` with BRIEF + ANALYSIS REPORT.
Invoke `brainstorming` (vendored superpowers skill) with BRIEF + ANALYSIS REPORT.
Produce DESIGN: stack+versions, full folder tree, module responsibilities, data flow, interfaces (signatures only), config+tooling, test strategy, resolved decisions, prereqs list.
Then run pass B of `$HOME/.claude/lib/contract-interview.md` against the DESIGN
(minus what the BRIEF and the brainstorm settled): one batch before STEP 4;
@@ -179,7 +179,7 @@ This is the deterministic scaffold commit owner (closes BLK-010). The MVP is
implemented on a `feature/*` branch off `develop` (STEP 8).
## STEP 6 — PLAN
Invoke `superpowers:writing-plans` with BRIEF + skeleton.
Invoke `writing-plans` (vendored superpowers skill) with BRIEF + skeleton.
Granular tasks (2-5 min each), exact file paths, TDD: tests before code.
## STEP 6b — CHALLENGE THE PLAN (before the gate)
@@ -212,7 +212,7 @@ Start the MVP feature branch off develop, then implement on it:
```bash
bash "$HOME/.claude/lib/gitflow.sh" start feature mvp
```
Invoke `superpowers:subagent-driven-development` for the per-task implement loop
Invoke `subagent-driven-development` (vendored superpowers skill) for the per-task implement loop
**and** the final whole-branch review **only**. Do NOT run its terminal
`finishing-a-development-branch` step — this orchestrator owns integration via
`gitflow finish` (STEP 11). When SDD's flow reaches "Use
@@ -256,7 +256,7 @@ against the founding contract. Distinct axis from STEP 10 code review
([[LRN-095]]) — both run.
## STEP 10 — CODE REVIEW
Invoke `superpowers:requesting-code-review`. **Model routing (BDR-077):** the
Invoke `requesting-code-review` (vendored superpowers skill). **Model routing (BDR-077):** the
review subagent it dispatches MUST carry `model: "opus"` in the Agent call —
craft review is dispatched judgment, never inherited from the session. Fix
all CRITICAL before proceeding.
+4 -2
View File
@@ -56,8 +56,10 @@ lists items + types:
| `mcp` | advisory — prints manual `claude mcp add …` command (no server is managed today: `MANAGED_MCPS` is empty since 21st.dev moved to a CLI) |
| `cli` | advisory only — reports installed/not-installed |
**Always-on plugins** (`security-guidance`, `superpowers`) are
protected — `set` will refuse to disable them even if the profile omits them.
**Always-on plugins** (`security-guidance`) and the vendored superpowers
skills are never toggled by a profile — `set` will refuse to disable the
plugin even if the profile omits it, and the 7 superpowers skills are
linked outside any profile.
**Managed plugins** that `set` may disable when not in profile:
`ui-ux-pro-max@ui-ux-pro-max-skill`, `plugin-dev@claude-code-plugins`,
`pr-review-toolkit@claude-code-plugins`. Other plugins are never auto-toggled.
+4 -4
View File
@@ -100,7 +100,7 @@ approved at STEP 3 ENRICHES it, and STEP 5's verifier judges the diff against
the ENRICHED contract. This is the only flow where the contract grows mid-run.
## STEP 1 — BRAINSTORM
Invoke `superpowers:brainstorming` — but FEED it the STEP 0d digest as binding context,
Invoke `brainstorming` (vendored superpowers skill) — but FEED it the STEP 0d digest as binding context,
not the raw request alone:
"Feature request: <$ARGUMENTS>.
In-force constraints (must hold): <only the IN-FORCE + ALREADY-SEEN items from 0d's
@@ -114,7 +114,7 @@ Consumption = INPUT INJECTION (we can't modify the external skill; we control it
Refine request into validated design via Socratic questioning. Don't proceed until design approved.
## STEP 2 — PLAN
Invoke `superpowers:writing-plans` with the validated design AND the 0d digest: every task
Invoke `writing-plans` (vendored superpowers skill) with the validated design AND the 0d digest: every task
must be consistent with the in-force constraints; where a task implements or affects one,
note the ID inline. Break design into tasks (2-5 min each). Each task: exact file paths, full code, verification steps.
Then run pass B of `$HOME/.claude/lib/contract-interview.md` against the plan:
@@ -173,7 +173,7 @@ Start the feature branch off develop, then implement on it:
```bash
bash "$HOME/.claude/lib/gitflow.sh" start feature <name>
```
Invoke `superpowers:subagent-driven-development` for the per-task implement loop
Invoke `subagent-driven-development` (vendored superpowers skill) for the per-task implement loop
**and** the final whole-branch review **only**. Do NOT run its terminal
`finishing-a-development-branch` step — this orchestrator owns integration via
`gitflow finish` (STEP 9). When SDD's flow reaches "Use
@@ -234,7 +234,7 @@ conformity + security vs. craft/design) — both run, neither subsumes the
other ([[LRN-095]]).
## STEP 6 — CODE REVIEW
Invoke `superpowers:requesting-code-review`. **Model routing (BDR-077):** the
Invoke `requesting-code-review` (vendored superpowers skill). **Model routing (BDR-077):** the
review subagent it dispatches MUST carry `model: "opus"` in the Agent call —
craft review is dispatched judgment, never inherited from the session. Fix
all CRITICAL before proceeding.
+4 -3
View File
@@ -315,9 +315,10 @@ without that approval — neither this repo's nor any target project's.
## TDD note (skill itself)
Baseline-tested per superpowers:writing-skills (2026-07-04, seeded
fixture, no skill): the agent branched correctly via gitflow and did not
merge, BUT (1) silently rewrote the target TODO (checked boxes,
Baseline-tested per writing-skills (vendored superpowers skill;
2026-07-04, seeded fixture, no skill): the agent branched correctly via
gitflow and did not merge, BUT (1) silently rewrote the target TODO (checked
boxes,
restructured) during "reconcile"; (2) authored BDR/journal registry
entries autonomously; (3) ran security as ad-hoc grep + ruff — no
semgrep, no pinned rulesets; (4) left findings only in its final chat
+7 -3
View File
@@ -377,9 +377,10 @@ else
info "design-motion-principles not installed — skipping"
fi
# ── 7.3. Update Agent Skills + Mengto scroll skills (pinned commit) ──
# Both re-fetched at the SAME pinned commit (never advances the pin) via
# the shared lib/vendor-skills.sh helper — see install-plugins.sh Step 8e.
# ── 7.3. Update Agent Skills + Mengto scroll skills + superpowers
# (pinned commit) — all three re-fetched at the SAME pinned commit
# (never advances the pin) via the shared lib/vendor-skills.sh helper —
# see install-plugins.sh Step 8e.
echo ""
echo "── Updating Agent Skills (addyosmani/agent-skills)..."
# shellcheck source=lib/vendor-skills.sh disable=SC1091
@@ -388,6 +389,9 @@ vendor_pinned_skills agent-skills refresh
echo ""
echo "── Updating Mengto scroll skills (MengTo/Skills)..."
vendor_pinned_skills mengto-skills refresh
echo ""
echo "── Updating superpowers skills (obra/superpowers)..."
vendor_pinned_skills superpowers refresh
# ── Impeccable (design detector + skill + subagents) ──
# Global scope: the installer writes through the ~/.claude/{skills,agents}