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.
Files changed (93) hide show
  1. package/README.md +52 -31
  2. package/dist/__tests__/fixtures/review-gate.d.ts +59 -0
  3. package/dist/__tests__/fixtures/review-gate.d.ts.map +1 -0
  4. package/dist/__tests__/fixtures/review-gate.js +150 -0
  5. package/dist/__tests__/fixtures/review-gate.js.map +1 -0
  6. package/dist/cli.js +19 -0
  7. package/dist/cli.js.map +1 -1
  8. package/dist/export-profile.d.ts +50 -0
  9. package/dist/export-profile.d.ts.map +1 -0
  10. package/dist/export-profile.js +321 -0
  11. package/dist/export-profile.js.map +1 -0
  12. package/dist/harnesses/registry.d.ts +4 -2
  13. package/dist/harnesses/registry.d.ts.map +1 -1
  14. package/dist/harnesses/registry.js +4 -2
  15. package/dist/harnesses/registry.js.map +1 -1
  16. package/dist/index.d.ts.map +1 -1
  17. package/dist/index.js +67 -3
  18. package/dist/index.js.map +1 -1
  19. package/dist/profiles.d.ts +163 -0
  20. package/dist/profiles.d.ts.map +1 -0
  21. package/dist/profiles.js +561 -0
  22. package/dist/profiles.js.map +1 -0
  23. package/dist/types.d.ts +37 -0
  24. package/dist/types.d.ts.map +1 -1
  25. package/dist/types.js +15 -1
  26. package/dist/types.js.map +1 -1
  27. package/dist-web/assets/{arc-CsLKjSmD.js → arc-DMHUv2NY.js} +1 -1
  28. package/dist-web/assets/{architectureDiagram-3BPJPVTR-CUdI2ZME.js → architectureDiagram-3BPJPVTR-CeAAqVS4.js} +1 -1
  29. package/dist-web/assets/{blockDiagram-GPEHLZMM-BzGl3sJ5.js → blockDiagram-GPEHLZMM-Hns_u_jz.js} +1 -1
  30. package/dist-web/assets/{c4Diagram-AAUBKEIU-B9BcD268.js → c4Diagram-AAUBKEIU-BH3RLVAi.js} +1 -1
  31. package/dist-web/assets/channel-Dk0dEQIT.js +1 -0
  32. package/dist-web/assets/{chunk-2J33WTMH-jrfdvIhS.js → chunk-2J33WTMH-h6Ws9VXu.js} +1 -1
  33. package/dist-web/assets/{chunk-4BX2VUAB-BppnV9t3.js → chunk-4BX2VUAB-BSBeNNnS.js} +1 -1
  34. package/dist-web/assets/{chunk-55IACEB6-Dgig1qV7.js → chunk-55IACEB6-BmUY060b.js} +1 -1
  35. package/dist-web/assets/{chunk-727SXJPM-CssKzpPg.js → chunk-727SXJPM-CmemMVvQ.js} +1 -1
  36. package/dist-web/assets/{chunk-AQP2D5EJ-DWYbdfaL.js → chunk-AQP2D5EJ-LQpUb_FL.js} +1 -1
  37. package/dist-web/assets/{chunk-FMBD7UC4-Cbt7Dqxf.js → chunk-FMBD7UC4-wk7OYcdf.js} +1 -1
  38. package/dist-web/assets/{chunk-ND2GUHAM-2W-YdHxx.js → chunk-ND2GUHAM-O3K3rkHW.js} +1 -1
  39. package/dist-web/assets/{chunk-QZHKN3VN-BSLdTa36.js → chunk-QZHKN3VN-CvppUbp9.js} +1 -1
  40. package/dist-web/assets/classDiagram-4FO5ZUOK-gqDJqcDV.js +1 -0
  41. package/dist-web/assets/classDiagram-v2-Q7XG4LA2-gqDJqcDV.js +1 -0
  42. package/dist-web/assets/{cose-bilkent-S5V4N54A-D0_MX2M6.js → cose-bilkent-S5V4N54A-Cf1nQ4V_.js} +1 -1
  43. package/dist-web/assets/{dagre-BM42HDAG-DGXkicI6.js → dagre-BM42HDAG-YyP7mwPP.js} +1 -1
  44. package/dist-web/assets/{diagram-2AECGRRQ-DMfWZxh-.js → diagram-2AECGRRQ-BmAtTKkQ.js} +1 -1
  45. package/dist-web/assets/{diagram-5GNKFQAL-IChrzosS.js → diagram-5GNKFQAL-Bem8_DUK.js} +1 -1
  46. package/dist-web/assets/{diagram-KO2AKTUF-C7IVA_Py.js → diagram-KO2AKTUF-0gNyY9-f.js} +1 -1
  47. package/dist-web/assets/{diagram-LMA3HP47-UQXc1x2n.js → diagram-LMA3HP47-CJJh_IUU.js} +1 -1
  48. package/dist-web/assets/{diagram-OG6HWLK6-Z69O_NXy.js → diagram-OG6HWLK6-DJcCho7F.js} +1 -1
  49. package/dist-web/assets/{erDiagram-TEJ5UH35-xrgfPZU-.js → erDiagram-TEJ5UH35-D-TI_EbX.js} +1 -1
  50. package/dist-web/assets/{flowDiagram-I6XJVG4X-Co-y5e2I.js → flowDiagram-I6XJVG4X-BUrB4EYN.js} +1 -1
  51. package/dist-web/assets/{ganttDiagram-6RSMTGT7-C9TOh3M1.js → ganttDiagram-6RSMTGT7-C9_ItheP.js} +1 -1
  52. package/dist-web/assets/{gitGraphDiagram-PVQCEYII-iBpK83U-.js → gitGraphDiagram-PVQCEYII-DYQEmll0.js} +1 -1
  53. package/dist-web/assets/{index-DaaOiRou.js → index-DULKNhw0.js} +4 -4
  54. package/dist-web/assets/{index-6RY653Ds.js → index-X-a-o-AT.js} +1 -1
  55. package/dist-web/assets/{index-D4y2EDE-.js → index-mEUl0sqe.js} +1 -1
  56. package/dist-web/assets/{infoDiagram-5YYISTIA-C-_CUdyF.js → infoDiagram-5YYISTIA-B06Tp7cb.js} +1 -1
  57. package/dist-web/assets/{ishikawaDiagram-YF4QCWOH-zPkWZ6FX.js → ishikawaDiagram-YF4QCWOH-DY9iP3P6.js} +1 -1
  58. package/dist-web/assets/{journeyDiagram-JHISSGLW-CsTWcFHo.js → journeyDiagram-JHISSGLW-Bk4MV49m.js} +1 -1
  59. package/dist-web/assets/{kanban-definition-UN3LZRKU-CCsrhCu2.js → kanban-definition-UN3LZRKU-B9-wsNt9.js} +1 -1
  60. package/dist-web/assets/{linear-DlkSJnhW.js → linear-DEY9HwQB.js} +1 -1
  61. package/dist-web/assets/{mermaid.core-BM7nlTu6.js → mermaid.core-Cn0e4l6V.js} +4 -4
  62. package/dist-web/assets/{mindmap-definition-RKZ34NQL-C5tQ7zJH.js → mindmap-definition-RKZ34NQL-pN4Q2WNG.js} +1 -1
  63. package/dist-web/assets/{pieDiagram-4H26LBE5-CsK9eMOa.js → pieDiagram-4H26LBE5-DTkPv6S2.js} +1 -1
  64. package/dist-web/assets/{quadrantDiagram-W4KKPZXB-CsUwvpcD.js → quadrantDiagram-W4KKPZXB-BS9LhTv0.js} +1 -1
  65. package/dist-web/assets/{requirementDiagram-4Y6WPE33-CzQDuhAP.js → requirementDiagram-4Y6WPE33-BlSOLsQe.js} +1 -1
  66. package/dist-web/assets/{sankeyDiagram-5OEKKPKP-BTa3-BBs.js → sankeyDiagram-5OEKKPKP-B1xl-B1U.js} +1 -1
  67. package/dist-web/assets/{sequenceDiagram-3UESZ5HK-CPPduAn5.js → sequenceDiagram-3UESZ5HK-BoiYrW_0.js} +1 -1
  68. package/dist-web/assets/{stateDiagram-AJRCARHV-T5j3NpOr.js → stateDiagram-AJRCARHV-BxvfZYDK.js} +1 -1
  69. package/dist-web/assets/stateDiagram-v2-BHNVJYJU-XGZY1tGg.js +1 -0
  70. package/dist-web/assets/{timeline-definition-PNZ67QCA-BG2gG3_T.js → timeline-definition-PNZ67QCA-CUEbrRkc.js} +1 -1
  71. package/dist-web/assets/{vennDiagram-CIIHVFJN-B3LyjiD_.js → vennDiagram-CIIHVFJN-CgQiBucH.js} +1 -1
  72. package/dist-web/assets/{wardley-L42UT6IY-CTsJTFG9.js → wardley-L42UT6IY-BsGW6T55.js} +1 -1
  73. package/dist-web/assets/{wardleyDiagram-YWT4CUSO-cmPISkrt.js → wardleyDiagram-YWT4CUSO-Cq3RMp6B.js} +1 -1
  74. package/dist-web/assets/{xychartDiagram-2RQKCTM6-BWy_dUgl.js → xychartDiagram-2RQKCTM6-WaoV-V3f.js} +1 -1
  75. package/dist-web/index.html +1 -1
  76. package/package.json +3 -3
  77. package/templates/harness/skills/st-code-review/SKILL.md +309 -0
  78. package/templates/harness/skills/st-code-review/scripts/code-review.cjs +1539 -0
  79. package/templates/harness/skills/st-code-review/scripts/find-strikethroo-root.cjs +116 -0
  80. package/templates/harness/skills/st-code-review/scripts/validate-plan-blueprint.cjs +429 -0
  81. package/templates/harness/skills/st-execute-blueprint/SKILL.md +48 -1
  82. package/templates/harness/skills/st-execute-blueprint/scripts/capture-base-commit.cjs +325 -0
  83. package/templates/harness/skills/st-execute-blueprint/scripts/dispatch-task-execution.cjs +46 -26
  84. package/templates/harness/skills/st-execute-task/scripts/dispatch-task-execution.cjs +46 -26
  85. package/templates/harness/skills/st-full-workflow/SKILL.md +48 -1
  86. package/templates/harness/skills/st-full-workflow/scripts/capture-base-commit.cjs +325 -0
  87. package/templates/harness/skills/st-full-workflow/scripts/dispatch-task-execution.cjs +46 -26
  88. package/templates/strikethroo/config/hooks/CODE_REVIEW.md +60 -0
  89. package/templates/strikethroo/config/schemas/self-review-v2.xsd +437 -0
  90. package/dist-web/assets/channel-CN9J8c_F.js +0 -1
  91. package/dist-web/assets/classDiagram-4FO5ZUOK-DHR8VHf9.js +0 -1
  92. package/dist-web/assets/classDiagram-v2-Q7XG4LA2-DHR8VHf9.js +0 -1
  93. 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 that fits each codebase like a glove.</strong><br>
7
- Plain-Markdown hooks teach the agent your conventions, so every plan, task, and run inherits them. No API keys, no extra tools to run.
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 &mdash; 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> &nbsp;·&nbsp;
18
19
  <a href="https://strikethroo.canpicasoft.com/workflow.html">Workflow</a> &nbsp;·&nbsp;
19
20
  <a href="https://strikethroo.canpicasoft.com/customization.html">Customization</a> &nbsp;·&nbsp;
20
21
  <a href="https://strikethroo.canpicasoft.com/visualizations.html">Visualizations</a> &nbsp;·&nbsp;
@@ -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/sliders-horizontal.svg" width="28" height="28" alt="" />
33
+ <img src="docs/assets/icons/focus.svg" width="28" height="28" alt="" />
31
34
 
32
- ### Bends to your conventions
35
+ ### You review the plan, not the diff
33
36
 
34
- Plain-Markdown hooks fire at nine points across the workflow; inject your test commands, standards, and domain rules so every plan, task, and run inherits them. No plugins, no code.
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/focus.svg" width="28" height="28" alt="" />
42
+ <img src="docs/assets/icons/shield-check.svg" width="28" height="28" alt="" />
40
43
 
41
- ### Clean context per agent
44
+ ### Guarantees are compiled, not requested
42
45
 
43
- Every step runs with a fresh, focused context: the planner sees only your work order, the task generator only the approved plan, each execution sub-agent only its single task. No context bleed, no drift.
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/scissors.svg" width="28" height="28" alt="" />
53
+ <img src="docs/assets/icons/git-fork.svg" width="28" height="28" alt="" />
51
54
 
52
- ### No API keys
55
+ ### Nobody marks their own homework
53
56
 
54
- Runs inside the assistant you already use -- Claude Code, Codex, Cursor, OpenCode, or Copilot -- on the subscription you already pay for. Nothing to provision, host, or rotate.
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/puzzle.svg" width="28" height="28" alt="" />
62
+ <img src="docs/assets/icons/sliders-horizontal.svg" width="28" height="28" alt="" />
60
63
 
61
- ### Harness-agnostic skills
64
+ ### Bends to your conventions
62
65
 
63
- The workflow ships as Agent Skills: one `SKILL.md` works on any harness supporting the format. Install once; the right skill auto-loads when you describe what you need.
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 nine 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.
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| D[Tasks]
110
- D --> E{Verify}
111
- E --> G[Execute]
112
- G --> H{Review}
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
- Three steps, each delivered as an Agent Skill that loads when you describe what you need:
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
- | Step | Skill | Output |
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
- Human review gates between steps catch scope creep before any code is written. Each step runs with clean context -- the planning agent sees only the work order, the task agent sees only the approved plan, and each execution sub-agent receives only its specific task.
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
  | [![img](docs/assets/plans-board.png)](docs/assets/plans-board.png) | [![img](docs/assets/plan-detail-graph.png)](docs/assets/plan-detail-graph.png) | [![img](docs/assets/archive-all.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 project context
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;AAE/D,MAAM,OAAO,GAAG,IAAI,mBAAO,EAAE,CAAC;AAE9B,OAAO,CAAC,IAAI,CAAC,aAAa,CAAC,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC,WAAW,CAAC,qCAAqC,CAAC,CAAC;AAEhG,OAAO;KACJ,OAAO,CAAC,MAAM,CAAC;KACf,WAAW,CAAC,sCAAsC,CAAC;KACnD,cAAc,CACb,qBAAqB,EACrB,8FAA8F,CAC/F;KACA,MAAM,CACL,gCAAgC,EAChC,uEAAuE,CACxE;KACA,MAAM,CAAC,SAAS,EAAE,6CAA6C,CAAC;KAChE,MAAM,CAAC,KAAK,EAAE,OAAoB,EAAE,EAAE;IACrC,IAAI,CAAC;QACH,2BAA2B;QAC3B,MAAM,MAAM,GAAG,MAAM,IAAA,YAAI,EAAC,OAAO,CAAC,CAAC;QAEnC,6CAA6C;QAC7C,IAAI,MAAM,CAAC,OAAO,EAAE,CAAC;YACnB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;aAAM,CAAC;YACN,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;IACH,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,qBAAqB,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC;QAC7F,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;AACH,CAAC,CAAC,CAAC;AAEL,OAAO;KACJ,OAAO,CAAC,OAAO,CAAC;KAChB,WAAW,CAAC,kFAAkF,CAAC;KAC/F,MAAM,CAAC,YAAY,EAAE,cAAc,EAAE,MAAM,CAAC;KAC5C,MAAM,CAAC,WAAW,EAAE,kCAAkC,CAAC;KACvD,MAAM,CAAC,oBAAoB,EAAE,mCAAmC,CAAC;KACjE,MAAM,CAAC,KAAK,EAAE,IAAyD,EAAE,EAAE;IAC1E,IAAI,CAAC;QACH,MAAM,QAAQ,GAAG,IAAA,2BAAoB,EAAC,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS,EAAE,CAAC,CAAC;QACrE,IAAI,IAAA,qBAAc,EAAC,QAAQ,CAAC,EAAE,CAAC;YAC7B,OAAO,CAAC,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC;YAC9B,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;QAED,MAAM,MAAM,GAAG,MAAM,IAAA,oBAAW,EAAC;YAC/B,IAAI,EAAE,QAAQ,CAAC,IAAI;YACnB,IAAI,EAAE,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC;YACvB,IAAI,EAAE,IAAI,CAAC,IAAI;YACf,SAAS,EAAE,IAAA,yBAAgB,GAAE;SAC9B,CAAC,CAAC;QACH,OAAO,CAAC,GAAG,CAAC,WAAW,MAAM,CAAC,GAAG,EAAE,CAAC,CAAC;IACvC,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CACX,0BAA0B,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CACnF,CAAC;QACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;AACH,CAAC,CAAC,CAAC;AAEL,sCAAsC;AACtC,OAAO,CAAC,EAAE,CAAC,WAAW,EAAE,KAAK,EAAC,QAAQ,EAAC,EAAE;IACvC,OAAO,CAAC,KAAK,CAAC,oBAAoB,QAAQ,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IACjD,OAAO,CAAC,GAAG,CAAC,sCAAsC,CAAC,CAAC;IACpD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC,CAAC,CAAC;AAEH,+BAA+B;AAC/B,OAAO,CAAC,KAAK,EAAE,CAAC;AAEhB,sCAAsC;AACtC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC;IAClC,OAAO,CAAC,UAAU,EAAE,CAAC;IACrB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC"}
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"}