strikethroo 3.14.3 → 3.16.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/README.md +52 -31
- package/dist/__tests__/fixtures/review-gate.d.ts +59 -0
- package/dist/__tests__/fixtures/review-gate.d.ts.map +1 -0
- package/dist/__tests__/fixtures/review-gate.js +150 -0
- package/dist/__tests__/fixtures/review-gate.js.map +1 -0
- package/dist/cli.js +19 -0
- package/dist/cli.js.map +1 -1
- package/dist/export-profile.d.ts +50 -0
- package/dist/export-profile.d.ts.map +1 -0
- package/dist/export-profile.js +321 -0
- package/dist/export-profile.js.map +1 -0
- package/dist/harnesses/registry.d.ts +4 -2
- package/dist/harnesses/registry.d.ts.map +1 -1
- package/dist/harnesses/registry.js +4 -2
- package/dist/harnesses/registry.js.map +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +67 -3
- package/dist/index.js.map +1 -1
- package/dist/profiles.d.ts +163 -0
- package/dist/profiles.d.ts.map +1 -0
- package/dist/profiles.js +561 -0
- package/dist/profiles.js.map +1 -0
- package/dist/types.d.ts +37 -0
- package/dist/types.d.ts.map +1 -1
- package/dist/types.js +15 -1
- package/dist/types.js.map +1 -1
- package/dist-web/assets/{arc-CsLKjSmD.js → arc-DMHUv2NY.js} +1 -1
- package/dist-web/assets/{architectureDiagram-3BPJPVTR-CUdI2ZME.js → architectureDiagram-3BPJPVTR-CeAAqVS4.js} +1 -1
- package/dist-web/assets/{blockDiagram-GPEHLZMM-BzGl3sJ5.js → blockDiagram-GPEHLZMM-Hns_u_jz.js} +1 -1
- package/dist-web/assets/{c4Diagram-AAUBKEIU-B9BcD268.js → c4Diagram-AAUBKEIU-BH3RLVAi.js} +1 -1
- package/dist-web/assets/channel-Dk0dEQIT.js +1 -0
- package/dist-web/assets/{chunk-2J33WTMH-jrfdvIhS.js → chunk-2J33WTMH-h6Ws9VXu.js} +1 -1
- package/dist-web/assets/{chunk-4BX2VUAB-BppnV9t3.js → chunk-4BX2VUAB-BSBeNNnS.js} +1 -1
- package/dist-web/assets/{chunk-55IACEB6-Dgig1qV7.js → chunk-55IACEB6-BmUY060b.js} +1 -1
- package/dist-web/assets/{chunk-727SXJPM-CssKzpPg.js → chunk-727SXJPM-CmemMVvQ.js} +1 -1
- package/dist-web/assets/{chunk-AQP2D5EJ-DWYbdfaL.js → chunk-AQP2D5EJ-LQpUb_FL.js} +1 -1
- package/dist-web/assets/{chunk-FMBD7UC4-Cbt7Dqxf.js → chunk-FMBD7UC4-wk7OYcdf.js} +1 -1
- package/dist-web/assets/{chunk-ND2GUHAM-2W-YdHxx.js → chunk-ND2GUHAM-O3K3rkHW.js} +1 -1
- package/dist-web/assets/{chunk-QZHKN3VN-BSLdTa36.js → chunk-QZHKN3VN-CvppUbp9.js} +1 -1
- package/dist-web/assets/classDiagram-4FO5ZUOK-gqDJqcDV.js +1 -0
- package/dist-web/assets/classDiagram-v2-Q7XG4LA2-gqDJqcDV.js +1 -0
- package/dist-web/assets/{cose-bilkent-S5V4N54A-D0_MX2M6.js → cose-bilkent-S5V4N54A-Cf1nQ4V_.js} +1 -1
- package/dist-web/assets/{dagre-BM42HDAG-DGXkicI6.js → dagre-BM42HDAG-YyP7mwPP.js} +1 -1
- package/dist-web/assets/{diagram-2AECGRRQ-DMfWZxh-.js → diagram-2AECGRRQ-BmAtTKkQ.js} +1 -1
- package/dist-web/assets/{diagram-5GNKFQAL-IChrzosS.js → diagram-5GNKFQAL-Bem8_DUK.js} +1 -1
- package/dist-web/assets/{diagram-KO2AKTUF-C7IVA_Py.js → diagram-KO2AKTUF-0gNyY9-f.js} +1 -1
- package/dist-web/assets/{diagram-LMA3HP47-UQXc1x2n.js → diagram-LMA3HP47-CJJh_IUU.js} +1 -1
- package/dist-web/assets/{diagram-OG6HWLK6-Z69O_NXy.js → diagram-OG6HWLK6-DJcCho7F.js} +1 -1
- package/dist-web/assets/{erDiagram-TEJ5UH35-xrgfPZU-.js → erDiagram-TEJ5UH35-D-TI_EbX.js} +1 -1
- package/dist-web/assets/{flowDiagram-I6XJVG4X-Co-y5e2I.js → flowDiagram-I6XJVG4X-BUrB4EYN.js} +1 -1
- package/dist-web/assets/{ganttDiagram-6RSMTGT7-C9TOh3M1.js → ganttDiagram-6RSMTGT7-C9_ItheP.js} +1 -1
- package/dist-web/assets/{gitGraphDiagram-PVQCEYII-iBpK83U-.js → gitGraphDiagram-PVQCEYII-DYQEmll0.js} +1 -1
- package/dist-web/assets/{index-DaaOiRou.js → index-DULKNhw0.js} +4 -4
- package/dist-web/assets/{index-6RY653Ds.js → index-X-a-o-AT.js} +1 -1
- package/dist-web/assets/{index-D4y2EDE-.js → index-mEUl0sqe.js} +1 -1
- package/dist-web/assets/{infoDiagram-5YYISTIA-C-_CUdyF.js → infoDiagram-5YYISTIA-B06Tp7cb.js} +1 -1
- package/dist-web/assets/{ishikawaDiagram-YF4QCWOH-zPkWZ6FX.js → ishikawaDiagram-YF4QCWOH-DY9iP3P6.js} +1 -1
- package/dist-web/assets/{journeyDiagram-JHISSGLW-CsTWcFHo.js → journeyDiagram-JHISSGLW-Bk4MV49m.js} +1 -1
- package/dist-web/assets/{kanban-definition-UN3LZRKU-CCsrhCu2.js → kanban-definition-UN3LZRKU-B9-wsNt9.js} +1 -1
- package/dist-web/assets/{linear-DlkSJnhW.js → linear-DEY9HwQB.js} +1 -1
- package/dist-web/assets/{mermaid.core-BM7nlTu6.js → mermaid.core-Cn0e4l6V.js} +4 -4
- package/dist-web/assets/{mindmap-definition-RKZ34NQL-C5tQ7zJH.js → mindmap-definition-RKZ34NQL-pN4Q2WNG.js} +1 -1
- package/dist-web/assets/{pieDiagram-4H26LBE5-CsK9eMOa.js → pieDiagram-4H26LBE5-DTkPv6S2.js} +1 -1
- package/dist-web/assets/{quadrantDiagram-W4KKPZXB-CsUwvpcD.js → quadrantDiagram-W4KKPZXB-BS9LhTv0.js} +1 -1
- package/dist-web/assets/{requirementDiagram-4Y6WPE33-CzQDuhAP.js → requirementDiagram-4Y6WPE33-BlSOLsQe.js} +1 -1
- package/dist-web/assets/{sankeyDiagram-5OEKKPKP-BTa3-BBs.js → sankeyDiagram-5OEKKPKP-B1xl-B1U.js} +1 -1
- package/dist-web/assets/{sequenceDiagram-3UESZ5HK-CPPduAn5.js → sequenceDiagram-3UESZ5HK-BoiYrW_0.js} +1 -1
- package/dist-web/assets/{stateDiagram-AJRCARHV-T5j3NpOr.js → stateDiagram-AJRCARHV-BxvfZYDK.js} +1 -1
- package/dist-web/assets/stateDiagram-v2-BHNVJYJU-XGZY1tGg.js +1 -0
- package/dist-web/assets/{timeline-definition-PNZ67QCA-BG2gG3_T.js → timeline-definition-PNZ67QCA-CUEbrRkc.js} +1 -1
- package/dist-web/assets/{vennDiagram-CIIHVFJN-B3LyjiD_.js → vennDiagram-CIIHVFJN-CgQiBucH.js} +1 -1
- package/dist-web/assets/{wardley-L42UT6IY-CTsJTFG9.js → wardley-L42UT6IY-BsGW6T55.js} +1 -1
- package/dist-web/assets/{wardleyDiagram-YWT4CUSO-cmPISkrt.js → wardleyDiagram-YWT4CUSO-Cq3RMp6B.js} +1 -1
- package/dist-web/assets/{xychartDiagram-2RQKCTM6-BWy_dUgl.js → xychartDiagram-2RQKCTM6-WaoV-V3f.js} +1 -1
- package/dist-web/index.html +1 -1
- package/package.json +3 -3
- package/templates/harness/skills/st-code-review/SKILL.md +309 -0
- package/templates/harness/skills/st-code-review/scripts/code-review.cjs +1539 -0
- package/templates/harness/skills/st-code-review/scripts/find-strikethroo-root.cjs +116 -0
- package/templates/harness/skills/st-code-review/scripts/validate-plan-blueprint.cjs +429 -0
- package/templates/harness/skills/st-execute-blueprint/SKILL.md +48 -1
- package/templates/harness/skills/st-execute-blueprint/scripts/capture-base-commit.cjs +325 -0
- package/templates/harness/skills/st-execute-blueprint/scripts/dispatch-task-execution.cjs +46 -26
- package/templates/harness/skills/st-execute-task/scripts/dispatch-task-execution.cjs +46 -26
- package/templates/harness/skills/st-full-workflow/SKILL.md +48 -1
- package/templates/harness/skills/st-full-workflow/scripts/capture-base-commit.cjs +325 -0
- package/templates/harness/skills/st-full-workflow/scripts/dispatch-task-execution.cjs +46 -26
- package/templates/strikethroo/config/hooks/CODE_REVIEW.md +60 -0
- package/templates/strikethroo/config/schemas/self-review-v2.xsd +437 -0
- package/dist-web/assets/channel-CN9J8c_F.js +0 -1
- package/dist-web/assets/classDiagram-4FO5ZUOK-DHR8VHf9.js +0 -1
- package/dist-web/assets/classDiagram-v2-Q7XG4LA2-DHR8VHf9.js +0 -1
- package/dist-web/assets/stateDiagram-v2-BHNVJYJU-CXpXsXHt.js +0 -1
package/README.md
CHANGED
|
@@ -3,8 +3,8 @@
|
|
|
3
3
|
</p>
|
|
4
4
|
|
|
5
5
|
<p align="center">
|
|
6
|
-
<strong>Spec-driven development
|
|
7
|
-
|
|
6
|
+
<strong>Spec-driven development optimized for time-to-merge, not time-to-first-draft.</strong><br>
|
|
7
|
+
You review the plan, where a correction costs a sentence — not the diff, where it costs a review cycle.
|
|
8
8
|
</p>
|
|
9
9
|
|
|
10
10
|
<p align="center">
|
|
@@ -15,6 +15,7 @@
|
|
|
15
15
|
</p>
|
|
16
16
|
|
|
17
17
|
<p align="center">
|
|
18
|
+
<a href="https://strikethroo.canpicasoft.com/why.html">Why Strikethroo</a> ·
|
|
18
19
|
<a href="https://strikethroo.canpicasoft.com/workflow.html">Workflow</a> ·
|
|
19
20
|
<a href="https://strikethroo.canpicasoft.com/customization.html">Customization</a> ·
|
|
20
21
|
<a href="https://strikethroo.canpicasoft.com/visualizations.html">Visualizations</a> ·
|
|
@@ -23,50 +24,57 @@
|
|
|
23
24
|
|
|
24
25
|
## Why Strikethroo?
|
|
25
26
|
|
|
27
|
+
Most spec-driven tools optimize the input: better spec in, better code out, human catches the rest at the end. Strikethroo assumes the agent is an unreliable narrator of its own work -- including a second agent asked to review the first -- and that the scarce resource is your attention, not tokens.
|
|
28
|
+
|
|
26
29
|
<table>
|
|
27
30
|
<tr>
|
|
28
31
|
<td width="50%" valign="top">
|
|
29
32
|
|
|
30
|
-
<img src="docs/assets/icons/
|
|
33
|
+
<img src="docs/assets/icons/focus.svg" width="28" height="28" alt="" />
|
|
31
34
|
|
|
32
|
-
###
|
|
35
|
+
### You review the plan, not the diff
|
|
33
36
|
|
|
34
|
-
|
|
37
|
+
Correcting a plan costs a sentence. Correcting the same misunderstanding in a diff costs a review cycle, a rework cycle, and a re-review. An explicit approval gate puts your careful read where it is worth the most, and one question is asked at a time so it never gets skim-answered.
|
|
35
38
|
|
|
36
39
|
</td>
|
|
37
40
|
<td width="50%" valign="top">
|
|
38
41
|
|
|
39
|
-
<img src="docs/assets/icons/
|
|
42
|
+
<img src="docs/assets/icons/shield-check.svg" width="28" height="28" alt="" />
|
|
40
43
|
|
|
41
|
-
###
|
|
44
|
+
### Guarantees are compiled, not requested
|
|
42
45
|
|
|
43
|
-
|
|
46
|
+
A rule in Markdown is a request; a rule in TypeScript is a guarantee. Hooks and templates are yours to edit. Termination bounds, safety floors, and fail-safe defaults are compiled -- `MAX_REVIEW_ROUNDS` can be tightened by config and raised by nothing.
|
|
44
47
|
|
|
45
48
|
</td>
|
|
46
49
|
</tr>
|
|
47
50
|
<tr>
|
|
48
51
|
<td width="50%" valign="top">
|
|
49
52
|
|
|
50
|
-
<img src="docs/assets/icons/
|
|
53
|
+
<img src="docs/assets/icons/git-fork.svg" width="28" height="28" alt="" />
|
|
51
54
|
|
|
52
|
-
###
|
|
55
|
+
### Nobody marks their own homework
|
|
53
56
|
|
|
54
|
-
|
|
57
|
+
The optional review gate runs on a *different* harness than the one that wrote the code -- the current harness is structurally excluded from the candidate set, not merely deprioritized. The reviewer detects and never fixes; remediation is dispatched separately.
|
|
55
58
|
|
|
56
59
|
</td>
|
|
57
|
-
<td>
|
|
60
|
+
<td width="50%" valign="top">
|
|
58
61
|
|
|
59
|
-
<img src="docs/assets/icons/
|
|
62
|
+
<img src="docs/assets/icons/sliders-horizontal.svg" width="28" height="28" alt="" />
|
|
60
63
|
|
|
61
|
-
###
|
|
64
|
+
### Bends to your conventions
|
|
62
65
|
|
|
63
|
-
|
|
66
|
+
Plain-Markdown hooks fire at eleven points across the workflow; inject your test commands, standards, and domain rules so every plan, task, and run inherits them. No plugins, no code.
|
|
64
67
|
|
|
65
68
|
</td>
|
|
66
|
-
<td width="50%" valign="top"></td>
|
|
67
69
|
</tr>
|
|
68
70
|
</table>
|
|
69
71
|
|
|
72
|
+
**Speed, measured honestly.** The industry clock starts at the prompt and stops when code appears. The clock that pays your salary stops when the code is **merged** -- and on that clock, generation is a rounding error next to the review rounds a fast-but-wrong draft costs you. Strikethroo is built against the second clock. That is not quality traded for speed; on that clock they are the same number.
|
|
73
|
+
|
|
74
|
+
Read the full thesis, with the file-by-file claims to verify it yourself: **[Why Strikethroo](https://strikethroo.canpicasoft.com/why.html)**.
|
|
75
|
+
|
|
76
|
+
<sub>Also true, and less interesting: no API keys (runs on the subscription you already pay for), harness-agnostic Agent Skills (one `SKILL.md` on any harness supporting the format), and clean per-agent context at every step.</sub>
|
|
77
|
+
|
|
70
78
|
## Adapts to every codebase
|
|
71
79
|
|
|
72
80
|
Every codebase has its own conventions, and Strikethroo bends to them instead of imposing its own. Three plain-Markdown surfaces -- no plugins, no code:
|
|
@@ -75,7 +83,7 @@ Every codebase has its own conventions, and Strikethroo bends to them instead of
|
|
|
75
83
|
|
|
76
84
|
### <img src="docs/assets/icons/waypoints.svg" width="28" height="28" alt="" /> Hooks
|
|
77
85
|
|
|
78
|
-
Fire at
|
|
86
|
+
Fire at eleven points across the workflow (before planning, after each phase, on errors, and more). Drop in your test commands, coding standards, and domain rules; every plan, task, and execution run inherits them.
|
|
79
87
|
|
|
80
88
|
### <img src="docs/assets/icons/file-text.svg" width="28" height="28" alt="" /> Templates
|
|
81
89
|
|
|
@@ -99,6 +107,10 @@ npx skills add e0ipso/strikethroo
|
|
|
99
107
|
|
|
100
108
|
Requires Node.js 22+ and an assistant that supports the Agent Skills format.
|
|
101
109
|
|
|
110
|
+
## Profiles: a tailored setup in one step
|
|
111
|
+
|
|
112
|
+
A strikethroo profile packages a complete workspace configuration -- hooks, templates, project context -- so `init --profile <folder | user/repo | git URL>` starts from a setup tuned for your stack instead of the shipped defaults, and `export profile` packages yours to share. See [Strikethroo profiles](https://strikethroo.canpicasoft.com/customization.html#strikethroo-profiles) in the Customization Guide.
|
|
113
|
+
|
|
102
114
|
## In your coding assistant
|
|
103
115
|
|
|
104
116
|
```mermaid
|
|
@@ -106,23 +118,23 @@ flowchart LR
|
|
|
106
118
|
A[Work Order] --> B[Plan]
|
|
107
119
|
B --> C{Review}
|
|
108
120
|
C -->|Edit| B
|
|
109
|
-
C -->|Approve|
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
H -->|Edit| G
|
|
114
|
-
H -->|Approve| J[Done]
|
|
121
|
+
C -->|Approve| G["Execute<br/>(generates tasks)"]
|
|
122
|
+
G --> H["Code Review<br/>(optional)"]
|
|
123
|
+
H -->|Fix| G
|
|
124
|
+
H -->|Pass| J[Done]
|
|
115
125
|
```
|
|
116
126
|
|
|
117
|
-
|
|
127
|
+
**Two commands.** Read the plan, approve it, run it:
|
|
128
|
+
|
|
129
|
+
| Step | Command | Output |
|
|
130
|
+
|-------------|---------------------------------|---------------------------------------------------------|
|
|
131
|
+
| **Plan** | `/st-create-plan <your prompt>` | `.ai/strikethroo/plans/64--auth/plan-64--auth.md` |
|
|
132
|
+
| **Execute** | `/st-execute-blueprint 64` | Task blueprint, then working code, one commit per phase |
|
|
133
|
+
| **Review** | Automatic (optional) | Findings validated against schema; bounded fixes |
|
|
118
134
|
|
|
119
|
-
|
|
120
|
-
|-------------|---------------------------------|---------------------------------------------------|
|
|
121
|
-
| **Plan** | `/st-create-plan <your prompt>` | `.ai/strikethroo/plans/64--auth/plan-64--auth.md` |
|
|
122
|
-
| **Tasks** | `/st-generate-tasks 64` | `.ai/strikethroo/plans/64--auth/tasks/*.md` |
|
|
123
|
-
| **Execute** | `/st-execute-blueprint 64` | Working code, one commit per phase |
|
|
135
|
+
`st-execute-blueprint` decomposes the plan into atomic tasks and builds the dependency-mapped blueprint itself when one does not exist yet. Run `/st-generate-tasks 64` on its own only when you want to inspect or hand-tune the blueprint before execution starts.
|
|
124
136
|
|
|
125
|
-
|
|
137
|
+
Your review lands on the plan, before any code exists -- that is where a correction costs a sentence. Each step runs with clean context: the planning agent sees only the work order, and each execution sub-agent receives only its specific task. After execution, an optional automated review gate runs on a discovered second harness, critiques the cumulative diff, and drives bounded remediation if findings exceed configured thresholds.
|
|
126
138
|
|
|
127
139
|
See the [Workflow Guide](https://strikethroo.canpicasoft.com/workflow.html) for the full step-by-step with advanced patterns. Once a plan exists, visualize its plans, tasks, and dependency graph in [Visualizations](https://strikethroo.canpicasoft.com/visualizations.html).
|
|
128
140
|
|
|
@@ -139,10 +151,19 @@ This will open a web page that will help you navigate your plans and their tasks
|
|
|
139
151
|
|-------------------------------------------------------------|------------------------------------------------------------------------------------------------------------------------|-------------------------------------------------------------|
|
|
140
152
|
| [](docs/assets/plans-board.png) | [](docs/assets/plan-detail-graph.png) | [](docs/assets/archive-all.png) |
|
|
141
153
|
|
|
154
|
+
## Optional Code Review Gate
|
|
155
|
+
|
|
156
|
+
After blueprint execution, an optional automated code review gate runs when a second harness is discovered. The reviewer critiques the cumulative diff against the plan's requirements, emits findings validated against a schema, and hands high-confidence findings to the implementer for remediation. Any applied fix forces a full re-run of tests and validation before re-verification.
|
|
157
|
+
|
|
158
|
+
**To disable:** Edit `.ai/strikethroo/config/hooks/CODE_REVIEW.md` to empty or delete it. The gate skips cleanly with a note in the execution summary.
|
|
159
|
+
|
|
160
|
+
**Important:** A green review gate is not a correctness guarantee. The gate reduces exposure to the same class of error a human PR approval reduces, and leaves the same class of error behind. See [Customization](https://strikethroo.canpicasoft.com/customization.html) for limitations and configuration.
|
|
161
|
+
|
|
142
162
|
## Documentation
|
|
143
163
|
|
|
164
|
+
- [Why Strikethroo](https://strikethroo.canpicasoft.com/why.html) -- The design thesis, the trade-offs stated plainly, and how to verify the claims
|
|
144
165
|
- [Workflow Guide](https://strikethroo.canpicasoft.com/workflow.html) -- Step-by-step workflow with visual guides
|
|
145
|
-
- [Customization Guide](https://strikethroo.canpicasoft.com/customization.html) -- Hooks, templates, and
|
|
166
|
+
- [Customization Guide](https://strikethroo.canpicasoft.com/customization.html) -- Hooks, templates, project context, and code review configuration
|
|
146
167
|
- [Reference](https://strikethroo.canpicasoft.com/reference.html) -- Glossary and CLI reference
|
|
147
168
|
- [FAQ](https://strikethroo.canpicasoft.com/faq.html) -- Answers to common questions
|
|
148
169
|
- [Visualizations](https://strikethroo.canpicasoft.com/visualizations.html) -- See plans, tasks, and the dependency graph
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared fixture factories for the review-gate test suites
|
|
3
|
+
* (`harness-discovery.test.ts`, `capture-base-commit.integration.test.ts`,
|
|
4
|
+
* `code-review.integration.test.ts`, `review-findings.integration.test.ts`).
|
|
5
|
+
*
|
|
6
|
+
* Two factories: a minimal v4 workspace whose hook/XSD/base-commit presence is
|
|
7
|
+
* independently switchable (so each fail-safe skip reason is one toggle away),
|
|
8
|
+
* and a `<review>` XML builder so partition/validation tests describe findings
|
|
9
|
+
* as data instead of hand-written XML.
|
|
10
|
+
*/
|
|
11
|
+
export declare const REAL_HOOK_CONTENT: string;
|
|
12
|
+
export declare const REAL_XSD_PATH: string;
|
|
13
|
+
/** A syntactically valid placeholder sha — never a real commit, just 40 hex chars. */
|
|
14
|
+
export declare const FAKE_SHA: string;
|
|
15
|
+
export interface ReviewGateWorkspaceOptions {
|
|
16
|
+
/** `'default'` copies the real shipped hook; `'absent'` skips the file; a string is literal content. */
|
|
17
|
+
hook?: 'default' | 'absent' | string;
|
|
18
|
+
/** `'default'` copies the real vendored XSD; `'absent'` skips the file. */
|
|
19
|
+
xsd?: 'default' | 'absent';
|
|
20
|
+
/** A 40-hex sha to record, or `'absent'` to skip writing base-commit.json. */
|
|
21
|
+
baseCommit?: string | 'absent';
|
|
22
|
+
planId?: number;
|
|
23
|
+
planSlug?: string;
|
|
24
|
+
}
|
|
25
|
+
export interface ReviewGateWorkspace {
|
|
26
|
+
/** The temporary project root — the directory a real `git init` would run in. */
|
|
27
|
+
root: string;
|
|
28
|
+
strikethrooRoot: string;
|
|
29
|
+
planDir: string;
|
|
30
|
+
planFile: string;
|
|
31
|
+
hookFile: string;
|
|
32
|
+
xsdFile: string;
|
|
33
|
+
baseCommitFile: string;
|
|
34
|
+
cleanup: () => void;
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Builds `<root>/.ai/strikethroo/...` with a v4 `.init-metadata.json`, one plan
|
|
38
|
+
* directory with a valid frontmatter, and switchable hook/XSD/base-commit
|
|
39
|
+
* presence — every input the review gate's fail-safe skip ladder depends on.
|
|
40
|
+
*/
|
|
41
|
+
export declare const makeReviewGateWorkspace: (options?: ReviewGateWorkspaceOptions) => ReviewGateWorkspace;
|
|
42
|
+
export interface FindingSpec {
|
|
43
|
+
file: string;
|
|
44
|
+
severity?: string;
|
|
45
|
+
confidence?: string;
|
|
46
|
+
hasSuggestion?: boolean;
|
|
47
|
+
category?: string;
|
|
48
|
+
body?: string;
|
|
49
|
+
/** Verbatim XML to splice in place of the generated <body>/<category>/<suggestion> — for malformed-content cases (CDATA, escaped markup). */
|
|
50
|
+
rawInner?: string;
|
|
51
|
+
}
|
|
52
|
+
/**
|
|
53
|
+
* Renders a schema-shaped `<review>` document from finding descriptions, one
|
|
54
|
+
* `<file>` per distinct `file` value (in first-seen order). Kept intentionally
|
|
55
|
+
* simple string concatenation — the documents under test are small and the
|
|
56
|
+
* point is to describe findings as data, not to build a general XML writer.
|
|
57
|
+
*/
|
|
58
|
+
export declare const buildReviewXml: (findings: readonly FindingSpec[], timestamp?: string) => string;
|
|
59
|
+
//# sourceMappingURL=review-gate.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"review-gate.d.ts","sourceRoot":"","sources":["../../../src/__tests__/fixtures/review-gate.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAyBH,eAAO,MAAM,iBAAiB,QAA4C,CAAC;AAC3E,eAAO,MAAM,aAAa,QAAkB,CAAC;AAE7C,sFAAsF;AACtF,eAAO,MAAM,QAAQ,QAAiB,CAAC;AAEvC,MAAM,WAAW,0BAA0B;IACzC,wGAAwG;IACxG,IAAI,CAAC,EAAE,SAAS,GAAG,QAAQ,GAAG,MAAM,CAAC;IACrC,2EAA2E;IAC3E,GAAG,CAAC,EAAE,SAAS,GAAG,QAAQ,CAAC;IAC3B,8EAA8E;IAC9E,UAAU,CAAC,EAAE,MAAM,GAAG,QAAQ,CAAC;IAC/B,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,mBAAmB;IAClC,iFAAiF;IACjF,IAAI,EAAE,MAAM,CAAC;IACb,eAAe,EAAE,MAAM,CAAC;IACxB,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,MAAM,CAAC;IAChB,cAAc,EAAE,MAAM,CAAC;IACvB,OAAO,EAAE,MAAM,IAAI,CAAC;CACrB;AAED;;;;GAIG;AACH,eAAO,MAAM,uBAAuB,GAClC,UAAS,0BAA+B,KACvC,mBA4DF,CAAC;AAEF,MAAM,WAAW,WAAW;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,6IAA6I;IAC7I,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED;;;;;GAKG;AACH,eAAO,MAAM,cAAc,GACzB,UAAU,SAAS,WAAW,EAAE,EAChC,kBAAkC,KACjC,MAuCF,CAAC"}
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Shared fixture factories for the review-gate test suites
|
|
4
|
+
* (`harness-discovery.test.ts`, `capture-base-commit.integration.test.ts`,
|
|
5
|
+
* `code-review.integration.test.ts`, `review-findings.integration.test.ts`).
|
|
6
|
+
*
|
|
7
|
+
* Two factories: a minimal v4 workspace whose hook/XSD/base-commit presence is
|
|
8
|
+
* independently switchable (so each fail-safe skip reason is one toggle away),
|
|
9
|
+
* and a `<review>` XML builder so partition/validation tests describe findings
|
|
10
|
+
* as data instead of hand-written XML.
|
|
11
|
+
*/
|
|
12
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
13
|
+
if (k2 === undefined) k2 = k;
|
|
14
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
15
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
16
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
17
|
+
}
|
|
18
|
+
Object.defineProperty(o, k2, desc);
|
|
19
|
+
}) : (function(o, m, k, k2) {
|
|
20
|
+
if (k2 === undefined) k2 = k;
|
|
21
|
+
o[k2] = m[k];
|
|
22
|
+
}));
|
|
23
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
24
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
25
|
+
}) : function(o, v) {
|
|
26
|
+
o["default"] = v;
|
|
27
|
+
});
|
|
28
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
29
|
+
var ownKeys = function(o) {
|
|
30
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
31
|
+
var ar = [];
|
|
32
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
33
|
+
return ar;
|
|
34
|
+
};
|
|
35
|
+
return ownKeys(o);
|
|
36
|
+
};
|
|
37
|
+
return function (mod) {
|
|
38
|
+
if (mod && mod.__esModule) return mod;
|
|
39
|
+
var result = {};
|
|
40
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
41
|
+
__setModuleDefault(result, mod);
|
|
42
|
+
return result;
|
|
43
|
+
};
|
|
44
|
+
})();
|
|
45
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
46
|
+
exports.buildReviewXml = exports.makeReviewGateWorkspace = exports.FAKE_SHA = exports.REAL_XSD_PATH = exports.REAL_HOOK_CONTENT = void 0;
|
|
47
|
+
const fs = __importStar(require("fs"));
|
|
48
|
+
const os = __importStar(require("os"));
|
|
49
|
+
const path = __importStar(require("path"));
|
|
50
|
+
const metadata_1 = require("../../metadata");
|
|
51
|
+
const REPO_ROOT = path.resolve(__dirname, '..', '..', '..');
|
|
52
|
+
const REAL_XSD_SOURCE = path.join(REPO_ROOT, 'templates', 'strikethroo', 'config', 'schemas', 'self-review-v2.xsd');
|
|
53
|
+
const REAL_HOOK_SOURCE = path.join(REPO_ROOT, 'templates', 'strikethroo', 'config', 'hooks', 'CODE_REVIEW.md');
|
|
54
|
+
exports.REAL_HOOK_CONTENT = fs.readFileSync(REAL_HOOK_SOURCE, 'utf8');
|
|
55
|
+
exports.REAL_XSD_PATH = REAL_XSD_SOURCE;
|
|
56
|
+
/** A syntactically valid placeholder sha — never a real commit, just 40 hex chars. */
|
|
57
|
+
exports.FAKE_SHA = 'a'.repeat(40);
|
|
58
|
+
/**
|
|
59
|
+
* Builds `<root>/.ai/strikethroo/...` with a v4 `.init-metadata.json`, one plan
|
|
60
|
+
* directory with a valid frontmatter, and switchable hook/XSD/base-commit
|
|
61
|
+
* presence — every input the review gate's fail-safe skip ladder depends on.
|
|
62
|
+
*/
|
|
63
|
+
const makeReviewGateWorkspace = (options = {}) => {
|
|
64
|
+
const planId = options.planId ?? 1;
|
|
65
|
+
const planSlug = options.planSlug ?? 'demo';
|
|
66
|
+
const root = fs.mkdtempSync(path.join(os.tmpdir(), 'strikethroo-review-gate-'));
|
|
67
|
+
const strikethrooRoot = path.join(root, '.ai', 'strikethroo');
|
|
68
|
+
const planDir = path.join(strikethrooRoot, 'plans', `${planId}--${planSlug}`);
|
|
69
|
+
fs.mkdirSync(planDir, { recursive: true });
|
|
70
|
+
fs.mkdirSync(path.join(strikethrooRoot, 'config', 'hooks'), { recursive: true });
|
|
71
|
+
fs.mkdirSync(path.join(strikethrooRoot, 'config', 'schemas'), { recursive: true });
|
|
72
|
+
fs.writeFileSync(path.join(strikethrooRoot, '.init-metadata.json'), JSON.stringify({
|
|
73
|
+
version: 'test',
|
|
74
|
+
workspaceSchemaVersion: metadata_1.CURRENT_WORKSPACE_SCHEMA_VERSION,
|
|
75
|
+
timestamp: new Date().toISOString(),
|
|
76
|
+
files: {},
|
|
77
|
+
}));
|
|
78
|
+
const planFile = path.join(planDir, `plan-${planId}--${planSlug}.md`);
|
|
79
|
+
fs.writeFileSync(planFile, `---\nid: ${planId}\nsummary: "fixture"\ncreated: 2026-01-01\n---\nbody\n`);
|
|
80
|
+
const hookFile = path.join(strikethrooRoot, 'config', 'hooks', 'CODE_REVIEW.md');
|
|
81
|
+
const hook = options.hook ?? 'default';
|
|
82
|
+
if (hook !== 'absent') {
|
|
83
|
+
fs.writeFileSync(hookFile, hook === 'default' ? exports.REAL_HOOK_CONTENT : hook);
|
|
84
|
+
}
|
|
85
|
+
const xsdFile = path.join(strikethrooRoot, 'config', 'schemas', 'self-review-v2.xsd');
|
|
86
|
+
if ((options.xsd ?? 'default') !== 'absent') {
|
|
87
|
+
fs.copyFileSync(REAL_XSD_SOURCE, xsdFile);
|
|
88
|
+
}
|
|
89
|
+
const baseCommitFile = path.join(planDir, 'review', 'base-commit.json');
|
|
90
|
+
if (options.baseCommit !== undefined && options.baseCommit !== 'absent') {
|
|
91
|
+
fs.mkdirSync(path.dirname(baseCommitFile), { recursive: true });
|
|
92
|
+
fs.writeFileSync(baseCommitFile, `${JSON.stringify({
|
|
93
|
+
version: 1,
|
|
94
|
+
baseCommit: options.baseCommit,
|
|
95
|
+
capturedAt: new Date().toISOString(),
|
|
96
|
+
})}\n`);
|
|
97
|
+
}
|
|
98
|
+
return {
|
|
99
|
+
root,
|
|
100
|
+
strikethrooRoot,
|
|
101
|
+
planDir,
|
|
102
|
+
planFile,
|
|
103
|
+
hookFile,
|
|
104
|
+
xsdFile,
|
|
105
|
+
baseCommitFile,
|
|
106
|
+
cleanup: () => fs.rmSync(root, { recursive: true, force: true }),
|
|
107
|
+
};
|
|
108
|
+
};
|
|
109
|
+
exports.makeReviewGateWorkspace = makeReviewGateWorkspace;
|
|
110
|
+
/**
|
|
111
|
+
* Renders a schema-shaped `<review>` document from finding descriptions, one
|
|
112
|
+
* `<file>` per distinct `file` value (in first-seen order). Kept intentionally
|
|
113
|
+
* simple string concatenation — the documents under test are small and the
|
|
114
|
+
* point is to describe findings as data, not to build a general XML writer.
|
|
115
|
+
*/
|
|
116
|
+
const buildReviewXml = (findings, timestamp = '2026-01-01T00:00:00Z') => {
|
|
117
|
+
const order = [];
|
|
118
|
+
const byFile = new Map();
|
|
119
|
+
for (const finding of findings) {
|
|
120
|
+
if (!byFile.has(finding.file)) {
|
|
121
|
+
byFile.set(finding.file, []);
|
|
122
|
+
order.push(finding.file);
|
|
123
|
+
}
|
|
124
|
+
byFile.get(finding.file).push(finding);
|
|
125
|
+
}
|
|
126
|
+
const filesXml = order
|
|
127
|
+
.map(file => {
|
|
128
|
+
const comments = byFile
|
|
129
|
+
.get(file)
|
|
130
|
+
.map(finding => {
|
|
131
|
+
const attrs = (finding.severity ? ` severity="${finding.severity}"` : '') +
|
|
132
|
+
(finding.confidence ? ` confidence="${finding.confidence}"` : '');
|
|
133
|
+
if (finding.rawInner !== undefined) {
|
|
134
|
+
return `<comment${attrs}>${finding.rawInner}</comment>`;
|
|
135
|
+
}
|
|
136
|
+
const suggestion = finding.hasSuggestion
|
|
137
|
+
? '<suggestion><original-code>old</original-code><proposed-code>new</proposed-code></suggestion>'
|
|
138
|
+
: '';
|
|
139
|
+
return (`<comment${attrs}><body>${finding.body ?? 'A finding.'}</body>` +
|
|
140
|
+
`<category>${finding.category ?? 'bug'}</category>${suggestion}</comment>`);
|
|
141
|
+
})
|
|
142
|
+
.join('');
|
|
143
|
+
return `<file path="${file}" change-type="modified" viewed="true">${comments}</file>`;
|
|
144
|
+
})
|
|
145
|
+
.join('');
|
|
146
|
+
return ('<?xml version="1.0" encoding="UTF-8"?>\n' +
|
|
147
|
+
`<review xmlns="urn:self-review:v2" timestamp="${timestamp}">${filesXml}</review>\n`);
|
|
148
|
+
};
|
|
149
|
+
exports.buildReviewXml = buildReviewXml;
|
|
150
|
+
//# sourceMappingURL=review-gate.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"review-gate.js","sourceRoot":"","sources":["../../../src/__tests__/fixtures/review-gate.ts"],"names":[],"mappings":"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"}
|
package/dist/cli.js
CHANGED
|
@@ -11,6 +11,7 @@ const commander_1 = require("commander");
|
|
|
11
11
|
const index_1 = require("./index");
|
|
12
12
|
const root_1 = require("./serve/root");
|
|
13
13
|
const server_1 = require("./serve/server");
|
|
14
|
+
const export_profile_1 = require("./export-profile");
|
|
14
15
|
const program = new commander_1.Command();
|
|
15
16
|
program.name('strikethroo').version('0.1.0').description('AI-powered task management CLI tool');
|
|
16
17
|
program
|
|
@@ -19,6 +20,7 @@ program
|
|
|
19
20
|
.requiredOption('--harnesses <value>', 'Comma-separated list of harnesses to configure (claude,codex,cursor,gemini,copilot,opencode)')
|
|
20
21
|
.option('--destination-directory <path>', 'Directory to create project structure in (default: current directory)')
|
|
21
22
|
.option('--force', 'Force overwrite all files without prompting')
|
|
23
|
+
.option('--profile <value>', 'Strikethroo profile to import: local folder, <user>/<repo> GitHub shorthand, or full git URL')
|
|
22
24
|
.action(async (options) => {
|
|
23
25
|
try {
|
|
24
26
|
// Execute the init command
|
|
@@ -36,6 +38,23 @@ program
|
|
|
36
38
|
process.exit(1);
|
|
37
39
|
}
|
|
38
40
|
});
|
|
41
|
+
const exportCommand = program
|
|
42
|
+
.command('export')
|
|
43
|
+
.description('Export workspace artifacts for reuse elsewhere');
|
|
44
|
+
exportCommand
|
|
45
|
+
.command('profile')
|
|
46
|
+
.description('Package the workspace configuration as a strikethroo profile')
|
|
47
|
+
.requiredOption('--destination-directory <dir>', 'Directory to write the strikethroo profile package into (must be missing or empty)')
|
|
48
|
+
.action(async (options) => {
|
|
49
|
+
try {
|
|
50
|
+
const result = await (0, export_profile_1.exportProfile)({ destinationDirectory: options.destinationDirectory });
|
|
51
|
+
process.exit(result.success ? 0 : 1);
|
|
52
|
+
}
|
|
53
|
+
catch (error) {
|
|
54
|
+
console.error(`Unexpected error: ${error instanceof Error ? error.message : String(error)}`);
|
|
55
|
+
process.exit(1);
|
|
56
|
+
}
|
|
57
|
+
});
|
|
39
58
|
program
|
|
40
59
|
.command('serve')
|
|
41
60
|
.description('Serve the workspace as a local web app (static SPA, JSON API, SSE change stream)')
|
package/dist/cli.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":";;AACA;;;;;GAKG;;AAEH,yCAAoC;AACpC,mCAA+B;AAE/B,uCAAoE;AACpE,2CAA+D;
|
|
1
|
+
{"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Export Profile Command
|
|
3
|
+
*
|
|
4
|
+
* Packages the current workspace's configuration surface as a strikethroo
|
|
5
|
+
* profile: copies `config/` (minus the CLI-owned `schemas/` subtree) into the
|
|
6
|
+
* destination and writes a `profile.yaml` manifest collected interactively,
|
|
7
|
+
* or supplied programmatically for non-interactive use.
|
|
8
|
+
*
|
|
9
|
+
* The produced package is validated with `validateProfilePackage` before
|
|
10
|
+
* success is reported, so an export can never emit a package that would fail
|
|
11
|
+
* to round-trip through `init --profile <dir>`.
|
|
12
|
+
*/
|
|
13
|
+
import { CommandResult } from './types';
|
|
14
|
+
import { ProfileManifest } from './profiles';
|
|
15
|
+
/**
|
|
16
|
+
* Manifest fields collected from the user; `schema_version` is stamped by the
|
|
17
|
+
* export itself
|
|
18
|
+
*/
|
|
19
|
+
export type ProfileManifestAnswers = Omit<ProfileManifest, 'schema_version'>;
|
|
20
|
+
/**
|
|
21
|
+
* Options for the export profile command
|
|
22
|
+
*/
|
|
23
|
+
export interface ExportProfileOptions {
|
|
24
|
+
/**
|
|
25
|
+
* Directory to write the profile package into. Must be missing or empty.
|
|
26
|
+
*/
|
|
27
|
+
destinationDirectory: string;
|
|
28
|
+
/**
|
|
29
|
+
* Pre-answered manifest fields for non-interactive use. When absent, the
|
|
30
|
+
* command prompts interactively for every field.
|
|
31
|
+
*/
|
|
32
|
+
manifest?: ProfileManifestAnswers;
|
|
33
|
+
/**
|
|
34
|
+
* Directory to start workspace-root discovery from (default: process.cwd())
|
|
35
|
+
*/
|
|
36
|
+
cwd?: string;
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Export the current workspace's configuration as a strikethroo profile.
|
|
40
|
+
*
|
|
41
|
+
* Steps: resolve the workspace root by walking up from `cwd`, refuse a
|
|
42
|
+
* non-empty destination before any write, collect the manifest (prompting
|
|
43
|
+
* unless pre-answered), copy `config/` minus `schemas/`, write
|
|
44
|
+
* `profile.yaml`, and validate the produced package as a final self-check.
|
|
45
|
+
*
|
|
46
|
+
* @param options - Destination directory plus optional pre-answered manifest
|
|
47
|
+
* @returns Command result describing success or failure
|
|
48
|
+
*/
|
|
49
|
+
export declare function exportProfile(options: ExportProfileOptions): Promise<CommandResult>;
|
|
50
|
+
//# sourceMappingURL=export-profile.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"export-profile.d.ts","sourceRoot":"","sources":["../src/export-profile.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAOH,OAAO,EAAE,aAAa,EAAgB,MAAM,SAAS,CAAC;AACtD,OAAO,EACL,eAAe,EAIhB,MAAM,YAAY,CAAC;AAYpB;;;GAGG;AACH,MAAM,MAAM,sBAAsB,GAAG,IAAI,CAAC,eAAe,EAAE,gBAAgB,CAAC,CAAC;AAE7E;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACnC;;OAEG;IACH,oBAAoB,EAAE,MAAM,CAAC;IAC7B;;;OAGG;IACH,QAAQ,CAAC,EAAE,sBAAsB,CAAC;IAClC;;OAEG;IACH,GAAG,CAAC,EAAE,MAAM,CAAC;CACd;AAWD;;;;;;;;;;GAUG;AACH,wBAAsB,aAAa,CAAC,OAAO,EAAE,oBAAoB,GAAG,OAAO,CAAC,aAAa,CAAC,CAiEzF"}
|