@opengsd/gsd-core 1.5.0-rc.2 → 1.5.0-rc.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.claude-plugin/plugin.json +1 -1
- package/agents/gsd-advisor-researcher.md +1 -1
- package/agents/gsd-assumptions-analyzer.md +1 -1
- package/agents/gsd-code-fixer.md +1 -1
- package/agents/gsd-code-reviewer.md +1 -1
- package/agents/gsd-codebase-mapper.md +1 -1
- package/agents/gsd-debugger.md +1 -1
- package/agents/gsd-doc-writer.md +1 -1
- package/agents/gsd-eval-auditor.md +1 -1
- package/agents/gsd-executor.md +1 -1
- package/agents/gsd-integration-checker.md +1 -1
- package/agents/gsd-mempalace-curator.md +47 -0
- package/agents/gsd-nyquist-auditor.md +1 -0
- package/agents/gsd-phase-researcher.md +1 -1
- package/agents/gsd-plan-checker.md +1 -1
- package/agents/gsd-planner.md +1 -1
- package/agents/gsd-project-researcher.md +1 -1
- package/agents/gsd-research-synthesizer.md +1 -1
- package/agents/gsd-roadmapper.md +55 -2
- package/agents/gsd-security-auditor.md +1 -0
- package/agents/gsd-ui-auditor.md +1 -1
- package/agents/gsd-ui-checker.md +1 -1
- package/agents/gsd-ui-researcher.md +1 -1
- package/agents/gsd-verifier.md +13 -2
- package/bin/install.js +61 -64
- package/commands/gsd/mempalace-capture.md +71 -0
- package/commands/gsd/mempalace-recall.md +102 -0
- package/commands/gsd/ns-context.md +4 -2
- package/commands/gsd/progress.md +2 -1
- package/gemini-extension.json +1 -1
- package/gsd-core/bin/gsd-tools.cjs +277 -95
- package/gsd-core/bin/lib/active-workstream-store.cjs +6 -0
- package/gsd-core/bin/lib/capability-activation.cjs +86 -0
- package/gsd-core/bin/lib/capability-registry.cjs +1468 -11
- package/gsd-core/bin/lib/capability-state.cjs +128 -21
- package/gsd-core/bin/lib/capability-writer.cjs +354 -0
- package/gsd-core/bin/lib/check-command-router.cjs +328 -1
- package/gsd-core/bin/lib/clusters.cjs +2 -0
- package/gsd-core/bin/lib/command-roster.cjs +19 -0
- package/gsd-core/bin/lib/commands.cjs +33 -10
- package/gsd-core/bin/lib/config-loader.cjs +7 -8
- package/gsd-core/bin/lib/config-schema.cjs +32 -3
- package/gsd-core/bin/lib/config.cjs +81 -26
- package/gsd-core/bin/lib/core.cjs +5 -2
- package/gsd-core/bin/lib/edge-probe.cjs +25 -2
- package/gsd-core/bin/lib/frontmatter.cjs +53 -1
- package/gsd-core/bin/lib/git-base-branch.cjs +194 -0
- package/gsd-core/bin/lib/init.cjs +36 -11
- package/gsd-core/bin/lib/install-profiles.cjs +57 -1
- package/gsd-core/bin/lib/installer-migration-report.cjs +1 -0
- package/gsd-core/bin/lib/loop-resolver.cjs +157 -16
- package/gsd-core/bin/lib/model-resolver.cjs +47 -5
- package/gsd-core/bin/lib/phase.cjs +99 -23
- package/gsd-core/bin/lib/plan-drift-guard.cjs +117 -0
- package/gsd-core/bin/lib/probe-core.cjs +117 -1
- package/gsd-core/bin/lib/profile-output.cjs +45 -4
- package/gsd-core/bin/lib/profile-pipeline-command-router.cjs +138 -0
- package/gsd-core/bin/lib/roadmap-parser.cjs +13 -3
- package/gsd-core/bin/lib/roadmap.cjs +97 -7
- package/gsd-core/bin/lib/runtime-artifact-conversion.cjs +1946 -0
- package/gsd-core/bin/lib/runtime-artifact-layout.cjs +54 -30
- package/gsd-core/bin/lib/runtime-config-adapter-registry.cjs +27 -19
- package/gsd-core/bin/lib/runtime-homes.cjs +26 -20
- package/gsd-core/bin/lib/state-command-router.cjs +15 -3
- package/gsd-core/bin/lib/state-document.cjs +46 -1
- package/gsd-core/bin/lib/state.cjs +461 -94
- package/gsd-core/bin/lib/verify.cjs +92 -8
- package/gsd-core/bin/lib/worktree-safety.cjs +2 -1
- package/gsd-core/bin/shared/config-defaults.manifest.json +1 -2
- package/gsd-core/bin/shared/config-schema.manifest.json +0 -18
- package/gsd-core/bin/shared/model-catalog.json +1 -0
- package/gsd-core/references/edge-probe.md +11 -0
- package/gsd-core/references/loop-hook-dispatch.md +61 -0
- package/gsd-core/references/prohibition-probe-fixtures/01-streak-reminder/expected.json +14 -0
- package/gsd-core/references/prohibition-probe-fixtures/02-clean-utility/expected.json +4 -0
- package/gsd-core/references/prohibition-probe-fixtures/03-multi-prohibition/expected.json +32 -0
- package/gsd-core/references/prohibition-probe.md +248 -0
- package/gsd-core/templates/config.json +1 -1
- package/gsd-core/templates/spec.md +14 -0
- package/gsd-core/workflows/audit-milestone.md +5 -3
- package/gsd-core/workflows/autonomous.md +10 -5
- package/gsd-core/workflows/code-review-fix.md +9 -7
- package/gsd-core/workflows/code-review.md +8 -6
- package/gsd-core/workflows/complete-milestone.md +1 -5
- package/gsd-core/workflows/discuss-phase.md +14 -0
- package/gsd-core/workflows/execute-phase.md +86 -146
- package/gsd-core/workflows/execute-plan.md +21 -6
- package/gsd-core/workflows/help/modes/full.md +7 -1
- package/gsd-core/workflows/new-project.md +3 -3
- package/gsd-core/workflows/next.md +50 -2
- package/gsd-core/workflows/pause-work.md +7 -1
- package/gsd-core/workflows/plan-phase.md +91 -221
- package/gsd-core/workflows/plan-review-convergence.md +14 -4
- package/gsd-core/workflows/pr-branch.md +4 -2
- package/gsd-core/workflows/profile-user.md +3 -1
- package/gsd-core/workflows/progress.md +58 -1
- package/gsd-core/workflows/quick.md +12 -8
- package/gsd-core/workflows/resume-project.md +17 -1
- package/gsd-core/workflows/review.md +19 -2
- package/gsd-core/workflows/secure-phase.md +4 -2
- package/gsd-core/workflows/settings-advanced.md +2 -0
- package/gsd-core/workflows/settings.md +27 -1
- package/gsd-core/workflows/ship.md +58 -5
- package/gsd-core/workflows/spec-phase.md +75 -0
- package/gsd-core/workflows/validate-phase.md +4 -2
- package/gsd-core/workflows/verify-phase.md +14 -4
- package/gsd-core/workflows/verify-work.md +27 -11
- package/hooks/dist/gsd-ensure-canonical-path.js +305 -0
- package/hooks/dist/gsd-statusline.js +1 -1
- package/hooks/dist/managed-hooks-registry.cjs +1 -0
- package/hooks/gsd-ensure-canonical-path.js +305 -0
- package/hooks/gsd-statusline.js +1 -1
- package/hooks/hooks.json +1 -0
- package/hooks/managed-hooks-registry.cjs +1 -0
- package/package.json +5 -4
- package/scripts/affected-tests-lib.cjs +16 -4
- package/scripts/build-hooks.js +7 -0
- package/scripts/changeset/new.cjs +17 -3
- package/scripts/fix-slash-commands.cjs +15 -3
- package/scripts/gen-capability-registry.cjs +373 -49
- package/scripts/gen-inventory-manifest.cjs +1 -4
- package/scripts/gen-loop-host-contract.cjs +55 -0
- package/scripts/issue-version-gate.cjs +140 -0
- package/scripts/lint-allow-test-rule-refs.allowlist.json +327 -0
- package/scripts/lint-allow-test-rule-refs.cjs +162 -0
- package/scripts/lint-test-file-count.allowlist.json +14 -0
- package/scripts/mutation-matrix.cjs +108 -7
- package/scripts/pr-target-policy.cjs +63 -0
- package/scripts/release-tarball-smoke.cjs +7 -1
- package/scripts/research-profiles.cjs +5 -5
- package/scripts/run-tests.cjs +178 -17
|
@@ -74,11 +74,10 @@ AGENT_SKILLS_RESEARCHER=$(gsd_run query agent-skills gsd-phase-researcher)
|
|
|
74
74
|
AGENT_SKILLS_PLANNER=$(gsd_run query agent-skills gsd-planner)
|
|
75
75
|
AGENT_SKILLS_CHECKER=$(gsd_run query agent-skills gsd-plan-checker)
|
|
76
76
|
CONTEXT_WINDOW=$(gsd_run query config-get context_window 2>/dev/null || echo "200000")
|
|
77
|
-
TDD_MODE=$(gsd_run query config-get workflow.tdd_mode 2>/dev/null || echo "false")
|
|
78
77
|
MVP_MODE_CFG=$(gsd_run query config-get workflow.mvp_mode 2>/dev/null || echo "false")
|
|
79
78
|
```
|
|
80
79
|
|
|
81
|
-
When `
|
|
80
|
+
When the tdd capability's `workflow.tdd_mode` is active (resolved via the plan:pre render-hooks), the planner agent is instructed to apply `type: tdd` to eligible tasks using heuristics from `references/tdd.md`. The TDD guidance is injected via the tdd capability's contribution hook at §5.6; no inline config-get is needed.
|
|
82
81
|
|
|
83
82
|
When `CONTEXT_WINDOW >= 500000`, the planner prompt includes the 3 most recent prior phase CONTEXT.md and SUMMARY.md files PLUS any phases explicitly listed in the current phase's `Depends on:` field in ROADMAP.md. Explicit dependencies always load regardless of recency (e.g., Phase 7 declaring `Depends on: Phase 2` always sees Phase 2's context). Bounded recency keeps the planner's context budget focused on recent work.
|
|
84
83
|
|
|
@@ -165,7 +164,9 @@ Set `TEXT_MODE=true` if `--text` is present in $ARGUMENTS OR `text_mode` from in
|
|
|
165
164
|
```bash
|
|
166
165
|
MVP_FLAG_ARG=""
|
|
167
166
|
if [[ "$ARGUMENTS" =~ (^|[[:space:]])--mvp([[:space:]]|$) ]]; then MVP_FLAG_ARG="--cli-flag"; fi
|
|
168
|
-
if [[ "$ARGUMENTS" =~ (^|[[:space:]])--tdd([[:space:]]|$) ]]; then
|
|
167
|
+
if [[ "$ARGUMENTS" =~ (^|[[:space:]])--tdd([[:space:]]|$) ]]; then
|
|
168
|
+
gsd_run query config-set workflow.tdd_mode true 2>/dev/null || true
|
|
169
|
+
fi
|
|
169
170
|
```
|
|
170
171
|
|
|
171
172
|
Defer the `phase.mvp-mode` query until `PHASE` is finalized (after explicit argument parsing/fallback phase detection + validation). The verb returns `true|false`; full result also exposes `source` (`cli_flag` | `roadmap` | `config` | `none`) for diagnostics. Mode is **all-or-nothing per phase** (PRD decision Q1).
|
|
@@ -411,45 +412,20 @@ If "Run discuss-phase first":
|
|
|
411
412
|
```
|
|
412
413
|
**Exit the plan-phase workflow. Do not continue.**
|
|
413
414
|
|
|
414
|
-
## 4.5.
|
|
415
|
+
## 4.5. Resolve AI-SPEC Artifact
|
|
415
416
|
|
|
416
|
-
|
|
417
|
+
AI integration activation is owned by the `ai-integration` capability's `plan:pre` step hook. The plan-phase host only discovers existing artifacts here so the planner can consume them; it must not read the capability's config key directly.
|
|
417
418
|
|
|
418
419
|
```bash
|
|
419
420
|
AI_SPEC_FILE=$(ls "${PHASE_DIR}"/*-AI-SPEC.md 2>/dev/null | head -1)
|
|
420
|
-
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
**If `AI_SPEC_FILE` is empty:** Check phase goal for AI keywords:
|
|
426
|
-
```bash
|
|
427
|
-
echo "${phase_goal}" | grep -qi "agent\|llm\|rag\|chatbot\|embedding\|langchain\|llamaindex\|crewai\|langgraph\|openai\|anthropic\|vector\|eval\|ai system"
|
|
428
|
-
```
|
|
429
|
-
|
|
430
|
-
**If AI keywords detected AND no AI-SPEC.md:**
|
|
431
|
-
```
|
|
432
|
-
◆ Note: This phase appears to involve AI system development.
|
|
433
|
-
Consider running /gsd:ai-integration-phase {N} before planning to:
|
|
434
|
-
- Select the right framework for your use case
|
|
435
|
-
- Research its docs and best practices
|
|
436
|
-
- Design an evaluation strategy
|
|
437
|
-
|
|
438
|
-
Continue planning without AI-SPEC? (non-blocking — /gsd:ai-integration-phase can be run after)
|
|
421
|
+
AI_SPEC_PATH="${AI_SPEC_FILE}"
|
|
422
|
+
FRAMEWORK_LINE=""
|
|
423
|
+
if [ -n "$AI_SPEC_FILE" ]; then
|
|
424
|
+
FRAMEWORK_LINE=$(grep "Selected Framework:" "${AI_SPEC_FILE}" | head -1)
|
|
425
|
+
fi
|
|
439
426
|
```
|
|
440
427
|
|
|
441
|
-
|
|
442
|
-
- "Continue — plan without AI-SPEC"
|
|
443
|
-
- "Stop — I'll run /gsd:ai-integration-phase {N} first"
|
|
444
|
-
|
|
445
|
-
If "Stop": Exit with `/gsd:ai-integration-phase {N}` reminder.
|
|
446
|
-
If "Continue": Proceed. (Non-blocking — planner will note AI-SPEC is absent.)
|
|
447
|
-
|
|
448
|
-
**If `AI_SPEC_FILE` is non-empty:** Extract framework for planner context:
|
|
449
|
-
```bash
|
|
450
|
-
FRAMEWORK_LINE=$(grep "Selected Framework:" "${AI_SPEC_FILE}" | head -1)
|
|
451
|
-
```
|
|
452
|
-
Pass `ai_spec_path` and `framework_line` to planner in step 7 so it can reference the AI design contract.
|
|
428
|
+
If `AI_SPEC_FILE` is non-empty, pass `AI_SPEC_PATH` and `FRAMEWORK_LINE` to the planner in step 8 so it can reference the AI design contract. If it is empty, the active `ai-integration` capability hook in step 5.6 handles any AI-system nudge or `/gsd:ai-integration-phase` dispatch.
|
|
453
429
|
|
|
454
430
|
## 5. Handle Research
|
|
455
431
|
|
|
@@ -525,41 +501,21 @@ Display banner:
|
|
|
525
501
|
|
|
526
502
|
```bash
|
|
527
503
|
PHASE_DESC=$(gsd_run query roadmap.get-phase "${PHASE}" --pick section)
|
|
504
|
+
if [ -z "${PLAN_PRE_HOOKS_JSON:-}" ]; then
|
|
505
|
+
PLAN_PRE_HOOKS_JSON=$(gsd_run loop render-hooks plan:pre --raw)
|
|
506
|
+
fi
|
|
528
507
|
```
|
|
529
508
|
|
|
530
|
-
|
|
509
|
+
Find the active `research` step hook in `PLAN_PRE_HOOKS_JSON`. Use the hook's `fragment.inline` as the prompt template and substitute the phase fields below before spawning its declared `ref.agent`.
|
|
531
510
|
|
|
532
511
|
```markdown
|
|
533
|
-
|
|
534
|
-
Research how to implement Phase {phase_number}: {phase_name}
|
|
535
|
-
Answer: "What do I need to know to PLAN this phase well?"
|
|
536
|
-
</objective>
|
|
537
|
-
|
|
538
|
-
<files_to_read>
|
|
539
|
-
- {context_path} (USER DECISIONS from /gsd:discuss-phase)
|
|
540
|
-
- {requirements_path} (Project requirements)
|
|
541
|
-
- {state_path} (Project decisions and history)
|
|
542
|
-
</files_to_read>
|
|
543
|
-
|
|
544
|
-
${AGENT_SKILLS_RESEARCHER}
|
|
545
|
-
|
|
546
|
-
<additional_context>
|
|
547
|
-
**Phase description:** {phase_description}
|
|
548
|
-
**Phase requirement IDs (MUST address):** {phase_req_ids}
|
|
549
|
-
|
|
550
|
-
**Project instructions:** Read ./CLAUDE.md if exists — follow project-specific guidelines
|
|
551
|
-
**Project skills:** Check .claude/skills/ or .agents/skills/ directory (if either exists) — read SKILL.md files, research should account for project skill patterns
|
|
552
|
-
</additional_context>
|
|
553
|
-
|
|
554
|
-
<output>
|
|
555
|
-
Write to: {phase_dir}/{phase_num}-RESEARCH.md
|
|
556
|
-
</output>
|
|
512
|
+
{research_hook.fragment.inline}
|
|
557
513
|
```
|
|
558
514
|
|
|
559
515
|
```
|
|
560
516
|
Agent(
|
|
561
|
-
prompt=
|
|
562
|
-
subagent_type=
|
|
517
|
+
prompt=filled_research_hook_fragment,
|
|
518
|
+
subagent_type=research_hook.ref.agent,
|
|
563
519
|
model="{researcher_model}",
|
|
564
520
|
description="Research Phase {phase}"
|
|
565
521
|
)
|
|
@@ -622,17 +578,19 @@ test -f "${PHASE_DIR}/${PADDED_PHASE}-VALIDATION.md" && echo "VALIDATION_CREATED
|
|
|
622
578
|
|
|
623
579
|
## 5.55. Security Threat Model Gate
|
|
624
580
|
|
|
625
|
-
>
|
|
581
|
+
> Capability-driven dispatch. Resolves active `plan:pre` hooks via the capability registry; the security hook's `when` condition is evaluated by the registry.
|
|
626
582
|
|
|
627
583
|
```bash
|
|
628
|
-
|
|
629
|
-
SECURITY_ASVS=$(gsd_run query config-get workflow.security_asvs_level --raw 2>/dev/null || echo "1")
|
|
630
|
-
SECURITY_BLOCK=$(gsd_run query config-get workflow.security_block_on --raw 2>/dev/null || echo "high")
|
|
584
|
+
PLAN_PRE_HOOKS_JSON=$(gsd_run loop render-hooks plan:pre --raw)
|
|
631
585
|
```
|
|
632
586
|
|
|
633
|
-
|
|
587
|
+
Resolve active contribution hooks from `PLAN_PRE_HOOKS_JSON` where `kind == "contribution"` and `capId == "security"`.
|
|
634
588
|
|
|
635
|
-
**If
|
|
589
|
+
**If no active security contribution hook exists:** Skip to step 5.6.
|
|
590
|
+
|
|
591
|
+
**If an active security contribution hook exists:** Read `SECURITY_ASVS` from the active hook's `configValues.security_asvs_level` (default: `1`) and `SECURITY_BLOCK` from `configValues.security_block_on` (default: `"high"`). These values are resolved by the capability registry from user config using the same four-level precedence as hook activation — no inline `config-get` is needed.
|
|
592
|
+
|
|
593
|
+
Display banner:
|
|
636
594
|
|
|
637
595
|
```
|
|
638
596
|
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
|
|
@@ -646,21 +604,31 @@ Opt out: set security_enforcement: false in .planning/config.json
|
|
|
646
604
|
|
|
647
605
|
Continue to step 5.6. Security config is passed to the planner in step 8.
|
|
648
606
|
|
|
649
|
-
## 5.6. UI Design Contract Gate
|
|
607
|
+
## 5.6. Plan:Pre Capability Dispatch and UI Design Contract Gate
|
|
650
608
|
|
|
651
|
-
> Capability-driven dispatch. Resolves active `plan:pre` hooks via the capability registry; each hook's `when` condition
|
|
609
|
+
> Capability-driven dispatch. Resolves active `plan:pre` hooks via the capability registry; each hook's `when` condition is evaluated by the registry — no inline config-get needed. This section handles skill-based planning preflights such as `ai-integration`, agent-backed hooks through `ref.agent`, and the UI gate whose deterministic check comes from `check.query`.
|
|
652
610
|
>
|
|
653
611
|
> **Config semantics (cutover fix):** `workflow.ui_phase` gates UI-SPEC *generation* (step); `workflow.ui_safety_gate` gates the *planning block* (gate). Both-on = identical to OLD §5.6. Intended change: `{ui_phase:true, ui_safety_gate:false}` now auto-generates in pipelines but does NOT block manual planning (each key controls exactly what its description says).
|
|
654
612
|
|
|
655
613
|
```bash
|
|
656
|
-
|
|
614
|
+
PLAN_PRE_HOOKS_JSON=${PLAN_PRE_HOOKS_JSON:-$(gsd_run loop render-hooks plan:pre --raw)}
|
|
615
|
+
HOOKS_JSON="$PLAN_PRE_HOOKS_JSON"
|
|
657
616
|
```
|
|
658
617
|
|
|
659
|
-
Read the `activeHooks` array directly from `HOOKS_JSON` (in-context — do NOT invoke a shell pipeline).
|
|
618
|
+
Read the `activeHooks` array directly from `PLAN_PRE_HOOKS_JSON` / `HOOKS_JSON` (in-context — do NOT invoke a shell pipeline).
|
|
619
|
+
|
|
620
|
+
**Branch 1 — all plan:pre hooks inactive (`activeHooks` is empty or absent):** Skip to step 6.
|
|
660
621
|
|
|
661
|
-
**
|
|
622
|
+
**Generic step hook dispatch contract:** For each active entry where `kind == "step"`:
|
|
623
|
+
- If `ref.skill` is set, dispatch with `Skill(skill="gsd-${ref.skill}", args="${PHASE} --auto ${GSD_WS}")` when pipeline mode allows auto-chaining. Prepend `gsd-` to `ref.skill` — `ui-phase` → `gsd-ui-phase`.
|
|
624
|
+
- If `ref.agent` is set, dispatch with `Agent(prompt=filled_hook_fragment, subagent_type=ref.agent, model="{researcher_model}")`. Use the hook's `fragment.inline` as the prompt body and fill phase fields before spawning.
|
|
625
|
+
- The `research` hook is handled by §5.1's research decision. The `pattern-mapper` hook is handled by §7.8 after `RESEARCH_PATH` is known. Future plan:pre agent hooks use the same `ref.agent` fragment contract.
|
|
662
626
|
|
|
663
|
-
|
|
627
|
+
**AI integration capability:** If the active `ai-integration` step hook is present, `AI_SPEC_PATH` is empty, and the phase goal contains AI keywords (`agent`, `llm`, `rag`, `chatbot`, `embedding`, `langchain`, `llamaindex`, `crewai`, `langgraph`, `openai`, `anthropic`, `vector`, `eval`, `ai system`), then:
|
|
628
|
+
- In pipeline / `--auto` mode, invoke the hook's `ref.skill` via `Skill(skill="gsd-${ref.skill}", args="${PHASE} --auto ${GSD_WS}")`.
|
|
629
|
+
- In manual mode, display the existing non-blocking `/gsd:ai-integration-phase {N}` recommendation and let the user continue planning without AI-SPEC or stop to run the capability workflow first.
|
|
630
|
+
|
|
631
|
+
Run the UI deterministic gate whenever **any** `plan:pre` UI hook is active — including the step-only case (`workflow.ui_safety_gate` off). (`check.query` = `"ui.plan-gate"`; router normalizes dots→hyphens.)
|
|
664
632
|
|
|
665
633
|
```bash
|
|
666
634
|
GATE=$(gsd_run check ui-plan-gate "${PHASE}" --raw)
|
|
@@ -668,7 +636,7 @@ GATE=$(gsd_run check ui-plan-gate "${PHASE}" --raw)
|
|
|
668
636
|
|
|
669
637
|
Read `frontend`, `hasUiSpec`, and `block` from `GATE`.
|
|
670
638
|
|
|
671
|
-
**Branch 2 — no frontend indicators (`frontend` is `false`):** Skip silently to step
|
|
639
|
+
**Branch 2 — no frontend indicators (`frontend` is `false`):** Skip silently to step 6.
|
|
672
640
|
|
|
673
641
|
**Branch 3 — UI-SPEC already exists (`hasUiSpec` is `true`):**
|
|
674
642
|
|
|
@@ -689,13 +657,13 @@ Read the ephemeral auto-chain flag:
|
|
|
689
657
|
AUTO_CHAIN=$(gsd_run query check auto-mode --pick auto_chain_active 2>/dev/null || echo "false")
|
|
690
658
|
```
|
|
691
659
|
|
|
692
|
-
**Branch 5 — `AUTO_CHAIN` is `true` (pipeline / `--auto`):** Fire each active **step** hook — runs independently of whether a gate is active (covers `{ui_phase:true,
|
|
660
|
+
**Branch 5 — `AUTO_CHAIN` is `true` (pipeline / `--auto`):** Fire each active UI **step** hook — runs independently of whether a gate is active (covers `{ui_phase:true,ui_safety_gate:false}`). For each entry in `activeHooks` (in array order) where `kind == "step"` and `ref.skill` is set:
|
|
693
661
|
|
|
694
662
|
```
|
|
695
663
|
Skill(skill="gsd-${ref.skill}", args="${PHASE} --auto ${GSD_WS}")
|
|
696
664
|
```
|
|
697
665
|
|
|
698
|
-
|
|
666
|
+
After all UI step hooks return, re-read:
|
|
699
667
|
|
|
700
668
|
```bash
|
|
701
669
|
UI_SPEC_FILE=$(ls "${PHASE_DIR}"/*-UI-SPEC.md 2>/dev/null | head -1)
|
|
@@ -719,68 +687,6 @@ Also available:
|
|
|
719
687
|
|
|
720
688
|
**Exit the plan-phase workflow. Do not continue.**
|
|
721
689
|
|
|
722
|
-
## 5.7. Schema Push Detection Gate
|
|
723
|
-
|
|
724
|
-
> Detects schema-relevant files in the phase scope and injects a mandatory `[BLOCKING]` schema push task into the plan. Prevents false-positive verification where build/types pass because TypeScript types come from config, not the live database.
|
|
725
|
-
|
|
726
|
-
Check if any files in the phase scope match schema patterns:
|
|
727
|
-
|
|
728
|
-
```bash
|
|
729
|
-
PHASE_SECTION=$(gsd_run query roadmap.get-phase "${PHASE}" --pick section 2>/dev/null)
|
|
730
|
-
```
|
|
731
|
-
|
|
732
|
-
Scan `PHASE_SECTION`, `CONTEXT.md` (if loaded), and `RESEARCH.md` (if exists) for file paths matching these ORM patterns:
|
|
733
|
-
|
|
734
|
-
| ORM | File Patterns |
|
|
735
|
-
|-----|--------------|
|
|
736
|
-
| Payload CMS | `src/collections/**/*.ts`, `src/globals/**/*.ts` |
|
|
737
|
-
| Prisma | `prisma/schema.prisma`, `prisma/schema/*.prisma` |
|
|
738
|
-
| Drizzle | `drizzle/schema.ts`, `src/db/schema.ts`, `drizzle/*.ts` |
|
|
739
|
-
| Supabase | `supabase/migrations/*.sql` |
|
|
740
|
-
| TypeORM | `src/entities/**/*.ts`, `src/migrations/**/*.ts` |
|
|
741
|
-
|
|
742
|
-
Also check if any existing PLAN.md files for this phase already reference these file patterns in `files_modified`.
|
|
743
|
-
|
|
744
|
-
**If schema-relevant files detected:**
|
|
745
|
-
|
|
746
|
-
Set `SCHEMA_PUSH_REQUIRED=true` and `SCHEMA_ORM={detected_orm}`.
|
|
747
|
-
|
|
748
|
-
Determine the push command for the detected ORM:
|
|
749
|
-
|
|
750
|
-
| ORM | Push Command | Non-TTY Workaround |
|
|
751
|
-
|-----|-------------|-------------------|
|
|
752
|
-
| Payload CMS | `npx payload migrate` | `CI=true PAYLOAD_MIGRATING=true npx payload migrate` |
|
|
753
|
-
| Prisma | `npx prisma db push` | `npx prisma db push --accept-data-loss` (if destructive) |
|
|
754
|
-
| Drizzle | `npx drizzle-kit push` | `npx drizzle-kit push` |
|
|
755
|
-
| Supabase | `supabase db push` | Set `SUPABASE_ACCESS_TOKEN` env var |
|
|
756
|
-
| TypeORM | `npx typeorm migration:run` | `npx typeorm migration:run -d src/data-source.ts` |
|
|
757
|
-
|
|
758
|
-
Inject the following into the planner prompt (step 8) as an additional constraint:
|
|
759
|
-
|
|
760
|
-
```markdown
|
|
761
|
-
<schema_push_requirement>
|
|
762
|
-
**[BLOCKING] Schema Push Required**
|
|
763
|
-
|
|
764
|
-
This phase modifies schema-relevant files ({detected_files}). The planner MUST include
|
|
765
|
-
a `[BLOCKING]` task that runs the database schema push command AFTER all schema file
|
|
766
|
-
modifications are complete but BEFORE verification.
|
|
767
|
-
|
|
768
|
-
- ORM detected: {SCHEMA_ORM}
|
|
769
|
-
- Push command: {push_command}
|
|
770
|
-
- Non-TTY workaround: {env_hint}
|
|
771
|
-
- If push requires interactive prompts that cannot be suppressed, flag the task for
|
|
772
|
-
manual intervention with `autonomous: false`
|
|
773
|
-
|
|
774
|
-
This task is mandatory — the phase CANNOT pass verification without it. Build and
|
|
775
|
-
type checks will pass without the push (types come from config, not the live database),
|
|
776
|
-
creating a false-positive verification state.
|
|
777
|
-
</schema_push_requirement>
|
|
778
|
-
```
|
|
779
|
-
|
|
780
|
-
Display: `Schema files detected ({SCHEMA_ORM}) — [BLOCKING] push task will be injected into plans`
|
|
781
|
-
|
|
782
|
-
**If no schema-relevant files detected:** Skip silently to step 6.
|
|
783
|
-
|
|
784
690
|
## 6. Check Existing Plans
|
|
785
691
|
|
|
786
692
|
```bash
|
|
@@ -845,14 +751,7 @@ Proceed to Step 7.8 (or Step 8 if pattern mapper is disabled) only if user selec
|
|
|
845
751
|
|
|
846
752
|
## 7.8. Spawn gsd-pattern-mapper Agent (Optional)
|
|
847
753
|
|
|
848
|
-
|
|
849
|
-
|
|
850
|
-
Check config:
|
|
851
|
-
```bash
|
|
852
|
-
PATTERN_MAPPER_CFG=$(gsd_run query config-get workflow.pattern_mapper 2>/dev/null || echo "true")
|
|
853
|
-
```
|
|
854
|
-
|
|
855
|
-
**If `PATTERN_MAPPER_CFG` is `false`:** Skip to step 8.
|
|
754
|
+
Pattern mapper activation is owned by the `pattern-mapper` capability's `plan:pre` step hook. Read `PLAN_PRE_HOOKS_JSON` and skip if no active step hook has `capId == "pattern-mapper"` and `ref.agent == "gsd-pattern-mapper"`. Also skip if no CONTEXT.md and no RESEARCH.md exist for this phase (nothing to extract file lists from).
|
|
856
755
|
|
|
857
756
|
**If PATTERNS.md already exists** (`PATTERNS_PATH` is non-empty from step 7): Skip to step 8 (use existing).
|
|
858
757
|
|
|
@@ -865,30 +764,17 @@ Display banner:
|
|
|
865
764
|
◆ Spawning pattern mapper... (runs in a subagent — no output until it returns, ~1–5 min; expected, not a freeze)
|
|
866
765
|
```
|
|
867
766
|
|
|
868
|
-
|
|
767
|
+
Use the active `pattern-mapper` hook's `fragment.inline` as the prompt template and substitute the phase fields below before spawning its declared `ref.agent`.
|
|
869
768
|
|
|
870
769
|
```markdown
|
|
871
|
-
|
|
872
|
-
**Phase:** {phase_number} - {phase_name}
|
|
873
|
-
**Phase directory:** {phase_dir}
|
|
874
|
-
**Padded phase:** {padded_phase}
|
|
875
|
-
|
|
876
|
-
<files_to_read>
|
|
877
|
-
- {context_path} (USER DECISIONS from /gsd:discuss-phase)
|
|
878
|
-
- {research_path} (Technical Research)
|
|
879
|
-
</files_to_read>
|
|
880
|
-
|
|
881
|
-
**Output file:** {phase_dir}/{padded_phase}-PATTERNS.md
|
|
882
|
-
|
|
883
|
-
Extract the list of files to be created/modified from CONTEXT.md and RESEARCH.md. For each file, classify by role and data flow, find the closest existing analog in the codebase, extract concrete code excerpts, and produce PATTERNS.md.
|
|
884
|
-
</pattern_mapping_context>
|
|
770
|
+
{pattern_mapper_hook.fragment.inline}
|
|
885
771
|
```
|
|
886
772
|
|
|
887
773
|
Spawn with:
|
|
888
774
|
```
|
|
889
775
|
Agent(
|
|
890
|
-
prompt=
|
|
891
|
-
subagent_type=
|
|
776
|
+
prompt=filled_pattern_mapper_hook_fragment,
|
|
777
|
+
subagent_type=pattern_mapper_hook.ref.agent,
|
|
892
778
|
model="{researcher_model}",
|
|
893
779
|
)
|
|
894
780
|
```
|
|
@@ -906,16 +792,21 @@ PATTERNS_PATH="${PHASE_DIR}/${PADDED_PHASE}-PATTERNS.md"
|
|
|
906
792
|
|
|
907
793
|
## 7.9. Regenerate API-SURFACE.md (intel gate)
|
|
908
794
|
|
|
795
|
+
> Capability-driven dispatch. Resolves active `plan:pre` step hooks via the capability registry; the intel hook's `when: intel.enabled` condition is evaluated by the registry — no inline config-get needed.
|
|
796
|
+
|
|
797
|
+
Read the active intel step hook from `PLAN_PRE_HOOKS_JSON` where `kind == "step"` and `capId == "intel"`.
|
|
798
|
+
|
|
799
|
+
**If no active intel step hook exists:** `API_SURFACE_PATH` stays empty; skip to step 8. The step-8 planner entry for API Surface is omitted when `API_SURFACE_PATH` is empty.
|
|
800
|
+
|
|
801
|
+
**If an active intel step hook exists:**
|
|
909
802
|
```bash
|
|
910
|
-
|
|
911
|
-
|
|
912
|
-
|
|
913
|
-
gsd_run intel api-surface
|
|
914
|
-
API_SURFACE_PATH=".planning/intel/API-SURFACE.md"
|
|
915
|
-
echo "✓ API surface regenerated: ${API_SURFACE_PATH}" # injected into step 8 as HINT
|
|
916
|
-
fi
|
|
803
|
+
gsd_run intel api-surface
|
|
804
|
+
API_SURFACE_PATH=".planning/intel/API-SURFACE.md"
|
|
805
|
+
echo "✓ API surface regenerated: ${API_SURFACE_PATH}" # injected into step 8 as HINT
|
|
917
806
|
```
|
|
918
807
|
|
|
808
|
+
Continue to step 8.
|
|
809
|
+
|
|
919
810
|
## 8. Spawn gsd-planner Agent
|
|
920
811
|
|
|
921
812
|
Display banner:
|
|
@@ -944,11 +835,12 @@ Planner prompt:
|
|
|
944
835
|
- {verification_path} (Verification Gaps - if --gaps)
|
|
945
836
|
- {uat_path} (UAT Gaps - if --gaps)
|
|
946
837
|
- {reviews_path} (Cross-AI Review Feedback - if --reviews; actionable findings must be incorporated or explicitly deferred/rejected in PLAN.md)
|
|
838
|
+
- {AI_SPEC_PATH} (AI Design Contract — framework and evaluation strategy, if exists)
|
|
947
839
|
- {UI_SPEC_PATH} (UI Design Contract — visual/interaction specs, if exists)
|
|
948
840
|
- {SPEC_PATH} (Phase SPEC — carries the ## Edge Coverage section to lift covered/backstop edges from, if exists)
|
|
949
841
|
- {SPIKE_FINDINGS_PATH} (Spike Findings — validated patterns, constraints, landmines from experiments, if exists)
|
|
950
842
|
- {SKETCH_FINDINGS_PATH} (Sketch Findings — validated design decisions, CSS patterns, visual direction, if exists)
|
|
951
|
-
- {API_SURFACE_PATH} (API Surface — HINT ONLY,
|
|
843
|
+
- {API_SURFACE_PATH} (API Surface — HINT ONLY, when intel capability is active; see <intel_surface_hint> below)
|
|
952
844
|
${CONTEXT_WINDOW >= 500000 ? `
|
|
953
845
|
**Cross-phase context (1M model enrichment):**
|
|
954
846
|
- CONTEXT.md files from the 3 most recent completed phases (locked decisions — maintain consistency)
|
|
@@ -977,19 +869,10 @@ Historical findings already incorporated, explicitly deferred/rejected in PLAN.m
|
|
|
977
869
|
|
|
978
870
|
**Phase requirement IDs (every ID MUST appear in a plan's `requirements` field):** {phase_req_ids}
|
|
979
871
|
|
|
980
|
-
**Project instructions:** Read ./CLAUDE.md if exists — follow project-specific guidelines
|
|
872
|
+
**Project instructions:** Read ./CLAUDE.md or ./.claude/CLAUDE.md if either exists — follow project-specific guidelines
|
|
981
873
|
**Project skills:** Check .claude/skills/ or .agents/skills/ directory (if either exists) — read SKILL.md files, plans should account for project skill rules
|
|
982
874
|
|
|
983
|
-
|
|
984
|
-
<tdd_mode_active>
|
|
985
|
-
**TDD Mode is ENABLED.** Apply TDD heuristics from @~/.claude/gsd-core/references/tdd.md to all eligible tasks:
|
|
986
|
-
- Business logic with defined I/O → type: tdd
|
|
987
|
-
- API endpoints with request/response contracts → type: tdd
|
|
988
|
-
- Data transformations, validation, algorithms → type: tdd
|
|
989
|
-
- UI, config, glue code, CRUD → standard plan (type: execute)
|
|
990
|
-
Each TDD plan gets one feature with RED/GREEN/REFACTOR gate sequence.
|
|
991
|
-
</tdd_mode_active>
|
|
992
|
-
` : ''}
|
|
875
|
+
{For each active entry in `PLAN_PRE_HOOKS_JSON` where `kind == "contribution"` and `into == "planner"` (in array order): inject the entry's `fragment.inline` verbatim here. This delivers all planner-targeted contributions — including tdd's `<tdd_mode_active>` block (type:tdd heuristics), schema-gate's schema-push detection guidance (if active at plan:pre), and security's threat-model guidance. For the security contribution, also surface the resolved `configValues`: `security_asvs_level` (ASVS enforcement level) and `security_block_on` (severity threshold) so the planner uses the configured values when generating `<threat_model>` blocks. If no active planner contributions exist, omit this block entirely.}
|
|
993
876
|
|
|
994
877
|
**MVP_MODE:** ${MVP_MODE} (when true, follow vertical-slice rules from `~/.claude/gsd-core/references/planner-mvp-mode.md`; when false, ignore MVP guidance entirely.)
|
|
995
878
|
**WALKING_SKELETON:** ${WALKING_SKELETON} (when true, the first deliverable must be a Walking Skeleton — Read the template at `~/.claude/gsd-core/references/skeleton-template.md` and produce SKELETON.md alongside PLAN.md.)
|
|
@@ -1009,6 +892,7 @@ Output consumed by /gsd:execute-phase. Plans need:
|
|
|
1009
892
|
- Verification criteria
|
|
1010
893
|
- must_haves for goal-backward verification
|
|
1011
894
|
- If the SPEC has an `## Edge Coverage` section, lift every `covered` edge's acceptance criterion into `must_haves.truths`, and every `backstop` edge into `must_haves.truths` as a non-inferable check (note it needs a held-out/property-based test). `unresolved` edges are explicit assumptions — surface them in the plan, do not silently drop them.
|
|
895
|
+
- If the SPEC has a `## Prohibitions` section, lift every resolved prohibition into the `must_haves.prohibitions:` sibling block (NOT `truths` — ADR-550 D3) carrying `statement` + `status` + `verification`; unresolved prohibitions are explicit assumptions — surface them in the plan, do not silently drop them. A prohibition is a must-NOT (negative) check that belongs in its own `must_haves.prohibitions` block. Never place a must-NOT under `must_haves.truths` — that block keeps positive-observable semantics only.
|
|
1012
896
|
- **"Artifacts this phase produces" section (MANDATORY)** — list every symbol this phase creates: decorators, classes, functions, CLI flags, struct/dataclass fields, new file paths. The plan-review-convergence source-grounding pass reads this section to exclude newly-created symbols from drift verification; omitting it causes new symbols to be flagged for acknowledgement.
|
|
1013
897
|
</downstream_consumer>
|
|
1014
898
|
|
|
@@ -1055,6 +939,7 @@ Every task MUST include these fields — they are NOT optional:
|
|
|
1055
939
|
- [ ] must_haves derived from phase goal
|
|
1056
940
|
- [ ] Every PLAN.md includes an "Artifacts this phase produces" section listing symbols created by this phase (decorators, classes, functions, CLI flags, struct/dataclass fields, new file paths)
|
|
1057
941
|
- [ ] Every SPEC ## Edge Coverage covered/backstop edge is represented in a plan's must_haves (no silent drops)
|
|
942
|
+
- [ ] Every SPEC ## Prohibitions resolved item is represented in a plan's must_haves.prohibitions (no silent drops)
|
|
1058
943
|
</quality_gate>
|
|
1059
944
|
```
|
|
1060
945
|
|
|
@@ -1316,7 +1201,7 @@ If an actionable finding remains only in REVIEWS.md and would be invisible to /g
|
|
|
1316
1201
|
|
|
1317
1202
|
**Phase requirement IDs (MUST ALL be covered):** {phase_req_ids}
|
|
1318
1203
|
|
|
1319
|
-
**Project instructions:** Read ./CLAUDE.md if exists — verify plans honor project guidelines
|
|
1204
|
+
**Project instructions:** Read ./CLAUDE.md or ./.claude/CLAUDE.md if either exists — verify plans honor project guidelines
|
|
1320
1205
|
**Project skills:** Check .claude/skills/ or .agents/skills/ directory (if either exists) — verify plans account for project skill rules
|
|
1321
1206
|
</verification_context>
|
|
1322
1207
|
|
|
@@ -1682,53 +1567,38 @@ gsd_run query commit "docs(${PADDED_PHASE}): create phase plan" --files "${PHASE
|
|
|
1682
1567
|
|
|
1683
1568
|
This commits all PLAN.md files for the phase plus the updated STATE.md and ROADMAP.md to version-control the planning artifacts. Skip this step if `commit_docs` is false.
|
|
1684
1569
|
|
|
1685
|
-
## 13e. Post-Planning Gap Analysis
|
|
1686
|
-
|
|
1687
|
-
After all plans are generated, committed, and the Requirements Coverage Gate (§13)
|
|
1688
|
-
has run, emit a single unified gap report covering both REQUIREMENTS.md and the
|
|
1689
|
-
CONTEXT.md `<decisions>` section. This is a **proactive, post-hoc report** — it
|
|
1690
|
-
does not block phase advancement and does not re-plan. It exists so that any
|
|
1691
|
-
requirement or decision that slipped through the per-plan checks is surfaced in
|
|
1692
|
-
one place before execution begins.
|
|
1570
|
+
## 13e. Post-Planning Gap Analysis (plan:post capability gate dispatch)
|
|
1693
1571
|
|
|
1694
|
-
|
|
1572
|
+
Proactive, non-blocking coverage report gated on `workflow.post_planning_gaps`
|
|
1573
|
+
(default `true`). Dispatched via the `plan:post` capability gate owned by the
|
|
1574
|
+
`gap-analysis` capability (ADR-857 §53). Reads REQUIREMENTS.md and CONTEXT.md
|
|
1575
|
+
`<decisions>` and cross-references each REQ-ID / D-ID against `${PHASE_DIR}/*-PLAN.md`.
|
|
1695
1576
|
|
|
1696
1577
|
```bash
|
|
1697
|
-
|
|
1698
|
-
|
|
1699
|
-
# Scope to this phase's mapped REQ-IDs (#447); null/TBD skips the requirements comparison (CONTEXT.md decisions still reported), mirroring §13.
|
|
1700
|
-
gsd_run gap-analysis --phase-dir "${PHASE_DIR}" --phase-req-ids "$(gsd_run query init.plan-phase "$PHASE" --pick phase_req_ids 2>/dev/null || echo TBD)"
|
|
1701
|
-
fi
|
|
1578
|
+
PLAN_POST_HOOKS_JSON=$(gsd_run loop render-hooks plan:post --raw)
|
|
1579
|
+
PHASE_REQ_IDS=$(gsd_run query init.plan-phase "$PHASE" --pick phase_req_ids 2>/dev/null || echo TBD)
|
|
1702
1580
|
```
|
|
1703
1581
|
|
|
1704
|
-
|
|
1705
|
-
|
|
1706
|
-
REQ-ID and D-ID. Word-boundary matching prevents `REQ-1` from being mistaken for
|
|
1707
|
-
`REQ-10`.)
|
|
1582
|
+
Read the `activeHooks` array from `PLAN_POST_HOOKS_JSON` in-context. If the
|
|
1583
|
+
`gap-analysis` gate hook is absent (capability inactive), skip this step.
|
|
1708
1584
|
|
|
1709
|
-
**
|
|
1710
|
-
sort within source):**
|
|
1585
|
+
**For each active entry where `kind == "gate"`** (process in array order):
|
|
1711
1586
|
|
|
1587
|
+
```bash
|
|
1588
|
+
GATE_RESULT=$(gsd_run check ${hook.check.query} "${PHASE_DIR}" "${PHASE_REQ_IDS}" --raw)
|
|
1589
|
+
CHECK_EXIT=$?
|
|
1712
1590
|
```
|
|
1713
|
-
## Post-Planning Gap Analysis
|
|
1714
1591
|
|
|
1715
|
-
|
|
1716
|
-
|
|
1717
|
-
|
|
1718
|
-
|
|
1719
|
-
| CONTEXT.md | D-01 | ✓ Covered |
|
|
1720
|
-
| CONTEXT.md | D-02 | ✗ Not covered |
|
|
1721
|
-
|
|
1722
|
-
⚠ N items not covered by any plan
|
|
1723
|
-
```
|
|
1592
|
+
**Step 1 — did the CHECK COMMAND itself succeed?**
|
|
1593
|
+
If the check command failed (non-zero `CHECK_EXIT`, empty output, or unparseable JSON):
|
|
1594
|
+
- `onError == "halt"` → halt and surface command error.
|
|
1595
|
+
- `onError == "skip"` → log a warning and continue to the next hook.
|
|
1724
1596
|
|
|
1725
|
-
**
|
|
1726
|
-
- REQUIREMENTS.md missing → CONTEXT-only report.
|
|
1727
|
-
- CONTEXT.md missing → REQUIREMENTS-only report.
|
|
1728
|
-
- Both missing or `<decisions>` block missing → "No requirements or decisions to check" line, no error.
|
|
1597
|
+
**Step 2 — read `GATE_RESULT.block` (boolean).** Only reached when command succeeded.
|
|
1729
1598
|
|
|
1730
|
-
|
|
1731
|
-
|
|
1599
|
+
- If `hook.blocking == true` and `GATE_RESULT.block == true`: halt. (gap-analysis is always `blocking: false` so this branch is informational only.)
|
|
1600
|
+
- If `hook.blocking == false` (advisory): if `GATE_RESULT.block == true` or non-empty `table`/`summary`, output the gap table and continue. Advisory gates never block phase completion.
|
|
1601
|
+
- If `hook.blocking == true` and `GATE_RESULT.block == false`: continue silently.
|
|
1732
1602
|
|
|
1733
1603
|
## 14. Present Final Status
|
|
1734
1604
|
|
|
@@ -185,13 +185,23 @@ Run this pass unless `plan_review.source_grounding` is `false`. It verifies ever
|
|
|
185
185
|
|
|
186
186
|
1. **Enumerate cited symbols.** List every referenced symbol by kind, quoting the plan line for each (coverage must be auditable): decorators (`@name`), classes/methods (`Class.method`), functions (`module.function`), CLI flags (`--name`), file paths, dataclass/struct fields.
|
|
187
187
|
2. **Exclude new artifacts.** Do NOT verify symbols the plan declares under its "Artifacts this phase produces" section — those are created by this phase, not references to existing code.
|
|
188
|
-
3. **Resolve each remaining symbol** using the adapter
|
|
188
|
+
3. **Resolve each remaining symbol** using the effective authority adapter (resolved deterministically — see step 4a):
|
|
189
189
|
- `grep` — ripgrep / Read the source; confirm the name appears as a real declaration.
|
|
190
190
|
- `intel` — consult `.planning/intel/API-SURFACE.md` / `api-map.json` (only when `intel.enabled`).
|
|
191
191
|
Record one verdict per symbol: **VERIFIED** (quote `file:line`), **MISSING** (adapter can check this language/kind and the symbol is absent), **AMBIGUOUS** (multiple candidates), or **UNCHECKABLE** (adapter cannot analyze this language/kind — e.g. non-JS under `intel`, or any signature under `grep`). Never treat UNCHECKABLE as verified or missing.
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
-
|
|
192
|
+
4a. **Resolve effective authority** (deterministic — replaces manual `intel.enabled` reasoning):
|
|
193
|
+
```bash
|
|
194
|
+
EFFECTIVE_AUTHORITY=$(gsd_run drift-guard authority --raw)
|
|
195
|
+
```
|
|
196
|
+
4. **Severity & gating** — classify each symbol's verdict using the seam (do not apply the table manually):
|
|
197
|
+
```bash
|
|
198
|
+
# For each symbol, e.g.:
|
|
199
|
+
RESULT=$(gsd_run drift-guard severity --status <verdict> --authority "$EFFECTIVE_AUTHORITY")
|
|
200
|
+
# $RESULT is JSON: {"severity":"…","hardBlock":true|false}
|
|
201
|
+
```
|
|
202
|
+
- `hardBlock: true` (HIGH at authority `lsp`/`scip`) — stops the review cycle immediately; do not proceed until the plan author resolves the missing symbol.
|
|
203
|
+
- `hardBlock: false`, severity `needs-acknowledgement` — plan proceeds only if the author confirms the symbol is genuinely new or dynamically resolved, and that acknowledgement is recorded.
|
|
204
|
+
- `AMBIGUOUS` → MEDIUM. `UNCHECKABLE` → INFO.
|
|
195
205
|
- Signature mismatches cannot be asserted under `grep`/`intel`; report the signature as UNCHECKABLE.
|
|
196
206
|
5. **Coverage block.** Append a "Verification coverage" section to `REVIEWS.md` listing every UNCHECKABLE/skipped symbol and why — a clean review must never silently mean "nothing was checked."
|
|
197
207
|
|
|
@@ -10,11 +10,13 @@ Uses git cherry-pick with path filtering to rebuild a clean history.
|
|
|
10
10
|
<process>
|
|
11
11
|
|
|
12
12
|
<step name="detect_state">
|
|
13
|
-
Parse `$ARGUMENTS` for target branch
|
|
13
|
+
Parse `$ARGUMENTS` for target branch. If no argument is supplied, detect the
|
|
14
|
+
default branch via the single resolver (#1146).
|
|
14
15
|
|
|
15
16
|
```bash
|
|
17
|
+
_GSD_SHIM_NAME="gsd-tools.cjs"; _GSD_RUNTIME_ROOT="${RUNTIME_DIR:-$(git rev-parse --show-toplevel 2>/dev/null || pwd)}"; GSD_TOOLS="${_GSD_RUNTIME_ROOT}/gsd-core/bin/${_GSD_SHIM_NAME}"; if [ -f "$GSD_TOOLS" ]; then gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${_GSD_RUNTIME_ROOT}/.claude/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${_GSD_RUNTIME_ROOT}/.claude/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${_GSD_RUNTIME_ROOT}/.codex/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${_GSD_RUNTIME_ROOT}/.codex/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif command -v gsd-tools >/dev/null 2>&1; then GSD_TOOLS="$(command -v gsd-tools)"; gsd_run() { "$GSD_TOOLS" "$@"; }; elif [ -f "$HOME/.claude/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="$HOME/.claude/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${HERMES_HOME:-$HOME/.hermes}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${HERMES_HOME:-$HOME/.hermes}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${CURSOR_CONFIG_DIR:-$HOME/.cursor}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${CURSOR_CONFIG_DIR:-$HOME/.cursor}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${CODEX_HOME:-$HOME/.codex}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${CODEX_HOME:-$HOME/.codex}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${GEMINI_CONFIG_DIR:-$HOME/.gemini}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${GEMINI_CONFIG_DIR:-$HOME/.gemini}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${COPILOT_CONFIG_DIR:-$HOME/.copilot}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${COPILOT_CONFIG_DIR:-$HOME/.copilot}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${WINDSURF_CONFIG_DIR:-$HOME/.codeium/windsurf}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${WINDSURF_CONFIG_DIR:-$HOME/.codeium/windsurf}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${AUGMENT_CONFIG_DIR:-$HOME/.augment}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${AUGMENT_CONFIG_DIR:-$HOME/.augment}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${TRAE_CONFIG_DIR:-$HOME/.trae}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${TRAE_CONFIG_DIR:-$HOME/.trae}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${QWEN_CONFIG_DIR:-$HOME/.qwen}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${QWEN_CONFIG_DIR:-$HOME/.qwen}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${CODEBUDDY_CONFIG_DIR:-$HOME/.codebuddy}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${CODEBUDDY_CONFIG_DIR:-$HOME/.codebuddy}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${CLINE_CONFIG_DIR:-$HOME/.cline}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${CLINE_CONFIG_DIR:-$HOME/.cline}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${GROK_AGENTS_HOME:-$HOME/.agents}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${GROK_AGENTS_HOME:-$HOME/.agents}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${ANTIGRAVITY_CONFIG_DIR:-$HOME/.gemini/antigravity}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${ANTIGRAVITY_CONFIG_DIR:-$HOME/.gemini/antigravity}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${OPENCODE_CONFIG_DIR:-${XDG_CONFIG_HOME:-$HOME/.config}/opencode}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${OPENCODE_CONFIG_DIR:-${XDG_CONFIG_HOME:-$HOME/.config}/opencode}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; elif [ -f "${KILO_CONFIG_DIR:-${XDG_CONFIG_HOME:-$HOME/.config}/kilo}/gsd-core/bin/${_GSD_SHIM_NAME}" ]; then GSD_TOOLS="${KILO_CONFIG_DIR:-${XDG_CONFIG_HOME:-$HOME/.config}/kilo}/gsd-core/bin/${_GSD_SHIM_NAME}"; gsd_run() { node "$GSD_TOOLS" "$@"; }; else echo "ERROR: gsd-tools.cjs not found at $GSD_TOOLS and gsd-tools is not on PATH. Run: npx -y @opengsd/gsd-core@latest --claude --local" >&2; exit 1; fi; if [ -n "${CLAUDE_ENV_FILE:-}" ] && [ -n "${GSD_TOOLS:-}" ]; then printf "export PATH='%s':\"\$PATH\"\n" "${GSD_TOOLS%/*}" >> "$CLAUDE_ENV_FILE" 2>/dev/null || true; fi
|
|
16
18
|
CURRENT_BRANCH=$(git branch --show-current)
|
|
17
|
-
TARGET=${1
|
|
19
|
+
TARGET=${1:-$(gsd_run query git.base-branch)}
|
|
18
20
|
```
|
|
19
21
|
|
|
20
22
|
Check preconditions:
|
|
@@ -414,10 +414,12 @@ Then list paths for each generated artifact:
|
|
|
414
414
|
```
|
|
415
415
|
Artifacts:
|
|
416
416
|
✓ /gsd-dev-preferences $HOME/.claude/skills/gsd-dev-preferences/SKILL.md
|
|
417
|
-
✓ CLAUDE.md section
|
|
417
|
+
✓ CLAUDE.md section <resolved claude_md_path, default ./.claude/CLAUDE.md>
|
|
418
418
|
✓ Global CLAUDE.md $HOME/.claude/CLAUDE.md
|
|
419
419
|
```
|
|
420
420
|
|
|
421
|
+
(Show the `claude_md_path` actually returned by the command — it defaults to `./.claude/CLAUDE.md` but may be overridden by config or `--output`.)
|
|
422
|
+
|
|
421
423
|
(Only show artifacts that were actually generated.)
|
|
422
424
|
|
|
423
425
|
**Clean up temp files:**
|