refactor: hard-fork GSD -> MSD (Make Software Done)

Mechanical rename produced by scripts/msd-rename.cjs: gsd/Gsd/GSD -> msd/Msd/MSD
across contents and paths, upstream package/repo coordinates -> @golem15/msd-core
and golem15com/msd-core. Deep links into upstream history, sibling upstream
packages, the GSD-2 import feature, CHANGELOG.md and .changeset/ are kept as-is.

Hand edits on top: MSD block-letter banner and logos, LICENSE copyright line,
package/plugin identity, regenerated lockfile, install-tree fixtures, derived
registries and benchmark baseline; migration checksum baseline re-locked
(MSD keeps its own install state, so no install had applied the old sums);
sort-order and regex-escaped expectations in tests adjusted.
This commit is contained in:
Jakub Zych
2026-10-06 01:47:40 +02:00
parent fe069b2a56
commit a9a7a328e6
2763 changed files with 78465 additions and 78434 deletions

View File

@@ -1,8 +1,8 @@
# Installer Migration Architecture
This document defines the migration layer for GSD installs and upgrades.
This document defines the migration layer for MSD installs and upgrades.
It is for contributors who need to retire files, move install surfaces,
rewrite runtime config, or preserve user data while changing how GSD is
rewrite runtime config, or preserve user data while changing how MSD is
installed.
After reading this document, a contributor should be able to add a new
@@ -13,7 +13,7 @@ to protect local user changes.
The installer already handles several upgrade behaviors:
- replacing GSD-managed command, skill, agent, hook, and engine files
- replacing MSD-managed command, skill, agent, hook, and engine files
- backing up locally modified managed files before replacement
- preserving known user-owned artifacts
- cleaning old hook files and hook registrations
@@ -24,7 +24,7 @@ Those behaviors are currently distributed across install branches. That
works for isolated fixes, but it makes feature retirement risky. A future
change can remove a file from the package while leaving stale installed
copies behind, or delete a user-created file because it happens to live
inside a GSD-managed directory.
inside a MSD-managed directory.
The migration layer exists to make upgrade behavior explicit, reviewed, and
repeatable.
@@ -32,7 +32,7 @@ repeatable.
## Design Goals
1. Protect user data by default.
2. Remove stale GSD-managed files when a feature is retired.
2. Remove stale MSD-managed files when a feature is retired.
3. Make destructive actions visible before they run.
4. Record what happened so future installs do not re-run the same migration.
5. Give each runtime the same safety model, even when the concrete files differ.
@@ -51,14 +51,14 @@ repeatable.
**Managed file**
A file that GSD installed and recorded in the install manifest. Managed files
A file that MSD installed and recorded in the install manifest. Managed files
can be replaced automatically when unchanged. If changed locally, they must be
backed up or merged.
**User-owned file**
A file created or maintained by a user workflow or by the user directly. These
files must never be removed just because they sit under a GSD directory.
files must never be removed just because they sit under a MSD directory.
**Unknown file**
@@ -88,8 +88,8 @@ record.
### File Manifest
`gsd-file-manifest.json` remains the ownership baseline. It records the
installed GSD version, install mode, the runtime and scope that wrote it, and
`msd-file-manifest.json` remains the ownership baseline. It records the
installed MSD version, install mode, the runtime and scope that wrote it, and
hashes for distribution-owned files.
```json
@@ -101,8 +101,8 @@ hashes for distribution-owned files.
"runtime": "claude",
"scope": "local",
"files": {
"gsd-core/VERSION": "sha256-hex…",
"commands/gsd-plan-phase.md": "sha256-hex…"
"msd-core/VERSION": "sha256-hex…",
"commands/msd-plan-phase.md": "sha256-hex…"
}
}
```
@@ -110,7 +110,7 @@ hashes for distribution-owned files.
| Field | Meaning |
|---|---|
| `manifestVersion` | Schema version of **this document**. Absent ⇒ version 1, a manifest written before #2872. |
| `version` | The GSD **package** version that wrote the manifest — *not* the schema version. The two are separate fields on purpose. |
| `version` | The MSD **package** version that wrote the manifest — *not* the schema version. The two are separate fields on purpose. |
| `timestamp` | ISO-8601 write time. |
| `mode` | `full` or `minimal`. |
| `runtime` | The runtime this install targeted (`claude`, `codex`, …). Added in schema 2. |
@@ -127,7 +127,7 @@ manifests to two directories that were never merged and never cross-read.
`readInstallManifest` reports `manifestVersion: 1` with `runtime: null` and
`scope: null`, and every consumer treats the absence of those fields as
"not declared", never as "not installed". A `manifestVersion` written by a
*newer* GSD is reported verbatim rather than rejected — two GSD versions on one
*newer* MSD is reported verbatim rather than rejected — two MSD versions on one
machine is a supported state — so consumers branch on `>= 2`, never `=== 2`.
The invariant is strict:
@@ -138,7 +138,7 @@ The invariant is strict:
### Install State
The installer writes `gsd-install-state.json` next to the manifest. It carries
The installer writes `msd-install-state.json` next to the manifest. It carries
migration bookkeeping only — the runtime, scope, version and mode of the
install live in the file manifest above, not here.
@@ -225,13 +225,13 @@ backup, rollback, and reporting.
### remove-managed
Remove a path only when it is known to be GSD-managed and unchanged from the
Remove a path only when it is known to be MSD-managed and unchanged from the
previous manifest, or when the migration provides a purpose-built detector for
an old GSD-owned shape.
an old MSD-owned shape.
Authoring guardrail: every `remove-managed` action must include
`ownershipEvidence` explaining the manifest entry, generated marker, or
purpose-built detector that proves GSD ownership.
purpose-built detector that proves MSD ownership.
Use for retired hooks, old generated agents, deprecated command files, and
stale runtime-specific generated artifacts.
@@ -254,7 +254,7 @@ directory-removal primitive, which the framework intentionally does not
provide (see migration 003's docblock and the 2026-08-07 amendment to
`docs/adr/0008-installer-migration-module.md`) — it exists only to retire a
directory NODE once every file inside it has already been individually proven
GSD-managed (or preserved as user-owned) by other actions in the same
MSD-managed (or preserved as user-owned) by other actions in the same
migration, never to sweep a subtree in one step.
Additional guards beyond emptiness: the target must not be a symlink (never
@@ -291,7 +291,7 @@ The initial executor support is `rewrite-json`: a migration reads JSON through
`readJson(relPath)`, returns the next parsed value in the action, and may set
`deleteIfEmpty: true` when the remaining structure is empty. The executor owns
the disk write, journal entry, rollback snapshot, and runtime/scope filtering.
Use this for legacy JSON config cleanup such as Codex `hooks.json`, where GSD
Use this for legacy JSON config cleanup such as Codex `hooks.json`, where MSD
can prove ownership of individual generated hook commands but not the whole
file.
@@ -322,7 +322,7 @@ Use only from the first-time baseline scanner.
Record a user-owned or unknown file discovered under a known install surface
without mutating it. Unknown files default to this action unless they look like
retired GSD-generated artifacts that need an explicit user choice.
retired MSD-generated artifacts that need an explicit user choice.
Use only from the first-time baseline scanner.
@@ -392,7 +392,7 @@ The same planner powers dry-run and apply. There must not be a separate
### Ownership
Never remove an unknown file. Unknown files are preserved unless a migration
contains a specific detector proving the file is a stale GSD artifact.
contains a specific detector proving the file is a stale MSD artifact.
### Modification Detection
@@ -411,9 +411,9 @@ that proves it is preserved across reinstall and omitted from the manifest.
### Config Files
Runtime config is mixed ownership. GSD may own marker blocks, generated agent
Runtime config is mixed ownership. MSD may own marker blocks, generated agent
sections, or hook entries, but it does not own the whole file unless the file
was created as a GSD-only file. Config migrations should remove or rewrite
was created as a MSD-only file. Config migrations should remove or rewrite
only the owned portion.
## Runtime Configuration Contract Registry
@@ -424,35 +424,35 @@ Last upstream documentation check: 2026-05-11. Kimi CLI was rechecked on
This registry is the source of truth for migrations that touch host runtime
configuration. Each row records:
- **What:** the GSD invocation, agent, skill, rule, hook, or config surface
- **What:** the MSD invocation, agent, skill, rule, hook, or config surface
- **Where:** the global and local roots the installer targets
- **When:** install, upgrade, uninstall, and migration touch points
- **Who:** the ownership boundary for surrounding user config
- **Why:** the upstream loader contract or current GSD compatibility shim
- **Why:** the upstream loader contract or current MSD compatibility shim
Migration authors must read the matching row before producing a
`rewrite-config`, `move-managed`, or destructive cleanup action. If upstream
docs change, update this registry, update `docs/ARCHITECTURE.md`, and add tests
for the new shape before changing migration behavior.
| Runtime | What GSD installs | Where GSD installs it | Config ownership boundary | Upstream contract snapshot |
| Runtime | What MSD installs | Where MSD installs it | Config ownership boundary | Upstream contract snapshot |
| --- | --- | --- | --- | --- |
| Claude Code | Global skills in `skills/gsd-*/SKILL.md`; local slash commands in `commands/gsd/*.md`; agents in `agents/gsd-*.md`; hooks in `hooks/`; `settings.json` registrations | Global `CLAUDE_CONFIG_DIR` or `~/.claude`; local `./.claude` | GSD owns only generated skills, local commands, `gsd-*` agents, hook files, and GSD hook/statusLine entries in `settings.json` | [Slash commands](https://docs.anthropic.com/en/docs/claude-code/slash-commands), [settings](https://docs.anthropic.com/en/docs/claude-code/settings), [hooks](https://docs.anthropic.com/en/docs/claude-code/hooks), [subagents](https://docs.anthropic.com/en/docs/claude-code/sub-agents); docs not versioned, checked 2026-05-11 |
| OpenCode | Flat markdown commands in `commands/gsd-*.md` (plural — OpenCode discovers slash commands from `commands/`, not the legacy singular `command/`, #2329); agents in `agents/gsd-*.md`; config updates in `opencode.json` or `opencode.jsonc` | Global `OPENCODE_CONFIG_DIR`, `dirname(OPENCODE_CONFIG)`, `XDG_CONFIG_HOME/opencode`, or `~/.config/opencode`; local `./.opencode` | GSD owns generated command/agent files and GSD entries in structured config only | [Config](https://opencode.ai/docs/config/), [Commands](https://opencode.ai/docs/commands/); docs published 2026-05, checked 2026-07-16 |
| Kilo | OpenCode-style flat markdown commands in `command/gsd-*.md`; agents in `agents/gsd-*.md`; config updates in `kilo.json` or `kilo.jsonc` | Global `KILO_CONFIG_DIR`, `dirname(KILO_CONFIG)`, `XDG_CONFIG_HOME/kilo`, or `~/.config/kilo`; local `./.kilo` | GSD owns generated command/agent files and GSD entries in structured config only | [Custom subagents](https://docs.kilo.ai/docs/customize/custom-subagents); docs not versioned, checked 2026-05-11 |
| Kimi CLI | Agent Skills in `skills/gsd-*/SKILL.md`; explicit custom agent YAML/prompt artifacts in `agents/gsd.yaml`, `agents/gsd.md`, and `agents/subagents/gsd-*`; `gsd-core/` payload files referenced by generated skills; manifest, pristine, local-patch, and migration journal files from the normal installer safety pipeline | Global `KIMI_CONFIG_DIR`, explicit `--config-dir`, or first-existing generic skills root: `~/.config/agents` when `~/.config/agents/skills` exists or no generic skills root exists yet, otherwise `~/.agents` when `~/.agents/skills` exists and `~/.config/agents/skills` does not; `KIMI_CONFIG_DIR` and `--config-dir` are GSD write-location overrides and arbitrary roots require Kimi-side `--skills-dir` or `extra_skill_dirs` configuration for skill discovery; local `--kimi --local` is guarded and writes no project-level artifacts | GSD owns only generated `skills/gsd-*`, `agents/gsd.*`, `agents/subagents/gsd-*`, installed `gsd-core/` payload files, and manifest/preservation/migration records. GSD does not own Kimi config files, hooks, settings, rules, statusline, update-banner registration, or non-GSD Kimi skills/agents. Reinstall/update must preserve locally modified generated Kimi artifacts through manifest-backed `gsd-local-patches/`; uninstall removes only GSD-owned Kimi artifacts and preserves non-GSD user content. | [Agent Skills](https://moonshotai.github.io/kimi-cli/en/customization/skills.html), [Agents and Subagents](https://moonshotai.github.io/kimi-cli/en/customization/agents.html), [Tools](https://moonshotai.github.io/kimi-code/en/reference/tools.html); docs checked 2026-06-07 |
| Codex | Skills in `skills/gsd-*/SKILL.md`; agents as source markdown plus per-agent TOML in `agents/` (Codex auto-discovers each standalone `agents/gsd-*.toml` — that is the sole role-registration source, #2406); bare `[agents]` dispatch-tuning scalar and hooks in `config.toml` | Global `CODEX_HOME` or `~/.codex`; local `./.codex` | GSD owns generated skills, generated agent TOML, the managed bare `[agents]` scalar table (`max_depth`; no `[agents.gsd-*]` role sections — those were a duplicate registration removed in #2406), `[features].hooks` when added by GSD (canonical; legacy alias `codex_hooks` is recognized and migrated forward, #3566), and GSD hook entries | [Codex config schema](https://developers.openai.com/codex/config-schema.json), [Codex developer docs](https://developers.openai.com/codex/); docs not versioned, checked 2026-05-15; installer compatibility sentinel: Codex 0.130.0 features.hooks key (legacy `codex_hooks` recognized) |
| GitHub Copilot | Skills in `skills/gsd-*/SKILL.md`; agents as `.agent.md`; repository instructions in `copilot-instructions.md` | Global `COPILOT_CONFIG_DIR`, `COPILOT_HOME`, or `~/.copilot`; local `./.github` | GSD owns generated skill/agent files and GSD-authored instruction files; no hook/statusline ownership | [Repository custom instructions](https://docs.github.com/en/copilot/how-tos/configure-custom-instructions/add-repository-instructions), [Copilot CLI custom instructions](https://docs.github.com/en/copilot/how-tos/copilot-cli/add-custom-instructions); GitHub Docs product docs, checked 2026-05-11 |
| Antigravity | Global skills in `~/.gemini/config/skills/gsd-*/SKILL.md` and agents in `~/.gemini/config/agents/` (the machine-local discovery dir, #3738; pre-#3738 installs wrote them under the configHome and migration 010 retires that spot); Gemini-style `settings.json` hooks at the configHome when installed by GSD | Global `ANTIGRAVITY_CONFIG_DIR` or `~/.gemini/antigravity`; local `./.agents` (canonical, #791) or `./.agent` (legacy, recognized for backward-compat) | GSD owns generated skills/agents/hooks and GSD settings entries only | Public Antigravity install/config docs for this file layout were not stable or complete as of 2026-05-11; installer compatibility therefore uses GSD's Gemini-compatible settings policy, documented shim baseline. Fresh installs write to `.agents/` (the Google-Codelabs-documented form); existing `.agent/` installs continue to be detected and served. |
| Cursor | Skills in `skills/gsd-*/SKILL.md`; agents in `agents/`; rule references under `rules/`; lifecycle hooks via `hooks.json` (sessionStart + postToolUse, #777) | Global `CURSOR_CONFIG_DIR` or `~/.cursor`; local `./.cursor` | GSD owns generated skills/agents, GSD rule files or references, and GSD-managed `hooks.json` entries (sentinel `gsd-managed:true`); no statusline ownership | [Cursor rules](https://docs.cursor.com/context/rules); [Cursor hooks](https://docs.cursor.com/context/hooks); docs not versioned, checked 2026-06-07 |
| Windsurf / Devin Desktop | Local slash-command workflows in `workflows/gsd-*.md`; no custom-agent artifact surface | Local workflow directory `./.windsurf/workflows`; global workflow install is intentionally a no-op | GSD owns generated local workflow files only; no hook/statusline ownership | Windsurf workflows are the documented `/` command surface. Workspace workflows live under `.windsurf/workflows/*.md`; global workflow locations are outside GSD's normal user-owned runtime config directory and are not written by the GSD installer. |
| Augment Code | Skills in `skills/gsd-*/SKILL.md`; agents in `agents/` | Global `AUGMENT_CONFIG_DIR` or `~/.augment`; local `./.augment` | GSD owns generated skills/agents only; no hook/statusline ownership | [Augment Agent Skills](https://docs.augmentcode.com/cli/skills), [Augment IDE skills](https://docs.augmentcode.com/using-augment/skills); IDE skills public beta in VS Code 0.789.0+, checked 2026-05-11 |
| Trae | Skills in `skills/gsd-*/SKILL.md`; agents in `agents/`; rule references under `rules/` | Global `TRAE_CONFIG_DIR` or `~/.trae`; local `./.trae` | GSD owns generated skills/agents and GSD rule files or references; no hook/statusline ownership | Public Trae docs expose AI settings and `.rules` announcements, but no stable skills/config API was found as of 2026-05-11; migrations must treat this row as source-limited |
| Qwen Code | Claude-compatible skills in `skills/gsd-*/SKILL.md`; agents in `agents/`; optional common hook/settings integration through GSD | Global `QWEN_CONFIG_DIR` or `~/.qwen`; local `./.qwen` | GSD owns generated skills/agents/hooks and GSD settings entries only | [Qwen commands and skills](https://qwenlm.github.io/qwen-code-docs/en/users/features/commands/); docs last updated 2026-05-06 |
| Hermes Agent | Category skills under `skills/gsd/` with `DESCRIPTION.md` plus nested `gsd-*/SKILL.md`; agents in `agents/`; optional common hook/settings integration through GSD | Global `HERMES_HOME` or `~/.hermes`; local `./.hermes` | GSD owns generated `skills/gsd/` category content, generated agents, and GSD settings entries only | [Hermes configuration](https://hermes-agent.nousresearch.com/docs/user-guide/configuration), [Hermes skills](https://hermes-agent.nousresearch.com/docs/zh-Hans/user-guide/features/skills), [working with skills](https://hermes-agent.nousresearch.com/docs/guides/work-with-skills); docs checked 2026-05-11 |
| CodeBuddy | Skills in `skills/gsd-*/SKILL.md`; agents in `agents/`; optional common hook/settings integration through GSD | Global `CODEBUDDY_CONFIG_DIR` or `~/.codebuddy`; local `./.codebuddy` | GSD owns generated skills/agents/hooks and GSD settings entries only | [CodeBuddy CLI skills](https://www.codebuddy.ai/docs/cli/skills), [CodeBuddy IDE skills](https://www.codebuddy.ai/docs/ide/Features/Skills); docs checked 2026-05-11 |
| pi | A single native extension at `extensions/gsd.js` (registers `/gsd` + the `gsd_invoke` tool programmatically); the shared `hooks/` + `hooks/lib/` bundle the extension spawns as bounded subprocesses; the `gsd-core/` payload. No commands/agents/skills surface (`pluginOnlyInstall`) | Global `~/.pi/agent`; local `./.pi` | GSD owns only the generated extension file, the installed `hooks/`/`hooks/lib/` bundle, and the `gsd-core/` payload. GSD writes **no** pi config: `configFormat: "none"`, `hooksSurface: "none"`, `writesSharedSettings: false` — `~/.pi/agent/settings.json` is entirely user-owned and must never be rewritten, including its `extensions` array. Other users' extensions in `extensions/` are unknown files and are preserved | [pi extension loader](https://github.com/earendil-works/pi/blob/main/packages/coding-agent/src/core/extensions/loader.ts): `discoverExtensionsInDir()` scans `<agentDir>/extensions/` and keeps only names passing `isExtensionFile()` (`.ts`/`.js`); accepted files load through `jiti`, which handles CommonJS and ESM alike, so the suffix — not the module format — is what gates discovery. Explicit paths in `settings.json` bypass the filter. Source read 2026-07-20 against `@earendil-works/pi-coding-agent` 0.80.10 (#2470) |
| Cline | Rule-based integration via `.clinerules` for current installer output | Global `CLINE_CONFIG_DIR` or `~/.cline`; local project root `.clinerules` | GSD owns the generated `.clinerules` file only when it created or manifest-tracked it; no hooks/statusline ownership | [Cline rules](https://docs.cline.bot/customization/cline-rules); docs prefer `.clinerules/` directory and still detect legacy rule files, checked 2026-05-11 |
| Claude Code | Global skills in `skills/msd-*/SKILL.md`; local slash commands in `commands/msd/*.md`; agents in `agents/msd-*.md`; hooks in `hooks/`; `settings.json` registrations | Global `CLAUDE_CONFIG_DIR` or `~/.claude`; local `./.claude` | MSD owns only generated skills, local commands, `msd-*` agents, hook files, and MSD hook/statusLine entries in `settings.json` | [Slash commands](https://docs.anthropic.com/en/docs/claude-code/slash-commands), [settings](https://docs.anthropic.com/en/docs/claude-code/settings), [hooks](https://docs.anthropic.com/en/docs/claude-code/hooks), [subagents](https://docs.anthropic.com/en/docs/claude-code/sub-agents); docs not versioned, checked 2026-05-11 |
| OpenCode | Flat markdown commands in `commands/msd-*.md` (plural — OpenCode discovers slash commands from `commands/`, not the legacy singular `command/`, #2329); agents in `agents/msd-*.md`; config updates in `opencode.json` or `opencode.jsonc` | Global `OPENCODE_CONFIG_DIR`, `dirname(OPENCODE_CONFIG)`, `XDG_CONFIG_HOME/opencode`, or `~/.config/opencode`; local `./.opencode` | MSD owns generated command/agent files and MSD entries in structured config only | [Config](https://opencode.ai/docs/config/), [Commands](https://opencode.ai/docs/commands/); docs published 2026-05, checked 2026-07-16 |
| Kilo | OpenCode-style flat markdown commands in `command/msd-*.md`; agents in `agents/msd-*.md`; config updates in `kilo.json` or `kilo.jsonc` | Global `KILO_CONFIG_DIR`, `dirname(KILO_CONFIG)`, `XDG_CONFIG_HOME/kilo`, or `~/.config/kilo`; local `./.kilo` | MSD owns generated command/agent files and MSD entries in structured config only | [Custom subagents](https://docs.kilo.ai/docs/customize/custom-subagents); docs not versioned, checked 2026-05-11 |
| Kimi CLI | Agent Skills in `skills/msd-*/SKILL.md`; explicit custom agent YAML/prompt artifacts in `agents/msd.yaml`, `agents/msd.md`, and `agents/subagents/msd-*`; `msd-core/` payload files referenced by generated skills; manifest, pristine, local-patch, and migration journal files from the normal installer safety pipeline | Global `KIMI_CONFIG_DIR`, explicit `--config-dir`, or first-existing generic skills root: `~/.config/agents` when `~/.config/agents/skills` exists or no generic skills root exists yet, otherwise `~/.agents` when `~/.agents/skills` exists and `~/.config/agents/skills` does not; `KIMI_CONFIG_DIR` and `--config-dir` are MSD write-location overrides and arbitrary roots require Kimi-side `--skills-dir` or `extra_skill_dirs` configuration for skill discovery; local `--kimi --local` is guarded and writes no project-level artifacts | MSD owns only generated `skills/msd-*`, `agents/msd.*`, `agents/subagents/msd-*`, installed `msd-core/` payload files, and manifest/preservation/migration records. MSD does not own Kimi config files, hooks, settings, rules, statusline, update-banner registration, or non-MSD Kimi skills/agents. Reinstall/update must preserve locally modified generated Kimi artifacts through manifest-backed `msd-local-patches/`; uninstall removes only MSD-owned Kimi artifacts and preserves non-MSD user content. | [Agent Skills](https://moonshotai.github.io/kimi-cli/en/customization/skills.html), [Agents and Subagents](https://moonshotai.github.io/kimi-cli/en/customization/agents.html), [Tools](https://moonshotai.github.io/kimi-code/en/reference/tools.html); docs checked 2026-06-07 |
| Codex | Skills in `skills/msd-*/SKILL.md`; agents as source markdown plus per-agent TOML in `agents/` (Codex auto-discovers each standalone `agents/msd-*.toml` — that is the sole role-registration source, #2406); bare `[agents]` dispatch-tuning scalar and hooks in `config.toml` | Global `CODEX_HOME` or `~/.codex`; local `./.codex` | MSD owns generated skills, generated agent TOML, the managed bare `[agents]` scalar table (`max_depth`; no `[agents.msd-*]` role sections — those were a duplicate registration removed in #2406), `[features].hooks` when added by MSD (canonical; legacy alias `codex_hooks` is recognized and migrated forward, #3566), and MSD hook entries | [Codex config schema](https://developers.openai.com/codex/config-schema.json), [Codex developer docs](https://developers.openai.com/codex/); docs not versioned, checked 2026-05-15; installer compatibility sentinel: Codex 0.130.0 features.hooks key (legacy `codex_hooks` recognized) |
| GitHub Copilot | Skills in `skills/msd-*/SKILL.md`; agents as `.agent.md`; repository instructions in `copilot-instructions.md` | Global `COPILOT_CONFIG_DIR`, `COPILOT_HOME`, or `~/.copilot`; local `./.github` | MSD owns generated skill/agent files and MSD-authored instruction files; no hook/statusline ownership | [Repository custom instructions](https://docs.github.com/en/copilot/how-tos/configure-custom-instructions/add-repository-instructions), [Copilot CLI custom instructions](https://docs.github.com/en/copilot/how-tos/copilot-cli/add-custom-instructions); GitHub Docs product docs, checked 2026-05-11 |
| Antigravity | Global skills in `~/.gemini/config/skills/msd-*/SKILL.md` and agents in `~/.gemini/config/agents/` (the machine-local discovery dir, #3738; pre-#3738 installs wrote them under the configHome and migration 010 retires that spot); Gemini-style `settings.json` hooks at the configHome when installed by MSD | Global `ANTIGRAVITY_CONFIG_DIR` or `~/.gemini/antigravity`; local `./.agents` (canonical, #791) or `./.agent` (legacy, recognized for backward-compat) | MSD owns generated skills/agents/hooks and MSD settings entries only | Public Antigravity install/config docs for this file layout were not stable or complete as of 2026-05-11; installer compatibility therefore uses MSD's Gemini-compatible settings policy, documented shim baseline. Fresh installs write to `.agents/` (the Google-Codelabs-documented form); existing `.agent/` installs continue to be detected and served. |
| Cursor | Skills in `skills/msd-*/SKILL.md`; agents in `agents/`; rule references under `rules/`; lifecycle hooks via `hooks.json` (sessionStart + postToolUse, #777) | Global `CURSOR_CONFIG_DIR` or `~/.cursor`; local `./.cursor` | MSD owns generated skills/agents, MSD rule files or references, and MSD-managed `hooks.json` entries (sentinel `msd-managed:true`); no statusline ownership | [Cursor rules](https://docs.cursor.com/context/rules); [Cursor hooks](https://docs.cursor.com/context/hooks); docs not versioned, checked 2026-06-07 |
| Windsurf / Devin Desktop | Local slash-command workflows in `workflows/msd-*.md`; no custom-agent artifact surface | Local workflow directory `./.windsurf/workflows`; global workflow install is intentionally a no-op | MSD owns generated local workflow files only; no hook/statusline ownership | Windsurf workflows are the documented `/` command surface. Workspace workflows live under `.windsurf/workflows/*.md`; global workflow locations are outside MSD's normal user-owned runtime config directory and are not written by the MSD installer. |
| Augment Code | Skills in `skills/msd-*/SKILL.md`; agents in `agents/` | Global `AUGMENT_CONFIG_DIR` or `~/.augment`; local `./.augment` | MSD owns generated skills/agents only; no hook/statusline ownership | [Augment Agent Skills](https://docs.augmentcode.com/cli/skills), [Augment IDE skills](https://docs.augmentcode.com/using-augment/skills); IDE skills public beta in VS Code 0.789.0+, checked 2026-05-11 |
| Trae | Skills in `skills/msd-*/SKILL.md`; agents in `agents/`; rule references under `rules/` | Global `TRAE_CONFIG_DIR` or `~/.trae`; local `./.trae` | MSD owns generated skills/agents and MSD rule files or references; no hook/statusline ownership | Public Trae docs expose AI settings and `.rules` announcements, but no stable skills/config API was found as of 2026-05-11; migrations must treat this row as source-limited |
| Qwen Code | Claude-compatible skills in `skills/msd-*/SKILL.md`; agents in `agents/`; optional common hook/settings integration through MSD | Global `QWEN_CONFIG_DIR` or `~/.qwen`; local `./.qwen` | MSD owns generated skills/agents/hooks and MSD settings entries only | [Qwen commands and skills](https://qwenlm.github.io/qwen-code-docs/en/users/features/commands/); docs last updated 2026-05-06 |
| Hermes Agent | Category skills under `skills/msd/` with `DESCRIPTION.md` plus nested `msd-*/SKILL.md`; agents in `agents/`; optional common hook/settings integration through MSD | Global `HERMES_HOME` or `~/.hermes`; local `./.hermes` | MSD owns generated `skills/msd/` category content, generated agents, and MSD settings entries only | [Hermes configuration](https://hermes-agent.nousresearch.com/docs/user-guide/configuration), [Hermes skills](https://hermes-agent.nousresearch.com/docs/zh-Hans/user-guide/features/skills), [working with skills](https://hermes-agent.nousresearch.com/docs/guides/work-with-skills); docs checked 2026-05-11 |
| CodeBuddy | Skills in `skills/msd-*/SKILL.md`; agents in `agents/`; optional common hook/settings integration through MSD | Global `CODEBUDDY_CONFIG_DIR` or `~/.codebuddy`; local `./.codebuddy` | MSD owns generated skills/agents/hooks and MSD settings entries only | [CodeBuddy CLI skills](https://www.codebuddy.ai/docs/cli/skills), [CodeBuddy IDE skills](https://www.codebuddy.ai/docs/ide/Features/Skills); docs checked 2026-05-11 |
| pi | A single native extension at `extensions/msd.js` (registers `/msd` + the `msd_invoke` tool programmatically); the shared `hooks/` + `hooks/lib/` bundle the extension spawns as bounded subprocesses; the `msd-core/` payload. No commands/agents/skills surface (`pluginOnlyInstall`) | Global `~/.pi/agent`; local `./.pi` | MSD owns only the generated extension file, the installed `hooks/`/`hooks/lib/` bundle, and the `msd-core/` payload. MSD writes **no** pi config: `configFormat: "none"`, `hooksSurface: "none"`, `writesSharedSettings: false` — `~/.pi/agent/settings.json` is entirely user-owned and must never be rewritten, including its `extensions` array. Other users' extensions in `extensions/` are unknown files and are preserved | [pi extension loader](https://github.com/earendil-works/pi/blob/main/packages/coding-agent/src/core/extensions/loader.ts): `discoverExtensionsInDir()` scans `<agentDir>/extensions/` and keeps only names passing `isExtensionFile()` (`.ts`/`.js`); accepted files load through `jiti`, which handles CommonJS and ESM alike, so the suffix — not the module format — is what gates discovery. Explicit paths in `settings.json` bypass the filter. Source read 2026-07-20 against `@earendil-works/pi-coding-agent` 0.80.10 (#2470) |
| Cline | Rule-based integration via `.clinerules` for current installer output | Global `CLINE_CONFIG_DIR` or `~/.cline`; local project root `.clinerules` | MSD owns the generated `.clinerules` file only when it created or manifest-tracked it; no hooks/statusline ownership | [Cline rules](https://docs.cline.bot/customization/cline-rules); docs prefer `.clinerules/` directory and still detect legacy rule files, checked 2026-05-11 |
### Registry Authoring Rules
@@ -461,7 +461,7 @@ for the new shape before changing migration behavior.
tests.
- Do not claim ownership of a mixed config file. Own only generated entries,
generated files, and explicit marker blocks.
- Preserve unknown user config, even when it sits inside a GSD-managed runtime
- Preserve unknown user config, even when it sits inside a MSD-managed runtime
root.
- Add or update the upstream snapshot date and version note when a runtime's
docs, CLI schema, or loader behavior changes.
@@ -491,7 +491,7 @@ It should:
1. read the current manifest if present
2. scan known runtime install surfaces
3. classify files as managed, user-owned, or unknown
4. report stale GSD-looking files that are not in the current manifest
4. report stale MSD-looking files that are not in the current manifest
5. offer actions for ambiguous files instead of deleting them
6. write install state after successful classification
@@ -504,8 +504,8 @@ The baseline action contract is:
- `record-baseline` for manifest-managed files
- `baseline-preserve-user` for known user-owned files and unknown files that do
not look like stale GSD-generated artifacts
- `prompt-user` for stale GSD-looking artifacts that are not manifest-proven
not look like stale MSD-generated artifacts
- `prompt-user` for stale MSD-looking artifacts that are not manifest-proven
This baseline is the escape hatch for old installs that predate full migration
tracking. It gives the user a reviewable redistribution/removal plan without
@@ -526,7 +526,7 @@ When a feature removes or moves install artifacts, the PR must include:
The author must answer these questions in the migration file:
- What old artifact or config shape is being retired?
- How do we prove it is GSD-owned?
- How do we prove it is MSD-owned?
- What happens if the user modified it?
- What happens if it is missing?
- What runtime and scope does it affect?
@@ -540,7 +540,7 @@ Every migration runner change should cover:
- reinstall with matching manifest
- upgrade with pending migration
- locally modified managed file
- unknown file under a GSD directory
- unknown file under a MSD directory
- user-owned file under a wiped directory
- failed apply with rollback
- global and local install scopes when applicable
@@ -571,16 +571,16 @@ Each row corresponds to one migration record in `src/installer-migrations/`.
| ID | File | Introduced In | Scopes | Destructive | Summary |
|----|------|---------------|--------|-------------|---------|
| `2026-05-11-first-time-baseline-scan` | `000-first-time-baseline.cts` | 1.50.0 | global, local | No | Records classification baseline for existing installs before destructive migrations run. |
| `2026-05-11-legacy-orphan-files` | `001-legacy-orphan-files.cts` | 1.50.0 | global, local | Yes | Removes manifest-managed legacy orphan hook files (`hooks/gsd-notify.sh`, `hooks/statusline.js`) retired by the installer. |
| `2026-05-11-codex-legacy-hooks-json` | `002-codex-legacy-hooks-json.cts` | 1.50.0 | global, local | Yes | Removes legacy GSD hook registrations from Codex `hooks.json` after the `config.toml` migration. |
| `2026-06-02-rename-get-shit-done-to-gsd-core` | `003-rename-get-shit-done-to-gsd-core.cts` | 1.2.0 | global, local | Yes | Removes managed files from the stale `get-shit-done/` runtime directory after the rename to `gsd-core/` (#604). User-added files are preserved; emptied directories may remain (framework limitation). <!-- gsd-allow-legacy-name --> |
| `2026-06-09-prune-stale-pristine-get-shit-done` | `004-prune-stale-pristine-snapshots.cts` | 1.4.3 | global, local | Yes | Removes stale `gsd-pristine/get-shit-done/` snapshot files left behind by migration 003, which caused false `verify-reapply-patches` failures (#934). <!-- gsd-allow-legacy-name -->
| `2026-05-11-legacy-orphan-files` | `001-legacy-orphan-files.cts` | 1.50.0 | global, local | Yes | Removes manifest-managed legacy orphan hook files (`hooks/msd-notify.sh`, `hooks/statusline.js`) retired by the installer. |
| `2026-05-11-codex-legacy-hooks-json` | `002-codex-legacy-hooks-json.cts` | 1.50.0 | global, local | Yes | Removes legacy MSD hook registrations from Codex `hooks.json` after the `config.toml` migration. |
| `2026-06-02-rename-get-shit-done-to-msd-core` | `003-rename-get-shit-done-to-msd-core.cts` | 1.2.0 | global, local | Yes | Removes managed files from the stale `get-shit-done/` runtime directory after the rename to `msd-core/` (#604). User-added files are preserved; emptied directories may remain (framework limitation). <!-- msd-allow-legacy-name --> |
| `2026-06-09-prune-stale-pristine-get-shit-done` | `004-prune-stale-pristine-snapshots.cts` | 1.4.3 | global, local | Yes | Removes stale `msd-pristine/get-shit-done/` snapshot files left behind by migration 003, which caused false `verify-reapply-patches` failures (#934). <!-- msd-allow-legacy-name -->
| `2026-07-17-opencode-baseline-commands-dir` | `005-opencode-baseline-commands-dir.cts` | 1.7.0 | global, local | No | Baselines pre-existing files under OpenCode's `commands/` (plural) directory during the first-time scan. #2329 moved OpenCode command materialization to `commands/`, but 000's `RUNTIME_SURFACES.opencode` is a shipped, immutable body that still only names the legacy `command/` alias, so this fix-forward migration widens the scanned surface. OpenCode only; Kilo is unaffected. |
| `2026-07-20-pi-extension-cjs-to-js` | `006-pi-extension-cjs-to-js.cts` | 1.7.1 | global, local | Yes | Removes the stale `extensions/gsd.cjs` left by pre-#2470 pi installs. pi's extension auto-discovery (`isExtensionFile()`) accepts only `.ts`/`.js`, so the `.cjs` file was never loaded and `/gsd` never registered; #2470 renamed the installed artifact to `extensions/gsd.js`, orphaning the old path. Locally modified copies are backed up rather than deleted; an unmanifested `gsd.cjs` is preserved as a user file. pi only. |
| `2026-07-28-retire-config-root-commonjs-marker` | `007-retire-config-root-commonjs-marker.cts` | 1.8.0 | global, local | Yes | Removes `<configRoot>/package.json` when it is exactly the `{"type":"commonjs"}` marker pre-#2544 installs wrote there. #2544 moved that marker into the directories GSD fills (`hooks/`, and the native plugin dir), so an upgraded install would otherwise keep both and stay pinned to CommonJS at a config root GSD no longer writes. Ownership is proven by exact content match, not the manifest (the marker was never manifest-recorded) — a `package.json` with any other content is left untouched, with no backup-and-remove branch. All runtimes; kimi's root marker lives outside `configDir` and is retired by the installer instead. |
| `2026-07-29-cursor-retire-commands-surface` | `008-cursor-retire-commands-surface.cts` | 1.8.1 | global, local | Yes | Removes manifest-managed `commands/gsd-*.md` files from Cursor installs. Cursor already exposes the corresponding skills in the slash menu and to contextual model invocation, so the command copies produced duplicate entries (#2644). Modified files are backed up; unmanifested files are preserved. |
| `2026-08-07-pi-retire-reserved-hooks-dir` | `009-pi-retire-reserved-hooks-dir.cts` | 1.9.2 | global, local | Yes | Removes manifest-managed files under pi's legacy `hooks/` directory and, once empty, the directory itself (and `hooks/lib/`), now that the shared hook bundle installs at `gsd-hooks/` instead. pi's `checkDeprecatedExtensionDirs()` warns on `hooks/`'s mere existence, not its contents, so an emptied shell would keep warning forever without the new `remove-empty-dir` action (#3023). Modified files are backed up; unmanifested files are preserved and keep the directory alive. pi only. |
| `2026-08-26-antigravity-retire-confighome-artifacts` | `010-antigravity-retire-confighome-artifacts.cts` | 1.11.0 | global | Yes | Removes manifest-managed `skills/gsd-*/` and `agents/gsd-*.md` under the Antigravity configHome (`~/.gemini/antigravity{,-ide,-cli}`) and, once empty, the container directories. Antigravity's machine-local discovery scans `~/.gemini/config/{skills,agents}` and does not scan the configHome, so pre-#3738 artifacts were silently ignored; since #3738 the global layout installs both kinds under the `.gemini/config` home override. Modified files are backed up; unmanifested and non-`gsd-` files are preserved and keep their directory alive. Global scope only — the local `.agents` workspace surface is live. Antigravity only. |
| `2026-07-20-pi-extension-cjs-to-js` | `006-pi-extension-cjs-to-js.cts` | 1.7.1 | global, local | Yes | Removes the stale `extensions/msd.cjs` left by pre-#2470 pi installs. pi's extension auto-discovery (`isExtensionFile()`) accepts only `.ts`/`.js`, so the `.cjs` file was never loaded and `/msd` never registered; #2470 renamed the installed artifact to `extensions/msd.js`, orphaning the old path. Locally modified copies are backed up rather than deleted; an unmanifested `msd.cjs` is preserved as a user file. pi only. |
| `2026-07-28-retire-config-root-commonjs-marker` | `007-retire-config-root-commonjs-marker.cts` | 1.8.0 | global, local | Yes | Removes `<configRoot>/package.json` when it is exactly the `{"type":"commonjs"}` marker pre-#2544 installs wrote there. #2544 moved that marker into the directories MSD fills (`hooks/`, and the native plugin dir), so an upgraded install would otherwise keep both and stay pinned to CommonJS at a config root MSD no longer writes. Ownership is proven by exact content match, not the manifest (the marker was never manifest-recorded) — a `package.json` with any other content is left untouched, with no backup-and-remove branch. All runtimes; kimi's root marker lives outside `configDir` and is retired by the installer instead. |
| `2026-07-29-cursor-retire-commands-surface` | `008-cursor-retire-commands-surface.cts` | 1.8.1 | global, local | Yes | Removes manifest-managed `commands/msd-*.md` files from Cursor installs. Cursor already exposes the corresponding skills in the slash menu and to contextual model invocation, so the command copies produced duplicate entries (#2644). Modified files are backed up; unmanifested files are preserved. |
| `2026-08-07-pi-retire-reserved-hooks-dir` | `009-pi-retire-reserved-hooks-dir.cts` | 1.9.2 | global, local | Yes | Removes manifest-managed files under pi's legacy `hooks/` directory and, once empty, the directory itself (and `hooks/lib/`), now that the shared hook bundle installs at `msd-hooks/` instead. pi's `checkDeprecatedExtensionDirs()` warns on `hooks/`'s mere existence, not its contents, so an emptied shell would keep warning forever without the new `remove-empty-dir` action (#3023). Modified files are backed up; unmanifested files are preserved and keep the directory alive. pi only. |
| `2026-08-26-antigravity-retire-confighome-artifacts` | `010-antigravity-retire-confighome-artifacts.cts` | 1.11.0 | global | Yes | Removes manifest-managed `skills/msd-*/` and `agents/msd-*.md` under the Antigravity configHome (`~/.gemini/antigravity{,-ide,-cli}`) and, once empty, the container directories. Antigravity's machine-local discovery scans `~/.gemini/config/{skills,agents}` and does not scan the configHome, so pre-#3738 artifacts were silently ignored; since #3738 the global layout installs both kinds under the `.gemini/config` home override. Modified files are backed up; unmanifested and non-`msd-` files are preserved and keep their directory alive. Global scope only — the local `.agents` workspace surface is live. Antigravity only. |
## Prior Art