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:
@@ -10,7 +10,7 @@
|
||||
* epic #1267; callers import resolvers from model-resolver.cjs directly.
|
||||
*
|
||||
* Dependencies (leaf modules only):
|
||||
* - node:fs / node:path (read the per-install .gsd-runtime marker + project config for the #2297 omit gate)
|
||||
* - node:fs / node:path (read the per-install .msd-runtime marker + project config for the #2297 omit gate)
|
||||
* - ./runtime-name-policy.cjs (resolveRuntimeNameFromCandidates — canonicalize the active runtime)
|
||||
* - ./planning-workspace.cjs (planningDir — workstream/project-aware project-config path)
|
||||
* - ./config-loader.cjs (loadConfig)
|
||||
@@ -48,18 +48,18 @@ const { planningDir } = planningWorkspaceMod;
|
||||
// ─── #2297: per-install runtime identity for the resolve_model_ids:"omit" gate ─
|
||||
//
|
||||
// The installer writes `resolve_model_ids:"omit"` into the SHARED
|
||||
// ~/.gsd/defaults.json for every runtime that lacks native model aliases (#1156).
|
||||
// ~/.msd/defaults.json for every runtime that lacks native model aliases (#1156).
|
||||
// Because that file is machine-wide, a non-Claude install would otherwise poison
|
||||
// a Claude no-project resolution into returning '' — silently defeating Claude's
|
||||
// adaptive tier aliases. The "omit" must therefore apply only when a runtime that
|
||||
// genuinely lacks native aliases is the one resolving.
|
||||
//
|
||||
// In a no-project session there is no `.planning/config.json` (so config.runtime
|
||||
// is null) and GSD_RUNTIME is not exported by gsd-core, so the only reliable
|
||||
// is null) and MSD_RUNTIME is not exported by msd-core, so the only reliable
|
||||
// current-runtime signal is the per-install marker the installer co-locates next
|
||||
// to VERSION at <install>/gsd-core/.gsd-runtime (this file's dir is
|
||||
// <install>/gsd-core/bin/lib). Precedence for the gate: project config.runtime →
|
||||
// GSD_RUNTIME env (manual/CI override + test seam) → install marker → 'claude'.
|
||||
// to VERSION at <install>/msd-core/.msd-runtime (this file's dir is
|
||||
// <install>/msd-core/bin/lib). Precedence for the gate: project config.runtime →
|
||||
// MSD_RUNTIME env (manual/CI override + test seam) → install marker → 'claude'.
|
||||
//
|
||||
// `claude` is currently the ONLY runtime with nativeModelAliases:true; a
|
||||
// registry-parity test guards this set so a future alias-capable runtime fails
|
||||
@@ -76,11 +76,11 @@ const RUNTIMES_WITH_NATIVE_ALIASES: ReadonlySet<string> = new Set(['claude']);
|
||||
// The runtime whose install is actually resolving, canonicalized so an alias or
|
||||
// case variant (e.g. "claude-code"/"Claude") cannot defeat the native-alias
|
||||
// check below (#2297 review). Precedence mirrors resolveRuntime()
|
||||
// (runtime-slash.cts): GSD_RUNTIME env → project config.runtime → per-install
|
||||
// .gsd-runtime marker → 'claude'.
|
||||
// (runtime-slash.cts): MSD_RUNTIME env → project config.runtime → per-install
|
||||
// .msd-runtime marker → 'claude'.
|
||||
function resolveActiveRuntime(config: Record<string, unknown>): string {
|
||||
return resolveRuntimeNameFromCandidates(
|
||||
process.env['GSD_RUNTIME'],
|
||||
process.env['MSD_RUNTIME'],
|
||||
config['runtime'],
|
||||
readInstallRuntimeMarker(),
|
||||
) || 'claude';
|
||||
@@ -88,7 +88,7 @@ function resolveActiveRuntime(config: Record<string, unknown>): string {
|
||||
|
||||
// Did the PROJECT's own config (root `.planning/config.json` or the active
|
||||
// workstream/project override) explicitly set resolve_model_ids to "omit"?
|
||||
// Project config takes precedence over the shared ~/.gsd/defaults.json (#2297
|
||||
// Project config takes precedence over the shared ~/.msd/defaults.json (#2297
|
||||
// out-of-scope guard + #2517 finding #4): an explicit project "omit" is honored
|
||||
// regardless of runtime, whereas an "omit" that came only from the global
|
||||
// defaults is ignored by native-alias runtimes. Workstream/project-scope aware
|
||||
@@ -153,7 +153,7 @@ function _resolveRuntimeTier(config: Record<string, unknown>, tier: string): Tie
|
||||
return resolveTierEntry({
|
||||
// #4505/#4495: TIER SELECTION follows the runtime that is actually
|
||||
// resolving, not whatever the config file happens to say. `config.runtime`
|
||||
// is frequently absent (the runtime is normally known from GSD_RUNTIME or
|
||||
// is frequently absent (the runtime is normally known from MSD_RUNTIME or
|
||||
// the per-install marker), and reading it raw made
|
||||
// `model_profile_overrides.<runtime>.<tier>` silently inert for every
|
||||
// install that did not also write the key by hand.
|
||||
@@ -183,7 +183,7 @@ function _resolveRuntimeTier(config: Record<string, unknown>, tier: string): Tie
|
||||
* `config['runtime']` and recorded that the value policy "must key off the
|
||||
* config the operator wrote, NOT resolveActiveRuntime". That reading turned out
|
||||
* to defeat #4192's own stated principle — that an explicit pin must not be
|
||||
* silently UNPINNED. With `config.runtime` absent and GSD_RUNTIME=opencode, the
|
||||
* silently UNPINNED. With `config.runtime` absent and MSD_RUNTIME=opencode, the
|
||||
* config-keyed read treated the session as claude and collapsed an explicit
|
||||
* `claude-opus-4-8` pin to the bare alias `opus`, which is a Claude-only token
|
||||
* the actual runtime cannot spawn. The runtime is now the ACTIVE one, so the
|
||||
@@ -233,7 +233,7 @@ function resolveClaudeTierOverrideModel(
|
||||
}
|
||||
|
||||
// Reverse of the Claude tier-default IDs, plus the Fable alias which Claude
|
||||
// Code's Agent tool accepts but which is not a GSD model-profile tier (#1133).
|
||||
// Code's Agent tool accepts but which is not a MSD model-profile tier (#1133).
|
||||
const CLAUDE_POLICY_ID_TO_ALIAS: Record<string, string> = {
|
||||
...Object.fromEntries(
|
||||
Object.entries(MODEL_ALIAS_MAP)
|
||||
@@ -254,7 +254,7 @@ function warnModelPolicyUnmappable(agentType: string, policyModel: string, tier:
|
||||
_modelPolicyUnmappableWarned.add(key);
|
||||
// MUST go to stderr — resolve-model's JSON result is parsed from stdout.
|
||||
process.stderr.write(
|
||||
`gsd: warning — model_policy resolved "${policyModel}" for ${agentType}, ` +
|
||||
`msd: warning — model_policy resolved "${policyModel}" for ${agentType}, ` +
|
||||
`but it has no Claude agent alias; using "${tier}" instead.\n`,
|
||||
);
|
||||
}
|
||||
@@ -278,7 +278,7 @@ function warnModelOverrideUnmappable(agentType: string, overrideValue: string):
|
||||
// model's JSON result is parsed from stdout.
|
||||
const safe = overrideValue.length > 64 ? overrideValue.slice(0, 64) + '…' : overrideValue;
|
||||
process.stderr.write(
|
||||
`gsd: warning — model_overrides value "${safe}" for ${agentType} is a fully-qualified ` +
|
||||
`msd: warning — model_overrides value "${safe}" for ${agentType} is a fully-qualified ` +
|
||||
`Claude model ID with no tier alias; passing it through verbatim. Claude Code setups ` +
|
||||
`whose Agent tool accepts only tier aliases will not honor it. (#4192)\n`,
|
||||
);
|
||||
@@ -306,7 +306,7 @@ function _resetModelOverrideWarningCacheForTests(): void {
|
||||
* for, the exact "profile can misrepresent what actually runs" defect #4192
|
||||
* files. The documented contract ("any fully-qualified model ID",
|
||||
* docs/CONFIGURATION.md § Per-Agent Overrides,
|
||||
* gsd-core/references/model-profiles.md § Per-Agent Overrides) is restored:
|
||||
* msd-core/references/model-profiles.md § Per-Agent Overrides) is restored:
|
||||
* the pin is resolved as configured. Values that DO map to a current tier
|
||||
* alias still collapse to that alias — byte-equivalent resolution, the #2041
|
||||
* protection preserved — and a mappable pin never warns.
|
||||
@@ -320,7 +320,7 @@ function mapClaudeOverrideForRuntime(
|
||||
override: string,
|
||||
// The ACTIVE runtime (#4505). Previously the raw `config['runtime']`, which
|
||||
// made an explicit claude pin collapse to a bare alias whenever the runtime
|
||||
// was declared via GSD_RUNTIME or the install marker rather than the config —
|
||||
// was declared via MSD_RUNTIME or the install marker rather than the config —
|
||||
// handing a Claude-only token to a runtime that cannot spawn it.
|
||||
activeRuntime: string | null | undefined,
|
||||
agentType: string,
|
||||
@@ -400,7 +400,7 @@ function resolveModelPolicy(policy: Record<string, unknown> | null | undefined,
|
||||
* #2229 — the profile/phase-type tier for (config, agentType).
|
||||
*
|
||||
* Extracted verbatim from resolveModelInternal's step 2 so the same expression can
|
||||
* answer "which tier did GSD resolve?" without also resolving a model id. The
|
||||
* answer "which tier did MSD resolve?" without also resolving a model id. The
|
||||
* extraction is behaviour-preserving by construction: resolveModelInternal calls
|
||||
* straight back into it.
|
||||
*
|
||||
@@ -438,7 +438,7 @@ function computeProfileTier(config: Record<string, unknown>, agentType: string):
|
||||
|
||||
/**
|
||||
* #2229 — the effective model TIER for (config, agentType), as a signal a workflow can
|
||||
* read: `gsd_run query resolve-model <agent> --pick tier`.
|
||||
* read: `msd_run query resolve-model <agent> --pick tier`.
|
||||
*
|
||||
* Why this is not just "look at the resolved model": on every runtime the installer
|
||||
* configures with `resolve_model_ids: "omit"` — which is every non-Claude runtime, see
|
||||
@@ -561,7 +561,7 @@ function resolveModelInternal(cwd: string, agentType: string): string {
|
||||
// question — which tier map to read, which value policy applies — now uses
|
||||
// the active runtime (#4505).
|
||||
const configRuntime = config['runtime'] as string | null | undefined;
|
||||
// #4505/#4495: GSD_RUNTIME -> config.runtime -> per-install marker -> 'claude'.
|
||||
// #4505/#4495: MSD_RUNTIME -> config.runtime -> per-install marker -> 'claude'.
|
||||
// Never undefined, so the "no runtime declared anywhere" case still resolves
|
||||
// 'claude' and step 3's deliberate claude skip (#1156/#2297/#4192) is
|
||||
// unchanged for every existing install.
|
||||
@@ -605,7 +605,7 @@ function resolveModelInternal(cwd: string, agentType: string): string {
|
||||
// runtime in the project config outranks an omit.
|
||||
// #4717 (user-sanctioned decision a — supersedes #2297 acceptance #4):
|
||||
// a DETECTED runtime now constitutes that opt-in too. The identity
|
||||
// fill in config-loader materializes GSD_RUNTIME / the per-install
|
||||
// fill in config-loader materializes MSD_RUNTIME / the per-install
|
||||
// marker into `config.runtime` when it is empty, so a genuinely
|
||||
// installed non-Claude runtime resolves its own tier map instead of
|
||||
// the omit's "". The shared "omit" remains a Claude protection:
|
||||
@@ -643,9 +643,9 @@ function resolveModelInternal(cwd: string, agentType: string): string {
|
||||
// PROJECT explicitly set it (user intent — project config wins, #2517 finding
|
||||
// #4) OR when the active runtime genuinely lacks native model aliases. Only a
|
||||
// native-alias runtime (Claude) ignores an "omit" that came solely from the
|
||||
// SHARED ~/.gsd/defaults.json — the #2297 poisoning fix — and falls through to
|
||||
// its tier aliases below. Active runtime: GSD_RUNTIME → config.runtime → the
|
||||
// per-install .gsd-runtime marker → 'claude' (canonicalized).
|
||||
// SHARED ~/.msd/defaults.json — the #2297 poisoning fix — and falls through to
|
||||
// its tier aliases below. Active runtime: MSD_RUNTIME → config.runtime → the
|
||||
// per-install .msd-runtime marker → 'claude' (canonicalized).
|
||||
// NOTE: a non-Claude runtime that HAS a populated runtime-tier map already
|
||||
// returned its own model id at step 3 above, before this gate — for those the
|
||||
// explicit-project-omit honoring here is moot (step 3 wins, by #2517 design).
|
||||
|
||||
Reference in New Issue
Block a user