Merge branch 'next' into codex/gsd-onboard
This commit is contained in:
77
scripts/gen-golden-install-parity-zcode.cjs
Normal file
77
scripts/gen-golden-install-parity-zcode.cjs
Normal file
@@ -0,0 +1,77 @@
|
||||
#!/usr/bin/env node
|
||||
'use strict';
|
||||
/**
|
||||
* Standalone golden-fixture generator for tests/golden-install-parity.
|
||||
*
|
||||
* This is a BUILD-TIME generation script — NOT a test run. It replicates the
|
||||
* buildParityManifest logic from tests/golden-install-parity.test.cjs and
|
||||
* captures the zcode fixture so the parity test (which the gsd-test gate runs)
|
||||
* has a committed artifact to compare against. The authoritative test gate
|
||||
* remains `gsd-test run`, never a local `node --test`.
|
||||
*
|
||||
* Usage: node scripts/gen-golden-install-parity-zcode.cjs
|
||||
*/
|
||||
const fs = require('node:fs');
|
||||
const path = require('node:path');
|
||||
const crypto = require('node:crypto');
|
||||
|
||||
const ROOT = path.resolve(__dirname, '..');
|
||||
const { walk, runMinimalInstall, RUNTIME_META } = require(path.join(ROOT, 'tests', 'helpers', 'install-shared.cjs'));
|
||||
const PKG_VERSION = require(path.join(ROOT, 'package.json')).version;
|
||||
const FIXTURE_DIR = path.join(ROOT, 'tests', 'fixtures', 'golden-install-parity');
|
||||
|
||||
const VOLATILE_FILES = new Set([
|
||||
'gsd-file-manifest.json',
|
||||
'gsd-install-state.json',
|
||||
'.gsd-source',
|
||||
'gsd-core/CHANGELOG.md',
|
||||
]);
|
||||
const HOOK_CONFIG_FILES = new Set(['settings.json', 'hooks.json']);
|
||||
const EXCLUDED_PREFIXES = ['gsd-core/bin/lib/'];
|
||||
|
||||
function buildParityManifest(configDir, root) {
|
||||
const allFiles = walk(configDir);
|
||||
const unsorted = {};
|
||||
for (const full of allFiles) {
|
||||
const rel = path.relative(configDir, full).split(path.sep).join('/');
|
||||
if (VOLATILE_FILES.has(rel)) continue;
|
||||
if (HOOK_CONFIG_FILES.has(path.basename(rel))) continue;
|
||||
if (EXCLUDED_PREFIXES.some((p) => rel.startsWith(p))) continue;
|
||||
const content = fs.readFileSync(full);
|
||||
const normalized = content.toString('utf8').split(root).join('<HOME>').split(PKG_VERSION).join('<VERSION>');
|
||||
const hash = crypto.createHash('sha256').update(normalized).digest('hex').slice(0, 16);
|
||||
unsorted[rel] = hash;
|
||||
}
|
||||
const sorted = {};
|
||||
for (const key of Object.keys(unsorted).sort()) sorted[key] = unsorted[key];
|
||||
return sorted;
|
||||
}
|
||||
|
||||
function cleanup(root) {
|
||||
try { fs.rmSync(root, { recursive: true, force: true }); } catch { /* best effort */ }
|
||||
}
|
||||
|
||||
// Regenerate the fixture for every runtime in RUNTIME_META. Needed when a
|
||||
// SHARED gsd-core payload file (e.g. model-catalog.json, capability-registry)
|
||||
// changes content — its hash appears in every runtime's manifest, so all
|
||||
// fixtures must be recaptured together. Usage:
|
||||
// node scripts/gen-golden-install-parity-zcode.cjs [runtime ...]
|
||||
// With no args, regenerates ALL runtimes. With args, only the named runtimes.
|
||||
const targets = process.argv.slice(2).length > 0 ? process.argv.slice(2) : Object.keys(RUNTIME_META);
|
||||
fs.mkdirSync(FIXTURE_DIR, { recursive: true });
|
||||
for (const runtime of targets) {
|
||||
if (!Object.prototype.hasOwnProperty.call(RUNTIME_META, runtime)) {
|
||||
process.stderr.write(`[gen] unknown runtime '${runtime}' (not in RUNTIME_META) — skipping\n`);
|
||||
continue;
|
||||
}
|
||||
const { configDir, root } = runMinimalInstall({ runtime, scope: 'global' });
|
||||
let actual;
|
||||
try {
|
||||
actual = buildParityManifest(configDir, root);
|
||||
} finally {
|
||||
cleanup(root);
|
||||
}
|
||||
const fixturePath = path.join(FIXTURE_DIR, `${runtime}.json`);
|
||||
fs.writeFileSync(fixturePath, JSON.stringify(actual, null, 2) + '\n', 'utf8');
|
||||
process.stdout.write(`[gen] ${runtime}: wrote ${Object.keys(actual).length} file hashes -> ${fixturePath}\n`);
|
||||
}
|
||||
@@ -24,7 +24,7 @@ const PROFILES = [
|
||||
'Researches domain ecosystem before roadmap creation. Produces files in .planning/research/ consumed during roadmap creation. Spawned by /gsd:new-project or /gsd:new-milestone orchestrators.',
|
||||
color: 'cyan',
|
||||
tools:
|
||||
'Read, Write, Bash, Grep, Glob, Skill, WebSearch, WebFetch, mcp__context7__*, mcp__firecrawl__*, mcp__exa__*, mcp__tavily__*, mcp__ref__*, mcp__jina__*, mcp__perplexity__*',
|
||||
'Read, Write, Bash, Grep, Glob, Skill, WebSearch, WebFetch, mcp__context7__*, mcp__plugin_context7_context7__*, mcp__firecrawl__*, mcp__exa__*, mcp__tavily__*, mcp__ref__*, mcp__jina__*, mcp__perplexity__*',
|
||||
requiredIncludes: [
|
||||
'@~/.claude/gsd-core/references/research-documentation-lookup.md',
|
||||
'@~/.claude/gsd-core/references/research-philosophy.md',
|
||||
@@ -46,7 +46,7 @@ const PROFILES = [
|
||||
'Researches how to implement a phase before planning. Produces RESEARCH.md consumed by gsd-planner. Spawned by /gsd:plan-phase orchestrator.',
|
||||
color: 'cyan',
|
||||
tools:
|
||||
'Read, Write, Edit, Bash, Grep, Glob, Skill, WebSearch, WebFetch, mcp__context7__*, mcp__firecrawl__*, mcp__exa__*, mcp__tavily__*, mcp__ref__*, mcp__jina__*, mcp__perplexity__*',
|
||||
'Read, Write, Edit, Bash, Grep, Glob, Skill, WebSearch, WebFetch, mcp__context7__*, mcp__plugin_context7_context7__*, mcp__firecrawl__*, mcp__exa__*, mcp__tavily__*, mcp__ref__*, mcp__jina__*, mcp__perplexity__*',
|
||||
requiredIncludes: [
|
||||
'@~/.claude/gsd-core/references/research-documentation-lookup.md',
|
||||
'@~/.claude/gsd-core/references/research-philosophy.md',
|
||||
@@ -68,7 +68,7 @@ const PROFILES = [
|
||||
description:
|
||||
'Researches a single gray area decision and returns a structured comparison table with rationale. Spawned by discuss-phase advisor mode.',
|
||||
color: 'cyan',
|
||||
tools: 'Read, Bash, Grep, Glob, Skill, WebSearch, WebFetch, mcp__context7__*',
|
||||
tools: 'Read, Bash, Grep, Glob, Skill, WebSearch, WebFetch, mcp__context7__*, mcp__plugin_context7_context7__*',
|
||||
requiredIncludes: [
|
||||
'@~/.claude/gsd-core/references/research-documentation-lookup.md',
|
||||
],
|
||||
@@ -84,7 +84,7 @@ const PROFILES = [
|
||||
'Researches a chosen AI framework\'s official docs to produce implementation-ready guidance — best practices, syntax, core patterns, and pitfalls distilled for the specific use case. Writes the Framework Quick Reference and Implementation Guidance sections of AI-SPEC.md. Spawned by /gsd:ai-integration-phase orchestrator.',
|
||||
color: 'green',
|
||||
tools:
|
||||
'Read, Write, Edit, Bash, Grep, Glob, WebFetch, WebSearch, mcp__context7__*',
|
||||
'Read, Write, Edit, Bash, Grep, Glob, WebFetch, WebSearch, mcp__context7__*, mcp__plugin_context7_context7__*',
|
||||
requiredIncludes: [
|
||||
'@~/.claude/gsd-core/references/research-documentation-lookup.md',
|
||||
],
|
||||
@@ -101,7 +101,7 @@ const PROFILES = [
|
||||
'Researches the business domain and real-world application context of the AI system being built. Surfaces domain expert evaluation criteria, industry-specific failure modes, regulatory context, and what "good" looks like for practitioners in this field — before the eval-planner turns it into measurable rubrics. Spawned by /gsd:ai-integration-phase orchestrator.',
|
||||
color: 'purple',
|
||||
tools:
|
||||
'Read, Write, Edit, Bash, Grep, Glob, WebSearch, WebFetch, mcp__context7__*',
|
||||
'Read, Write, Edit, Bash, Grep, Glob, WebSearch, WebFetch, mcp__context7__*, mcp__plugin_context7_context7__*',
|
||||
requiredIncludes: [
|
||||
'@~/.claude/gsd-core/references/research-documentation-lookup.md',
|
||||
],
|
||||
@@ -117,7 +117,7 @@ const PROFILES = [
|
||||
'Produces UI-SPEC.md design contract for frontend phases. Reads upstream artifacts, detects design system state, asks only unanswered questions. Spawned by /gsd:ui-phase orchestrator.',
|
||||
color: 'purple',
|
||||
tools:
|
||||
'Read, Write, Edit, Bash, Grep, Glob, Skill, WebSearch, WebFetch, mcp__context7__*, mcp__firecrawl__*, mcp__exa__*, mcp__tavily__*, mcp__ref__*, mcp__jina__*',
|
||||
'Read, Write, Edit, Bash, Grep, Glob, Skill, WebSearch, WebFetch, mcp__context7__*, mcp__plugin_context7_context7__*, mcp__firecrawl__*, mcp__exa__*, mcp__tavily__*, mcp__ref__*, mcp__jina__*',
|
||||
requiredIncludes: [
|
||||
'@~/.claude/gsd-core/references/research-documentation-lookup.md',
|
||||
],
|
||||
|
||||
@@ -570,11 +570,13 @@ function main() {
|
||||
// progress (verified: no leaked handle / hang; --test-force-exit exits leaks
|
||||
// cleanly, so the timeout was pure slowness, NOT the leak the kill message guesses).
|
||||
// The per-chunk timeout is sized for a "healthy chunk (~4-5 min)"; keep chunks at
|
||||
// roughly half a shard so each gets its own fresh 600s budget and a fresh node
|
||||
// process (also relieving per-process memory pressure from 170+ files at once).
|
||||
// roughly a third of a shard so each gets its own fresh 600s budget and a fresh
|
||||
// node process (also relieving per-process memory pressure from 170+ files at once).
|
||||
// Lowered from 90 to 60 after #1575 — macOS Node 22 shard 2/3 chunk 2 (~80 files
|
||||
// including state.test.cjs, perf-*, worktree-cleanup) exceeded 600s with 90.
|
||||
const MAX_FILES_PER_CHUNK = process.env.RUN_TESTS_MAX_FILES_PER_CHUNK
|
||||
? Number(process.env.RUN_TESTS_MAX_FILES_PER_CHUNK)
|
||||
: 90;
|
||||
: 60;
|
||||
|
||||
// node:test does not exit until the event loop drains. A unit test that leaks
|
||||
// an open handle (un-terminated Worker, un-killed child_process, ref'd timer)
|
||||
|
||||
Reference in New Issue
Block a user