hstack 0.1.0
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/CHANGELOG.md +31 -0
- package/LICENSE +21 -0
- package/README.md +169 -0
- package/VERSION +1 -0
- package/dist/cli.js +55 -0
- package/dist/cli.js.map +1 -0
- package/dist/commands/doctor.js +155 -0
- package/dist/commands/doctor.js.map +1 -0
- package/dist/commands/init.js +87 -0
- package/dist/commands/init.js.map +1 -0
- package/dist/commands/update.js +118 -0
- package/dist/commands/update.js.map +1 -0
- package/dist/lib/diff.js +120 -0
- package/dist/lib/diff.js.map +1 -0
- package/dist/lib/git.js +26 -0
- package/dist/lib/git.js.map +1 -0
- package/dist/lib/paths.js +35 -0
- package/dist/lib/paths.js.map +1 -0
- package/dist/lib/wire.js +314 -0
- package/dist/lib/wire.js.map +1 -0
- package/dist/manifest.js +53 -0
- package/dist/manifest.js.map +1 -0
- package/package.json +54 -0
- package/template/.claude/agents/adversarial-reviewer.md +123 -0
- package/template/.claude/agents/data-specialist.md +126 -0
- package/template/.claude/agents/implementer.md +154 -0
- package/template/.claude/agents/planner.md +110 -0
- package/template/.claude/agents/product-manager.md +111 -0
- package/template/.claude/agents/researcher.md +123 -0
- package/template/.claude/agents/security-reviewer.md +123 -0
- package/template/.claude/agents/spec-author.md +118 -0
- package/template/.claude/agents/test-strategist.md +129 -0
- package/template/.claude/agents/ui-ux-briefer.md +105 -0
- package/template/.claude/agents/verifier.md +109 -0
- package/template/.claude/skills/hstack-adr-new/SKILL.md +118 -0
- package/template/.claude/skills/hstack-adversarial-review/SKILL.md +187 -0
- package/template/.claude/skills/hstack-branch/SKILL.md +103 -0
- package/template/.claude/skills/hstack-change-new/SKILL.md +109 -0
- package/template/.claude/skills/hstack-change-plan/SKILL.md +119 -0
- package/template/.claude/skills/hstack-commit/SKILL.md +122 -0
- package/template/.claude/skills/hstack-configure/SKILL.md +126 -0
- package/template/.claude/skills/hstack-data-review/SKILL.md +132 -0
- package/template/.claude/skills/hstack-finalize/SKILL.md +159 -0
- package/template/.claude/skills/hstack-help/SKILL.md +174 -0
- package/template/.claude/skills/hstack-implement/SKILL.md +185 -0
- package/template/.claude/skills/hstack-init/SKILL.md +152 -0
- package/template/.claude/skills/hstack-module-spec/SKILL.md +105 -0
- package/template/.claude/skills/hstack-research/SKILL.md +145 -0
- package/template/.claude/skills/hstack-security-review/SKILL.md +133 -0
- package/template/.claude/skills/hstack-ship/SKILL.md +128 -0
- package/template/.claude/skills/hstack-story-draft/SKILL.md +117 -0
- package/template/.claude/skills/hstack-tech-debt-new/SKILL.md +122 -0
- package/template/.claude/skills/hstack-tech-debt-resolve/SKILL.md +158 -0
- package/template/.claude/skills/hstack-tech-debt-stale/SKILL.md +113 -0
- package/template/.claude/skills/hstack-tech-debt-wontfix/SKILL.md +104 -0
- package/template/.claude/skills/hstack-telemetry/SKILL.md +96 -0
- package/template/.claude/skills/hstack-test-plan/SKILL.md +182 -0
- package/template/.claude/skills/hstack-ui-brief/SKILL.md +108 -0
- package/template/.claude/skills/hstack-verify/SKILL.md +139 -0
- package/template/CLAUDE.md +390 -0
- package/template/scripts/telemetry/__init__.py +6 -0
- package/template/scripts/telemetry/insights/__init__.py +0 -0
- package/template/scripts/telemetry/insights/contract_drift.py +137 -0
- package/template/scripts/telemetry/insights/overengineering.py +115 -0
- package/template/scripts/telemetry/insights/quality_outcomes.py +131 -0
- package/template/scripts/telemetry/insights/token_economics.py +129 -0
- package/template/scripts/telemetry/insights/workflow_shape.py +198 -0
- package/template/scripts/telemetry/parsers/__init__.py +0 -0
- package/template/scripts/telemetry/parsers/bodies.py +87 -0
- package/template/scripts/telemetry/parsers/commits.py +219 -0
- package/template/scripts/telemetry/parsers/frontmatter.py +322 -0
- package/template/scripts/telemetry/parsers/transcripts.py +181 -0
- package/template/scripts/telemetry/render.py +311 -0
- package/template/scripts/telemetry/report.py +112 -0
- package/template/templates/adr.md +38 -0
- package/template/templates/adversarial-review.md +54 -0
- package/template/templates/change-spec.md +80 -0
- package/template/templates/ci-cd.md +27 -0
- package/template/templates/data-architecture.md +35 -0
- package/template/templates/data-review.md +54 -0
- package/template/templates/figma-handoff.md +38 -0
- package/template/templates/glossary.md +20 -0
- package/template/templates/hardening-checklist.md +73 -0
- package/template/templates/incident-runbook.md +57 -0
- package/template/templates/infrastructure.md +190 -0
- package/template/templates/module-spec.md +49 -0
- package/template/templates/mvp-scope.md +34 -0
- package/template/templates/persona.md +38 -0
- package/template/templates/plan.md +49 -0
- package/template/templates/security-review.md +63 -0
- package/template/templates/story.md +37 -0
- package/template/templates/tech-debt.md +61 -0
- package/template/templates/tech-stack.md +41 -0
- package/template/templates/telemetry-sidecar.md +184 -0
- package/template/templates/test-plan.md +119 -0
- package/template/templates/threat-model.md +54 -0
- package/template/templates/ui-brief.md +49 -0
- package/template/templates/verification.md +63 -0
- package/template/templates/vision.md +34 -0
|
@@ -0,0 +1,145 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: hstack-research
|
|
3
|
+
description: |
|
|
4
|
+
Use this skill when the engineer needs grounded research across one of five modes (API lookups, competitive scans, documentation, security CVEs, AI-native best practices) and wants a transient research session committed to `hstack/research/sessions/`. The Skill orchestrates the `researcher` subagent. A `--promote <session-id>` sub-mode elevates an existing session into an ADR (routes through `hstack-adr-new`), a tech-debt item (routes through `hstack-tech-debt-new`), or a durable note under `hstack/research/promoted/` (written by the researcher directly). Examples:
|
|
5
|
+
|
|
6
|
+
<example>
|
|
7
|
+
Context: The engineer is about to introduce a new HubSpot integration and needs to confirm current rate-limit and webhook signature behavior.
|
|
8
|
+
user: "/hstack:research HubSpot CRM v3 webhook signature verification and current rate limits."
|
|
9
|
+
assistant: "I'll invoke researcher in API-lookup mode. Canonical-source bias on HubSpot's docs over secondary tutorials; recency window pinned to the last 12 months. Session lands at hstack/research/sessions/<date>-hubspot-webhooks.md."
|
|
10
|
+
<commentary>
|
|
11
|
+
Mode classification drives source bias. API-lookup mode weights vendor docs over tutorials because tutorials are the most common cause of wrong-API integrations. Sessions are transient artifacts; the engineer chooses whether to promote.
|
|
12
|
+
</commentary>
|
|
13
|
+
</example>
|
|
14
|
+
|
|
15
|
+
<example>
|
|
16
|
+
Context: A research session reached a decision point; the engineer wants to promote it to an ADR.
|
|
17
|
+
user: "/hstack:research --promote 2026-05-orchestration-patterns"
|
|
18
|
+
assistant: "I'll route through /hstack:adr-new with --from-research 2026-05-orchestration-patterns. spec-author will receive the session findings as the Context section seed and walk the remaining Nygard sections via interview."
|
|
19
|
+
<commentary>
|
|
20
|
+
Promotion routing preserves the conversational interview pattern. The researcher does not write ADRs or tech-debt directly; it hands off via the appropriate Skill so the templates' challenge prompts are exercised.
|
|
21
|
+
</commentary>
|
|
22
|
+
</example>
|
|
23
|
+
tools:
|
|
24
|
+
- Read
|
|
25
|
+
- Write
|
|
26
|
+
- Edit
|
|
27
|
+
- Grep
|
|
28
|
+
- Glob
|
|
29
|
+
- Bash
|
|
30
|
+
- Task
|
|
31
|
+
- WebSearch
|
|
32
|
+
- WebFetch
|
|
33
|
+
- "{{TODO-MCP: Notion MCP — optional; useful when research must include prior team decisions in Notion}}"
|
|
34
|
+
- "{{TODO-MCP: GitHub MCP — optional; useful for searching issues and PRs on third-party SDK repos}}"
|
|
35
|
+
- "{{TODO-SCRIPT: hstack/scripts/validate-spec.ts — validates research session frontmatter}}"
|
|
36
|
+
- "{{TODO-SCRIPT: hstack/scripts/garbage-collect-research.sh — clears sessions past their garbage-collect-after date; promoted sessions exempt}}"
|
|
37
|
+
---
|
|
38
|
+
|
|
39
|
+
## Purpose
|
|
40
|
+
|
|
41
|
+
`hstack-research` produces grounded research outputs via the `researcher` subagent and routes explicit promotion to durable artifacts. The Skill has two modes:
|
|
42
|
+
|
|
43
|
+
- **Default mode.** Invoke the researcher with a query; classify into one of five modes; write a transient session artifact under `hstack/research/sessions/` with sources, confidence markers, and proposed promotion targets.
|
|
44
|
+
- **`--promote <session-id>` mode.** Elevate an existing session to a durable artifact: ADR (route through `hstack-adr-new`), tech-debt (route through `hstack-tech-debt-new`), or a durable note under `hstack/research/promoted/` (the researcher writes this directly).
|
|
45
|
+
|
|
46
|
+
## When to invoke
|
|
47
|
+
|
|
48
|
+
Invoke when the engineer wants to ground a decision or implementation choice in current external information rather than speculation. Common triggers: third-party API integration choices, competitive scans before an ADR, security-CVE checks against pinned dependencies, AI-native pattern lookups (prompt-caching, retrieval, orchestration).
|
|
49
|
+
|
|
50
|
+
## Inputs
|
|
51
|
+
|
|
52
|
+
Default mode:
|
|
53
|
+
- `<query>` (required, positional): the research question, in natural language. The Skill does not require a pre-classified mode — the researcher classifies during the session.
|
|
54
|
+
|
|
55
|
+
Promote mode:
|
|
56
|
+
- `--promote <session-id>` (required): the session to elevate.
|
|
57
|
+
- `--target adr | tech-debt | note` (optional): the promotion target. When omitted, the Skill asks the engineer based on the session's proposed promotion targets.
|
|
58
|
+
|
|
59
|
+
## Preconditions
|
|
60
|
+
|
|
61
|
+
Before any work:
|
|
62
|
+
|
|
63
|
+
- Verify `hstack/config.yaml` exists at `init-status: complete`.
|
|
64
|
+
- Default mode: verify `hstack/research/sessions/` exists; create if absent.
|
|
65
|
+
- Promote mode: verify the named session exists at `hstack/research/sessions/<session-id>.md` and is at `status: current`. Verify the session is not already promoted.
|
|
66
|
+
|
|
67
|
+
## Orchestration steps
|
|
68
|
+
|
|
69
|
+
### Default mode
|
|
70
|
+
|
|
71
|
+
1. **Invoke `researcher`.** Use the Task tool with `subagent_type: researcher` and context = [kernel, query, mode-relevant context docs per the researcher's contract — tech-stack for API/documentation modes, vision/mvp-scope for competitive/AI-native modes, threat-model/hardening-checklist for security-CVE mode]. The subagent classifies the query, applies the mode's source bias, and writes findings incrementally.
|
|
72
|
+
|
|
73
|
+
2. **Source discipline.** Per the `researcher` contract:
|
|
74
|
+
- API-lookup: canonical vendor docs over tutorials; 12-month recency window.
|
|
75
|
+
- Competitive-scan: engineering-side sources over marketing pages; vendors named explicitly.
|
|
76
|
+
- Documentation: canonical sources only; contradictions surfaced rather than papered.
|
|
77
|
+
- Security-CVE: CVE databases and vendor advisories; recency window open; cross-checked against `tech-stack.md` pins.
|
|
78
|
+
- AI-native best practices: 6-month recency bias; engineering blogs and tooling repos over vendor marketing.
|
|
79
|
+
Every source is named with URL and access timestamp. Single-source claims marked explicitly.
|
|
80
|
+
|
|
81
|
+
3. **Confidence markers.** Each finding lands with `high | medium | low` confidence per the researcher's contract.
|
|
82
|
+
|
|
83
|
+
4. **Proposed promotion targets.** The session artifact closes with a Promotion Targets section: "Promote to ADR / tech-debt / research-note? Engineer decides." The Skill does not promote unilaterally.
|
|
84
|
+
|
|
85
|
+
5. **Session artifact frontmatter.** Includes `garbage-collect-after: <today + 30 days>` per the architecture's retention rule. Promoted sessions are exempt; the `--promote` operation sets a flag that the garbage-collector honors.
|
|
86
|
+
|
|
87
|
+
### Promote mode
|
|
88
|
+
|
|
89
|
+
1. **Read the session.** Surface the proposed promotion targets to the engineer.
|
|
90
|
+
|
|
91
|
+
2. **Route by `--target` value:**
|
|
92
|
+
- `--target adr`: invoke `hstack-adr-new` with `--from-research <session-id>` and a slug supplied by the engineer. The ADR's Context section is seeded from the session findings; `spec-author` walks the remaining Nygard sections via its conversational interview, exercising the Consequences challenge prompt.
|
|
93
|
+
- `--target tech-debt`: invoke `hstack-tech-debt-new` with the engineer-supplied slug and any `--origin <change-spec-id>` when applicable. `spec-author` walks the six tech-debt sections.
|
|
94
|
+
- `--target note`: the `researcher` writes a durable note at `hstack/research/promoted/<topic>.md` directly. Free-form structure; no template constraint. This is the only target where the researcher writes the promoted artifact directly — the kernel's promotion-routing rule explicitly permits this for free-form notes.
|
|
95
|
+
|
|
96
|
+
3. **Mark the session as promoted.** Update the session's frontmatter with `promoted-to: adr:<ADR-NNNN>` (or `tech-debt:<TD-NNNN>` or `note:<path>`). Exempt from garbage collection.
|
|
97
|
+
|
|
98
|
+
## Outputs
|
|
99
|
+
|
|
100
|
+
Default mode:
|
|
101
|
+
- `hstack/research/sessions/<YYYY-MM-DD>-<topic-slug>.md` at `status: current`, with query, classified mode(s), sources, findings, options, and proposed promotion targets.
|
|
102
|
+
|
|
103
|
+
Promote mode (depending on `--target`):
|
|
104
|
+
- A new ADR at `hstack/adr/ADR-NNNN-<slug>.md` (via `hstack-adr-new`).
|
|
105
|
+
- A new tech-debt item at `hstack/tech-debt/TD-NNNN-<slug>.md` (via `hstack-tech-debt-new`).
|
|
106
|
+
- A new durable note at `hstack/research/promoted/<topic>.md` (written by the researcher).
|
|
107
|
+
- An edit to the source session marking it `promoted-to: ...`.
|
|
108
|
+
|
|
109
|
+
## Auto-commit triggers
|
|
110
|
+
|
|
111
|
+
- Default mode: one commit when the session artifact lands. Commit message: `research(<topic>): drafted`.
|
|
112
|
+
- Promote mode: the destination Skill's auto-commit fires (ADR or tech-debt). For `--target note`, one commit when the note lands plus the session's `promoted-to` edit.
|
|
113
|
+
|
|
114
|
+
## Idempotency contract
|
|
115
|
+
|
|
116
|
+
- Default mode: re-running with an identical query produces a new session file with today's date in the filename — research is recency-sensitive and re-running is intentional. The engineer may delete the prior session manually, or let the garbage collector handle it after 30 days.
|
|
117
|
+
- Promote mode: re-running on an already-promoted session is a no-op; the Skill detects the `promoted-to` field and exits.
|
|
118
|
+
|
|
119
|
+
## Stop conditions
|
|
120
|
+
|
|
121
|
+
Beyond the kernel's general stop conditions:
|
|
122
|
+
|
|
123
|
+
- Query is too vague to classify into a mode. Ask for clarification.
|
|
124
|
+
- A load-bearing context document is unreachable.
|
|
125
|
+
- Sources are contradictory and the resolution requires a human call.
|
|
126
|
+
- Promote mode: target is unspecified and the engineer has not chosen.
|
|
127
|
+
- Promote mode: the named session does not exist or is already promoted.
|
|
128
|
+
- Promote mode with `--target adr` or `--target tech-debt`: the routed Skill halts; surface the halt message.
|
|
129
|
+
|
|
130
|
+
## Failure modes
|
|
131
|
+
|
|
132
|
+
- **WebSearch / WebFetch rate-limited or unavailable.** Surface the limitation; the researcher proceeds with cached or partial results, naming confidence as `low` for affected findings.
|
|
133
|
+
- **A vendor's docs have moved and the canonical URL no longer resolves.** Note the broken canonical source explicitly; do not silently switch to a tutorial.
|
|
134
|
+
- **Promote-to-ADR or promote-to-tech-debt halts inside `spec-author`'s interview.** The session's `promoted-to` field is not written until the destination artifact is at terminal state. Resume by re-running the destination Skill directly.
|
|
135
|
+
|
|
136
|
+
## Anti-patterns
|
|
137
|
+
|
|
138
|
+
- Never paraphrase vendor marketing as fact.
|
|
139
|
+
- Never assign `high` confidence to a single-source claim.
|
|
140
|
+
- Never invent a CVE id or a version number.
|
|
141
|
+
- Never advocate for an option beyond what the evidence supports — present options with pros / cons / source-backing; the engineer decides.
|
|
142
|
+
- Never promote unilaterally. Promotion is engineer-driven via the explicit flag.
|
|
143
|
+
- Never write ADRs or tech-debt items directly from this Skill. Route via `hstack-adr-new` / `hstack-tech-debt-new`. The exception is `--target note`, which the researcher writes directly because durable notes are free-form.
|
|
144
|
+
- Never silently drop a contradiction between sources.
|
|
145
|
+
- Never load implementer transcripts or per-change artifacts for context bleed; research is upstream of implementation.
|
|
@@ -0,0 +1,133 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: hstack-security-review
|
|
3
|
+
description: |
|
|
4
|
+
Use this skill when a change-spec is at `status: ready-to-plan` or later and needs `security-review.md` produced before the implementer can start. The Skill orchestrates the `security-reviewer` subagent. In v1 the output is an LLM-scored structured judgment (`scoring-mode: llm-scored`), not an executable test result — the Skill enforces this framing on every output. Examples:
|
|
5
|
+
|
|
6
|
+
<example>
|
|
7
|
+
Context: A change-spec introduces a new public-schema table with RLS and is at ready-to-plan.
|
|
8
|
+
user: "/hstack:security-review 2026-05-billing-overage-warning"
|
|
9
|
+
assistant: "I'll invoke security-reviewer. Surfaces is [ui, db], so the threat-model-delta section is mandatory. Scoring biases toward CONCERNS over PASS when evidence is thin; the three challenge prompts run regardless of what surfaces declares."
|
|
10
|
+
<commentary>
|
|
11
|
+
The Skill is the only authoring path for security-review.md. It enforces SR-03 (threat-model-delta required when surfaces touches agent/auth/api/db) and SR-02 (three challenge prompts mandatory). v1 framing is enforced on every rationale.
|
|
12
|
+
</commentary>
|
|
13
|
+
</example>
|
|
14
|
+
|
|
15
|
+
<example>
|
|
16
|
+
Context: A change touches the agent surface — new orchestrator prompt and a new tool boundary — and the threat-model.md has not been touched in eight weeks.
|
|
17
|
+
user: "/hstack:security-review 2026-06-playbook-runner-prompt"
|
|
18
|
+
assistant: "I'll invoke security-reviewer. The threat-model-delta is mandatory because surfaces includes agent; I'll halt if the delta can't be produced from the current threat-model. Findings will frame as structured judgment, not verified by test execution."
|
|
19
|
+
<commentary>
|
|
20
|
+
Agent-surface changes are exactly where the v1 honesty clause matters most. The Skill ensures the subagent does not claim test-backed evidence for prompt-injection resistance — that is v2 substrate work.
|
|
21
|
+
</commentary>
|
|
22
|
+
</example>
|
|
23
|
+
|
|
24
|
+
<example>
|
|
25
|
+
Context: A change is a small refactor with no declared security-sensitive surface, but the diff touches authentication-adjacent code.
|
|
26
|
+
user: "/hstack:security-review 2026-05-auth-helper-rename"
|
|
27
|
+
assistant: "I'll invoke security-reviewer. Even on a refactor, the three challenge prompts run — attack vector not covered by checklist, tenant-isolation citation, malicious-payload behavior — to surface anything the surface declaration may have missed."
|
|
28
|
+
<commentary>
|
|
29
|
+
Refactors near auth are exactly the place where the surface declaration may understate the risk. The challenge-prompt machinery is the v1 mitigation for humans missing what's missing.
|
|
30
|
+
</commentary>
|
|
31
|
+
</example>
|
|
32
|
+
tools:
|
|
33
|
+
- Read
|
|
34
|
+
- Write
|
|
35
|
+
- Edit
|
|
36
|
+
- Grep
|
|
37
|
+
- Glob
|
|
38
|
+
- Bash
|
|
39
|
+
- Task
|
|
40
|
+
- "{{TODO-SCRIPT: hstack/scripts/score-security-review.ts — computes overall status from the scores map}}"
|
|
41
|
+
- "{{TODO-SCRIPT: hstack/scripts/validate-spec.ts — validates security-review frontmatter and SR-01..SR-05}}"
|
|
42
|
+
- "{{TODO-MCP: Supabase MCP — optional in v1 for live RLS introspection; v2 substrate will hard-fail when unreachable for db-surface changes}}"
|
|
43
|
+
---
|
|
44
|
+
|
|
45
|
+
## Purpose
|
|
46
|
+
|
|
47
|
+
`hstack-security-review` produces `security-review.md` for a change-spec by orchestrating the `security-reviewer` subagent. In hstack v1, the artifact is a structured LLM judgment against the hardening checklist plus three mandatory challenge prompts. It is not an executable test artifact; v2 substrate replaces the scoring with real probe outcomes (prompt-injection corpora, RLS bypass attempts, tenant_id fuzzing, secret-redaction probes). This Skill enforces the v1 honesty framing on every output.
|
|
48
|
+
|
|
49
|
+
## When to invoke
|
|
50
|
+
|
|
51
|
+
Invoke when a change-spec reaches `status: ready-to-plan` or later. Security-review can run before, after, or concurrently with `hstack-change-plan` and `hstack-data-review` — none of those gate one another. The implementer refuses to start unless this artifact is at `status: passed` or `concerns-acknowledged`.
|
|
52
|
+
|
|
53
|
+
## Inputs
|
|
54
|
+
|
|
55
|
+
- `<change-id>` (required, positional): the change-spec id.
|
|
56
|
+
|
|
57
|
+
## Preconditions
|
|
58
|
+
|
|
59
|
+
Before any work:
|
|
60
|
+
|
|
61
|
+
- Verify the change-spec exists and is at `status: ready-to-plan` or later.
|
|
62
|
+
- Verify `hstack/context/threat-model.md` is at `status: current` (not `needs-refresh` or absent). Halt otherwise — the subagent refuses to score against a stale or missing threat model.
|
|
63
|
+
- Verify `hstack/context/hardening-checklist.md` is at `status: current`.
|
|
64
|
+
- Read `hstack/context/tech-stack.md` and `ci-cd.md` (loaded by `security-reviewer` for grounding).
|
|
65
|
+
- Determine whether `surfaces` includes any of `agent`, `auth`, `api`, `db`. If yes, set `threat-model-delta-required: true` for the subagent's session.
|
|
66
|
+
- Note whether the Supabase MCP is wired up. If `surfaces` includes `db` and the MCP is unreachable, the Skill proceeds in v1 degraded mode (flagged in rationale) per the v1/v2 split; v2 substrate hard-fails here.
|
|
67
|
+
|
|
68
|
+
## Orchestration steps
|
|
69
|
+
|
|
70
|
+
1. **Invoke `security-reviewer`.** Use the Task tool with `subagent_type: security-reviewer` and context = [kernel, `hstack/templates/security-review.md`, change-spec, threat-model, hardening-checklist, tech-stack, ci-cd]. The subagent scores each applicable hardening item against PASS / CONCERNS / FAIL / not-applicable, with a one-paragraph rationale per item.
|
|
71
|
+
|
|
72
|
+
2. **Threat-model delta.** When `threat-model-delta-required: true`, the subagent writes section 3 with a non-empty delta against the current threat-model.md. SR-03 enforces this at validation.
|
|
73
|
+
|
|
74
|
+
3. **Three challenge prompts (mandatory).** Per SR-02 and the subagent's contract, the subagent answers all three challenge prompts verbatim:
|
|
75
|
+
- "What attack vector did the In-Scope diff create that is NOT covered by the hardening checklist? If none, justify."
|
|
76
|
+
- "Which tenant_isolation guarantee does this change depend on? Cite the line of code that enforces it."
|
|
77
|
+
- "What part of this change would behave incorrectly under a malicious payload that the test suite does not cover?"
|
|
78
|
+
Each answer is at least one paragraph. The Skill verifies `challenge-prompts-answered: 3` in frontmatter.
|
|
79
|
+
|
|
80
|
+
4. **Scoring discipline.** Per the subagent's contract, scoring biases toward CONCERNS when evidence is thin. The Skill does not override this bias. Tenant-isolation citations reference real lines of code; the subagent greps to verify.
|
|
81
|
+
|
|
82
|
+
5. **v1 framing.** Every rationale paragraph uses language like "based on the diff, RLS policy mirrors X" rather than "verified". The Skill rejects any rationale that asserts test-backed evidence — that is v2 substrate territory.
|
|
83
|
+
|
|
84
|
+
6. **Status transitions.** When every applicable score is `pass` or `not-applicable`, the subagent transitions to `status: passed`. When any score is `concerns`, the subagent transitions to `concerns-acknowledged` only when `concerns-acknowledged-by` is non-null (a human handle the owner has explicitly provided) and section 5 enumerates each open concern. Per SR-05, `passed` is impossible if any score is `concerns` or `fail`.
|
|
85
|
+
|
|
86
|
+
7. **Tech-debt for deferred concerns.** When a CONCERNS finding is being deferred rather than fixed, the subagent prompts the engineer to invoke `hstack-tech-debt-new` to create the paper trail. The Skill does not file the tech-debt itself; it surfaces the recommendation.
|
|
87
|
+
|
|
88
|
+
8. **Validate.** Run `{{TODO-SCRIPT: hstack/scripts/validate-spec.ts}}` and `{{TODO-SCRIPT: hstack/scripts/score-security-review.ts}}` — SR-01 through SR-05.
|
|
89
|
+
|
|
90
|
+
## Outputs
|
|
91
|
+
|
|
92
|
+
- `hstack/specs/changes/<change-id>/security-review.md` at `status: passed` or `concerns-acknowledged`.
|
|
93
|
+
- Optional surfaced recommendation to file tech-debt for any deferred CONCERNS.
|
|
94
|
+
|
|
95
|
+
## Auto-commit triggers
|
|
96
|
+
|
|
97
|
+
- Status transition to `in-progress` after the first scores land.
|
|
98
|
+
- Status transition to terminal (`passed` or `concerns-acknowledged`). Commit message: `security-review(<change-id>): passed` or `concerns-acknowledged`.
|
|
99
|
+
- Edits to the `scores` map (because SR-05's terminal-gating depends on it).
|
|
100
|
+
- Edits to `concerns-acknowledged-by` (because it gates SR-04).
|
|
101
|
+
|
|
102
|
+
## Idempotency contract
|
|
103
|
+
|
|
104
|
+
- Re-running on a terminal security-review without diff changes: the subagent reads the existing artifact and produces a no-op diff aside from `updated` timestamps.
|
|
105
|
+
- Re-running after the change-spec's `in-scope` has expanded: the subagent re-scopes the diff read and may produce new scores; the engineer confirms or amends.
|
|
106
|
+
- Re-running mid-authoring after a halt: the subagent reads the partial artifact and resumes at the next un-scored item or unanswered challenge prompt.
|
|
107
|
+
|
|
108
|
+
## Stop conditions
|
|
109
|
+
|
|
110
|
+
Beyond the kernel's general stop conditions:
|
|
111
|
+
|
|
112
|
+
- `threat-model.md` or `hardening-checklist.md` at `needs-refresh` or absent. Halt.
|
|
113
|
+
- Supabase MCP unreachable and `surfaces` includes `db` in a high-stakes context (new schema, new RLS). Halt in v1 if the change is high-stakes; v2 always hard-fails here.
|
|
114
|
+
- A score would require evidence (a test result, runtime check) that does not yet exist. The subagent marks CONCERNS with the missing evidence named; does not synthesize a PASS.
|
|
115
|
+
- `concerns-acknowledged-by` would be written without the owner's explicit acknowledgement. Halt.
|
|
116
|
+
- A forbidden surface is touched (service_role Supabase key in agent code, raw shell against production, Pipedream Connect against live customer accounts). Halt — kernel-level stop condition.
|
|
117
|
+
|
|
118
|
+
## Failure modes
|
|
119
|
+
|
|
120
|
+
- **Threat-model stale.** Halt; refresh via `hstack-configure --interview threat-model`.
|
|
121
|
+
- **Tenant-isolation citation cannot be produced because the In-Scope diff drops tenant context.** Halt and surface — the change introduces a tenant-isolation bug.
|
|
122
|
+
- **Validator fails SR-02 (fewer than 3 challenge prompts answered).** Halt; the subagent re-runs the missing prompt.
|
|
123
|
+
- **v1 framing slips in a rationale.** The Skill detects "verified by test" language in any rationale paragraph and halts; the subagent re-words.
|
|
124
|
+
|
|
125
|
+
## Anti-patterns
|
|
126
|
+
|
|
127
|
+
- Never produce a PASS when evidence is thin. Default to CONCERNS and let the human acknowledge.
|
|
128
|
+
- Never skip or paraphrase a challenge prompt. The three are verbatim and mandatory.
|
|
129
|
+
- Never claim test-backed evidence in v1. The honesty clause is load-bearing.
|
|
130
|
+
- Never write `concerns-acknowledged-by` without the owner's explicit acknowledgement.
|
|
131
|
+
- Never silently fall back to `data-architecture.md` when the live-schema MCP is unreachable on a db-surface change — flag the degradation in the rationale and (in v1) continue if the change is low-stakes, halt if high-stakes.
|
|
132
|
+
- Never fabricate line numbers in tenant_isolation citations.
|
|
133
|
+
- Never file tech-debt from this Skill; surface the recommendation for the engineer to invoke `hstack-tech-debt-new`.
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: hstack-ship
|
|
3
|
+
description: |
|
|
4
|
+
Use this skill when every artifact for a change is at terminal status and the engineer wants the final merge-readiness scorecard and a generated PR description. The Skill is the merge gate's prelude — it checks that every CI gate's preconditions are met, computes the scorecard, and produces the PR description body. It does not perform the merge; the engineer opens or marks the PR ready-for-review themselves. Examples:
|
|
5
|
+
|
|
6
|
+
<example>
|
|
7
|
+
Context: Every artifact for the billing-overage change is at terminal status and the engineer wants to open the PR.
|
|
8
|
+
user: "/hstack:ship 2026-05-billing-overage-warning"
|
|
9
|
+
assistant: "I'll compute the scorecard: spec at ready-to-ship, test-plan passed, plan completed, security-review passed, ui-brief drafted, figma-handoff ready, data-review passed, verification passed, adversarial-review findings-resolved, resolves-tech-debt items at in-progress (GT-11). PR description will land in hstack/specs/changes/<id>/pr-body.md for you to paste; after merge, run /hstack:finalize to flip the TD to resolved."
|
|
10
|
+
<commentary>
|
|
11
|
+
The Skill is mechanical — it reads frontmatter and computes the gate result. No subagent is invoked. If any gate fails, the Skill names the failing artifact and halts.
|
|
12
|
+
</commentary>
|
|
13
|
+
</example>
|
|
14
|
+
|
|
15
|
+
<example>
|
|
16
|
+
Context: The engineer tries to ship a change whose adversarial-review is still at findings-open.
|
|
17
|
+
user: "/hstack:ship 2026-06-knowledge-citations"
|
|
18
|
+
assistant: "I'll halt — adversarial-review is at findings-open. Three findings still at status: open with no resolution. Resolve those via the existing adversarial-review.md before re-running ship."
|
|
19
|
+
<commentary>
|
|
20
|
+
The Skill names the exact blocker and the exact remediation path. It does not advance any status itself; ship is read-only across the artifact set.
|
|
21
|
+
</commentary>
|
|
22
|
+
</example>
|
|
23
|
+
tools:
|
|
24
|
+
- Read
|
|
25
|
+
- Write
|
|
26
|
+
- Grep
|
|
27
|
+
- Glob
|
|
28
|
+
- Bash
|
|
29
|
+
- "{{TODO-SCRIPT: hstack/scripts/validate-spec.ts — validates every artifact's frontmatter}}"
|
|
30
|
+
- "{{TODO-SCRIPT: hstack/scripts/compute-merge-readiness.ts — computes the nine-gate scorecard from artifact frontmatter}}"
|
|
31
|
+
---
|
|
32
|
+
|
|
33
|
+
## Purpose
|
|
34
|
+
|
|
35
|
+
`hstack-ship` is the final merge-readiness Skill. It reads every artifact's frontmatter for the change, computes the nine-gate scorecard from `hstack-gates.yml`, and generates a PR description body. It does not invoke any subagent and does not write to any artifact — `ship` is read-only across the change-spec, plan, reviews, and verification.
|
|
36
|
+
|
|
37
|
+
## When to invoke
|
|
38
|
+
|
|
39
|
+
Invoke when every per-change artifact is at terminal status and the engineer is ready to open or mark the PR ready-for-review. May be invoked multiple times — the Skill is idempotent and is often used as a "what's left?" diagnostic before the final pass.
|
|
40
|
+
|
|
41
|
+
## Inputs
|
|
42
|
+
|
|
43
|
+
- `<change-id>` (required, positional): the change-spec id.
|
|
44
|
+
|
|
45
|
+
## Preconditions
|
|
46
|
+
|
|
47
|
+
Before any work:
|
|
48
|
+
|
|
49
|
+
- Verify the change folder `hstack/specs/changes/<change-id>/` exists.
|
|
50
|
+
- Verify the change-spec exists. Read its `surfaces`, `internal-tooling`, `trivial` flags to know which conditional gates apply.
|
|
51
|
+
|
|
52
|
+
The Skill does not pre-halt on artifact non-terminal status — that is what the scorecard reports. It halts only on missing artifacts or unreadable frontmatter.
|
|
53
|
+
|
|
54
|
+
## Orchestration steps
|
|
55
|
+
|
|
56
|
+
1. **Read every change artifact.** Read `spec.md`, `plan.md`, `test-plan.md`, `security-review.md`, `data-review.md` (when surfaces includes db), `ui-brief.md` and `figma-handoff.md` (when surfaces includes ui), `verification.md`, `adversarial-review.md`. Capture each artifact's `status` and key gating fields.
|
|
57
|
+
|
|
58
|
+
2. **Compute the eleven-gate scorecard.** Run `{{TODO-SCRIPT: hstack/scripts/compute-merge-readiness.ts}}` against the artifact set, or inline the equivalent logic:
|
|
59
|
+
- GT-01: spec presence — change folder exists with non-draft change-spec, or PR carries `trivial: true`.
|
|
60
|
+
- GT-02: diff within scope — every file in the PR diff (against the merge target) is a subset of `change-spec.in-scope`.
|
|
61
|
+
- GT-03: pattern lints — every `hstack/lints/*.yaml` rule passes (the Skill runs `{{TODO-SCRIPT: hstack/scripts/run-gates.sh}}` for this and reads the exit code).
|
|
62
|
+
- GT-04: adversarial-review at `findings-resolved`.
|
|
63
|
+
- GT-05: security-review at `passed` or `concerns-acknowledged`.
|
|
64
|
+
- GT-06: data-review at `passed` or `concerns-acknowledged` (when applicable).
|
|
65
|
+
- GT-07: ui-brief at `drafted` and figma-handoff at `ready` (when applicable).
|
|
66
|
+
- GT-08: `user-stories` non-empty (unless `internal-tooling: true`).
|
|
67
|
+
- GT-09: every cross-reference rule (CG-01..CG-04) passes.
|
|
68
|
+
- GT-10: test-plan at `passed` or `concerns-acknowledged`, and `verification.test-plan-coverage` shows no missing tenant-isolation tests and no out-of-budget performance assertions.
|
|
69
|
+
- GT-11: When `change-spec.resolves-tech-debt` is non-empty: (a) every referenced tech-debt must exist and be at `status: in-progress` with `resolution-attempted-at` set; (b) the adversarial-review must contain the AR-07 Acceptance-satisfied confirmation enumerating each TD's Acceptance bullets against the diff; (c) no referenced tech-debt may have a non-null `resolved-by` already (that would indicate a double-resolution attempt). When `resolves-tech-debt` is empty, GT-11 is `not-applicable`.
|
|
70
|
+
|
|
71
|
+
3. **Frontmatter validation.** Run `{{TODO-SCRIPT: hstack/scripts/validate-spec.ts}}` across every artifact. Any FM-* or per-type validation failure blocks ship.
|
|
72
|
+
|
|
73
|
+
4. **Generate the PR description body.** Write `hstack/specs/changes/<change-id>/pr-body.md` containing:
|
|
74
|
+
- Title: the change-spec's `Problem` first sentence, prefixed with the change id.
|
|
75
|
+
- Summary section: pull the Target Behavior bullets from the change-spec.
|
|
76
|
+
- Surfaces touched: from frontmatter.
|
|
77
|
+
- Linked artifacts: pointers to spec, plan, test-plan, reviews, verification, adversarial-review.
|
|
78
|
+
- Tech-debt created: pointers from `change-spec.creates-tech-debt`.
|
|
79
|
+
- Test plan: pulled from `test-plan.md` — pyramid summary, tenant-isolation tests, and performance budgets — cross-referenced with `verification.test-plan-coverage` to show observed-vs-promised.
|
|
80
|
+
- Tech-debt resolved: pointers from `change-spec.resolves-tech-debt` with each TD's Title and Acceptance summary. When non-empty, the body explicitly notes that `/hstack:finalize <change-id>` must be run post-merge to flip each TD to `resolved`.
|
|
81
|
+
- Scorecard summary: the eleven-gate table from step 2.
|
|
82
|
+
|
|
83
|
+
The pr-body.md is for the engineer to copy into the actual PR description — the Skill does not call `gh pr create` or otherwise open the PR.
|
|
84
|
+
|
|
85
|
+
5. **Advance change-spec status.** When every gate passes, the Skill emits the recommended status transition: `ready-for-review` → `ready-to-ship`. The Skill does not write this transition itself — the engineer either confirms (in which case the engineer can advance via direct edit, or `spec-author` is invoked separately) or addresses any remaining issues. This separation preserves the kernel's rule that humans confirm status transitions to ship-readiness.
|
|
86
|
+
|
|
87
|
+
6. **Surface finalize handoff.** When every gate passes AND `change-spec.resolves-tech-debt` is non-empty, the Skill emits a clear directive: "After this PR merges, run `/hstack:finalize <change-id>` to advance the change-spec to `shipped` and flip [TD-NNNN, TD-MMMM] to `resolved` with `resolved-by` set." When `resolves-tech-debt` is empty, the Skill still notes: "After merge, run `/hstack:finalize <change-id>` to advance the change-spec to `shipped`." The finalize handoff is informational at ship time — the actual writes happen in `/hstack:finalize`, never here.
|
|
88
|
+
|
|
89
|
+
## Outputs
|
|
90
|
+
|
|
91
|
+
- `hstack/specs/changes/<change-id>/pr-body.md` (new or updated) — the PR description body.
|
|
92
|
+
- A scorecard printed to the conversation: per-gate pass/fail summary with the failing artifact and field named for any FAIL.
|
|
93
|
+
- A recommended next action: either "open / mark the PR ready-for-review and advance status to `ready-to-ship`" or a list of failing gates.
|
|
94
|
+
|
|
95
|
+
The Skill does not auto-commit any artifact status transitions. `pr-body.md` is committed when written.
|
|
96
|
+
|
|
97
|
+
## Auto-commit triggers
|
|
98
|
+
|
|
99
|
+
- One commit when `pr-body.md` is written or updated. Commit message: `ship(<change-id>): pr-body`.
|
|
100
|
+
|
|
101
|
+
## Idempotency contract
|
|
102
|
+
|
|
103
|
+
- Re-running on the same change: re-reads every artifact and recomputes the scorecard. `pr-body.md` is rewritten if any artifact has changed since the prior run; otherwise a no-op.
|
|
104
|
+
- Re-running after fixing a failing gate: the scorecard reports the new state.
|
|
105
|
+
|
|
106
|
+
## Stop conditions
|
|
107
|
+
|
|
108
|
+
Beyond the kernel's general stop conditions:
|
|
109
|
+
|
|
110
|
+
- A required artifact is missing on disk.
|
|
111
|
+
- Any artifact's frontmatter cannot be parsed.
|
|
112
|
+
- GT-02 (diff within scope) fails — this is a hard halt with a clear message naming the out-of-scope files; the engineer either reshapes the change-spec via `spec-author` or splits via the multi-module pattern.
|
|
113
|
+
|
|
114
|
+
## Failure modes
|
|
115
|
+
|
|
116
|
+
- **Trivial PRs.** When the change-spec carries `trivial: true`, several gates are skipped per the kernel. The Skill still computes the diff-within-scope and pattern-lint gates (GT-02 and GT-03 remain mandatory even for trivial PRs).
|
|
117
|
+
- **Parent-change (multi-module) records.** When the change-spec is a coordination record (`children` non-empty), the Skill computes scorecards for every child and produces a parent-level summary. The parent reaches ready-to-ship only when every child does.
|
|
118
|
+
- **Pattern-lint failure.** Surface the failing rule and the offending lines. The fix is via a new `hstack-implement` invocation against an appropriate phase (or a scope amendment if the lint surfaced new in-scope needs).
|
|
119
|
+
|
|
120
|
+
## Anti-patterns
|
|
121
|
+
|
|
122
|
+
- Never write status transitions on any artifact from this Skill. Ship is read-only across the artifact set.
|
|
123
|
+
- Never call `gh pr create` or perform the merge. The engineer opens the PR.
|
|
124
|
+
- Never silently pass a gate. Every FAIL names the artifact and field.
|
|
125
|
+
- Never collapse the eleven gates into a single PASS / FAIL. The scorecard is per-gate.
|
|
126
|
+
- Never flip a tech-debt status from this Skill. That is `/hstack:finalize`'s job and only runs post-merge. Ship surfaces the directive; it does not perform the write.
|
|
127
|
+
- Never extend `change-spec.in-scope` to make GT-02 pass — the scope amendment goes through `spec-author`, not this Skill.
|
|
128
|
+
- Never overwrite `pr-body.md` content the engineer has hand-edited without confirmation. If the file exists with edits beyond the template, surface a diff and ask before rewriting.
|
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: hstack-story-draft
|
|
3
|
+
description: |
|
|
4
|
+
Use this skill when a user-facing change needs a story drafted or refined, anchored on an existing persona, with a concrete success metric and the user-visible edge cases enumerated. The Skill orchestrates the `product-manager` subagent and is conditional — it does not run when the parent change-spec has `internal-tooling: true`. Examples:
|
|
5
|
+
|
|
6
|
+
<example>
|
|
7
|
+
Context: The engineer just scaffolded a billing-overage change-spec and needs a linked user story before SP-09 lets the spec advance past draft.
|
|
8
|
+
user: "Draft a story for the billing overage warning, anchored on the growth-marketer persona."
|
|
9
|
+
assistant: "I'll invoke product-manager to walk the five story sections with the growth-marketer persona as the anchor. The story id will land in the configured story store; the change-spec's user-stories array updates reciprocally."
|
|
10
|
+
<commentary>
|
|
11
|
+
Stories are gated by SP-09 (`user-stories` non-empty unless `internal-tooling: true`). The Skill produces the story before the change-spec can advance, and writes the reciprocal `linked-change-specs` entry on the story.
|
|
12
|
+
</commentary>
|
|
13
|
+
</example>
|
|
14
|
+
|
|
15
|
+
<example>
|
|
16
|
+
Context: A story exists but the engineer wants to refine the success metric, which the product-manager flagged as too vague.
|
|
17
|
+
user: "Refine STORY-2026-05-014 — sharpen the success metric."
|
|
18
|
+
assistant: "I'll invoke product-manager with the existing story as the proposal layer. The other sections are accept-or-correct; the success-metric field gets the full interview treatment."
|
|
19
|
+
<commentary>
|
|
20
|
+
Refinement reuses the same orchestration with the existing story as the proposal context. The Skill does not re-walk every field; the subagent reads the existing content and targets the field the engineer named.
|
|
21
|
+
</commentary>
|
|
22
|
+
</example>
|
|
23
|
+
tools:
|
|
24
|
+
- Read
|
|
25
|
+
- Write
|
|
26
|
+
- Edit
|
|
27
|
+
- Grep
|
|
28
|
+
- Glob
|
|
29
|
+
- Bash
|
|
30
|
+
- Task
|
|
31
|
+
- "{{TODO-MCP: Notion MCP — required when configured story store is Notion}}"
|
|
32
|
+
- "{{TODO-MCP: Linear MCP — required when configured story store is Linear}}"
|
|
33
|
+
- "{{TODO-MCP: GitHub MCP — required when configured story store is GitHub Issues}}"
|
|
34
|
+
- "{{TODO-SCRIPT: hstack/scripts/validate-spec.ts — validates story frontmatter and ST-01/ST-02/ST-03}}"
|
|
35
|
+
---
|
|
36
|
+
|
|
37
|
+
## Purpose
|
|
38
|
+
|
|
39
|
+
`hstack-story-draft` produces or refines one user story by orchestrating the `product-manager` subagent. It maintains the reciprocal `user-stories` ↔ `linked-change-specs` linkage between the story and its parent change-spec. It is conditional — skipped automatically for changes marked `internal-tooling: true`.
|
|
40
|
+
|
|
41
|
+
## When to invoke
|
|
42
|
+
|
|
43
|
+
Invoke when the engineer wants a story for a user-facing change before SP-09 / GT-08 require it, or to refine an existing story whose fields the team is reworking. Run after `hstack-change-new` so the parent change-spec already exists and can receive the reciprocal link.
|
|
44
|
+
|
|
45
|
+
## Inputs
|
|
46
|
+
|
|
47
|
+
- `--change <id>` (optional): the parent change-spec id. If omitted, the Skill asks the engineer interactively.
|
|
48
|
+
- `--story <id>` (optional): an existing story id to refine. If omitted, the Skill drafts a new story.
|
|
49
|
+
- `--persona <id>` (optional): the persona to anchor on. If omitted, `product-manager` interviews the engineer for the anchor.
|
|
50
|
+
|
|
51
|
+
## Preconditions
|
|
52
|
+
|
|
53
|
+
Before any work:
|
|
54
|
+
|
|
55
|
+
- Verify `hstack/config.yaml` exists at `init-status: complete`.
|
|
56
|
+
- Verify the parent change-spec exists when `--change` is provided or when context implies it.
|
|
57
|
+
- Verify `hstack/context/personas/` (or the configured personas store) contains at least one persona at `status: current`.
|
|
58
|
+
- Verify the configured story store's MCP is reachable when the store is Notion / Linear / GitHub. If unreachable, halt — the kernel forbids silent fallback to a different store.
|
|
59
|
+
- If the parent change-spec carries `internal-tooling: true`, halt and surface a "story not required" message.
|
|
60
|
+
- Read `hstack/context/vision.md`, `mvp-scope.md`, and the personas index (required by `product-manager`'s session-start protocol).
|
|
61
|
+
|
|
62
|
+
## Orchestration steps
|
|
63
|
+
|
|
64
|
+
1. **Determine mode.** Draft a new story (no `--story` argument) or refine an existing one (`--story <id>` argument). Read the existing story when refining.
|
|
65
|
+
|
|
66
|
+
2. **Invoke `product-manager`.** Use the Task tool with `subagent_type: product-manager` and context = [kernel, `hstack/templates/story.md`, vision, mvp-scope, personas store, parent change-spec when known, existing story when refining]. The subagent runs the five-section interview — Who and Why, What Shipping Looks Like, Success Metric, Edge Cases the User Cares About, Out of Scope for This Story — with confirmation gates.
|
|
67
|
+
|
|
68
|
+
3. **Verify the persona anchor exists.** Per ST-01, the story's `persona` field must reference an existing persona at `current`. If the engineer names a persona that does not exist, `product-manager` halts and runs a sub-interview to author it first (or the engineer chooses an existing one).
|
|
69
|
+
|
|
70
|
+
4. **Exercise the Edge Cases challenge.** Per the `product-manager` contract, the Edge Cases section uses the challenge prompt "What does the user notice if this ships but is slightly broken?" with a minimum of two bullets. The Skill does not bypass this on refinement.
|
|
71
|
+
|
|
72
|
+
5. **Reciprocity.** When the story reaches `status: in-flight` (i.e., its `linked-change-specs` is non-empty), the Skill confirms the parent change-spec's `user-stories` array contains the story id and writes it if absent. The reciprocal write is performed by `product-manager` per its contract (the spec-author handles change-spec field writes generally, but for the `user-stories` array specifically, `product-manager`'s contract permits the reciprocal write).
|
|
73
|
+
|
|
74
|
+
6. **Persist.** When the story store is external (Notion/Linear/GitHub), `product-manager` writes via the MCP and produces a local sync stub at `hstack/stories/<id>.md` referencing the external record. When the store is `hstack/stories/`, the file is written directly.
|
|
75
|
+
|
|
76
|
+
7. **Validate.** Run `{{TODO-SCRIPT: hstack/scripts/validate-spec.ts}}` against the story — ST-01 (persona references existing), ST-02 (linked-change-specs non-empty at `in-flight`), ST-03 (success metric non-empty string).
|
|
77
|
+
|
|
78
|
+
## Outputs
|
|
79
|
+
|
|
80
|
+
- A new or updated story at the configured store, at `status: drafted`, `ready`, or `in-flight` per the engineer's intent.
|
|
81
|
+
- Reciprocal `user-stories: [<story-id>]` entry on the parent change-spec.
|
|
82
|
+
- When the store is external: a sync stub at `hstack/stories/<id>.md`.
|
|
83
|
+
|
|
84
|
+
## Auto-commit triggers
|
|
85
|
+
|
|
86
|
+
- Status transition of the story to `drafted` after the first sections land.
|
|
87
|
+
- Status transition to `ready` or `in-flight` at the end of the interview.
|
|
88
|
+
- Reciprocal write to the parent change-spec's `user-stories` array (commits the parent change-spec file).
|
|
89
|
+
|
|
90
|
+
## Idempotency contract
|
|
91
|
+
|
|
92
|
+
- Re-running with the same `--story` id and identical engineer answers is a no-op aside from `updated` timestamps.
|
|
93
|
+
- Re-running mid-interview after a halt: `product-manager` reads the partial story and resumes at the next un-confirmed field.
|
|
94
|
+
- Re-running to refine: existing values are the proposal layer; accepting all current values is a no-op.
|
|
95
|
+
|
|
96
|
+
## Stop conditions
|
|
97
|
+
|
|
98
|
+
Beyond the kernel's general stop conditions:
|
|
99
|
+
|
|
100
|
+
- The configured story-store MCP is unreachable. Halt.
|
|
101
|
+
- The named persona does not exist and the engineer declines the sub-interview to author it.
|
|
102
|
+
- The success metric the engineer offers is not concretely measurable. `product-manager` re-prompts; the Skill halts after a reasonable number of re-prompts.
|
|
103
|
+
- The story would drift outside `mvp-scope.md`. `product-manager` flags; the Skill asks whether to update mvp-scope (via `hstack-configure --interview mvp-scope`) or defer the story.
|
|
104
|
+
|
|
105
|
+
## Failure modes
|
|
106
|
+
|
|
107
|
+
- **Parent change-spec is `internal-tooling: true`.** Halt early; the story is unnecessary.
|
|
108
|
+
- **Reciprocal write to the parent change-spec would advance its status.** It should not — the reciprocal write only touches the `user-stories` array. If the validator detects a status change, halt and ask.
|
|
109
|
+
- **Validator fails.** Halt and surface; the engineer rewords the failing field.
|
|
110
|
+
|
|
111
|
+
## Anti-patterns
|
|
112
|
+
|
|
113
|
+
- Never anchor a story on an invented persona. The persona either exists at `current` or is authored first via a sub-interview.
|
|
114
|
+
- Never bypass the Edge Cases challenge prompt, even on refinement.
|
|
115
|
+
- Never write a story without a concretely measurable success metric.
|
|
116
|
+
- Never silently fall back to a local story file when the configured external store's MCP is unreachable.
|
|
117
|
+
- Never write reciprocal `user-stories` entries to a change-spec at a non-draft status without going through the `spec-author`'s field-change machinery — except for the array-append case explicitly carved out by `product-manager`'s contract.
|