dsh-pstack 0.1.0 → 0.2.0-beta.3

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 (406) hide show
  1. package/LICENSE +2 -3
  2. package/README.md +174 -148
  3. package/README.zh.md +185 -0
  4. package/assets/logo.png +0 -0
  5. package/cordis.patch.yml +103 -14
  6. package/dist/host-contract-CUPSpeNk.d.mts +22 -0
  7. package/dist/index.d.mts +87 -14
  8. package/dist/index.mjs +370 -143
  9. package/dist/models.d.mts +44 -0
  10. package/dist/models.mjs +201 -0
  11. package/dist/paths-BT77khwm.mjs +48 -0
  12. package/dist/{LICENSE → pstack/LICENSE} +1 -2
  13. package/dist/pstack/README.md +291 -0
  14. package/{assets → dist/pstack}/agents/comment-sicko.md +1 -1
  15. package/dist/pstack/agents/poteto-agent.md +9 -0
  16. package/{assets → dist/pstack}/docs/guide/01-setup.md +11 -9
  17. package/dist/{assets → pstack}/docs/guide/02-poteto-mode.md +2 -2
  18. package/{assets → dist/pstack}/docs/guide/04-design.md +4 -4
  19. package/dist/{assets → pstack}/docs/guide/05-build-and-clean.md +3 -3
  20. package/dist/{assets → pstack}/docs/guide/06-verify-and-ship.md +11 -1
  21. package/{assets → dist/pstack}/docs/guide/07-overnight.md +10 -10
  22. package/dist/{assets → pstack}/docs/guide/09-make-it-yours.md +4 -4
  23. package/{assets → dist/pstack}/docs/guide/10-recipes-and-pitfalls.md +6 -4
  24. package/dist/pstack/docs/guide/images/design.jpg +0 -0
  25. package/dist/pstack/docs/guide/images/overnight.jpg +0 -0
  26. package/dist/pstack/docs/guide/images/recipes.jpg +0 -0
  27. package/dist/pstack/docs/guide/images/router.jpg +0 -0
  28. package/dist/pstack/docs/guide/images/understanding.jpg +0 -0
  29. package/dist/pstack/docs/guide/images/verification.jpg +0 -0
  30. package/dist/pstack/docs/harness/dsh.md +98 -0
  31. package/{assets → dist/pstack}/skills/architect/SKILL.md +5 -5
  32. package/dist/pstack/skills/arena/SKILL.md +50 -0
  33. package/{assets → dist/pstack}/skills/automate-me/SKILL.md +14 -13
  34. package/dist/{assets → pstack}/skills/benchmark-checklist/SKILL.md +1 -3
  35. package/dist/{assets → pstack}/skills/blast-radius/SKILL.md +1 -3
  36. package/{assets → dist/pstack}/skills/bro/SKILL.md +0 -2
  37. package/dist/{assets → pstack}/skills/correct/SKILL.md +1 -3
  38. package/{assets → dist/pstack}/skills/create-formal-verification-skill/SKILL.md +5 -3
  39. package/{assets → dist/pstack}/skills/create-verification-skill/SKILL.md +6 -6
  40. package/{assets → dist/pstack}/skills/figure-it-out/SKILL.md +4 -4
  41. package/dist/{assets → pstack}/skills/how/SKILL.md +4 -4
  42. package/{assets → dist/pstack}/skills/how/references/explainer-prompt.md +1 -1
  43. package/dist/pstack/skills/in-your-own-words/SKILL.md +7 -0
  44. package/dist/pstack/skills/interrogate/SKILL.md +33 -0
  45. package/{assets → dist/pstack}/skills/ketchup/SKILL.md +1 -3
  46. package/dist/pstack/skills/ketchup-video/SKILL.md +29 -0
  47. package/{assets → dist/pstack}/skills/maintain-formal-verification-skill/SKILL.md +2 -2
  48. package/dist/{assets → pstack}/skills/maintain-verification-skill/SKILL.md +3 -3
  49. package/dist/pstack/skills/make-bot-ui/SKILL.md +117 -0
  50. package/{assets → dist/pstack}/skills/no-comments/SKILL.md +4 -4
  51. package/{assets → dist/pstack}/skills/poteto-help/SKILL.md +21 -17
  52. package/dist/{assets → pstack}/skills/poteto-help/references/prompting.md +1 -1
  53. package/dist/{assets → pstack}/skills/poteto-help/references/recipes.md +3 -3
  54. package/{assets → dist/pstack}/skills/poteto-mode/SKILL.md +20 -21
  55. package/dist/{assets → pstack}/skills/poteto-mode/playbooks/authoring-a-skill.md +1 -1
  56. package/dist/{assets → pstack}/skills/poteto-mode/playbooks/autonomous-run.md +2 -2
  57. package/{assets → dist/pstack}/skills/poteto-mode/playbooks/autopilot-full.md +7 -7
  58. package/dist/pstack/skills/poteto-mode/playbooks/autopilot-stack.md +8 -0
  59. package/{assets → dist/pstack}/skills/poteto-mode/playbooks/babysit.md +3 -3
  60. package/{assets → dist/pstack}/skills/poteto-mode/playbooks/bug-fix.md +3 -3
  61. package/dist/{assets → pstack}/skills/poteto-mode/playbooks/eval.md +1 -1
  62. package/{assets → dist/pstack}/skills/poteto-mode/playbooks/feature.md +1 -1
  63. package/{assets → dist/pstack}/skills/poteto-mode/playbooks/hillclimb.md +1 -1
  64. package/{assets → dist/pstack}/skills/poteto-mode/playbooks/multi-phase-plan.md +13 -13
  65. package/dist/{assets → pstack}/skills/poteto-mode/playbooks/opening-a-pr.md +3 -3
  66. package/dist/pstack/skills/poteto-mode/playbooks/orchestrate.md +25 -0
  67. package/dist/{assets → pstack}/skills/poteto-mode/playbooks/perf-issue.md +2 -2
  68. package/{assets → dist/pstack}/skills/poteto-mode/playbooks/prototype.md +1 -1
  69. package/dist/{assets → pstack}/skills/poteto-mode/playbooks/refactoring.md +2 -2
  70. package/{assets → dist/pstack}/skills/poteto-mode/playbooks/runtime-forensics.md +1 -1
  71. package/{assets → dist/pstack}/skills/poteto-mode/playbooks/session-pickup.md +1 -1
  72. package/dist/{assets → pstack}/skills/poteto-mode/playbooks/shipping.md +2 -2
  73. package/{assets → dist/pstack}/skills/poteto-mode/playbooks/visual-parity.md +1 -1
  74. package/dist/{assets → pstack}/skills/poteto-mode/playbooks/worktree-cleanup.md +2 -2
  75. package/{assets → dist/pstack}/skills/poteto-mode/scripts/check-plan.mjs +83 -70
  76. package/dist/{assets/skills/poteto-mode/scripts/check-plan.test.ts → pstack/skills/poteto-mode/scripts/check-plan.test.mjs} +53 -21
  77. package/dist/pstack/skills/poteto-mode/scripts/expect.mjs +254 -0
  78. package/dist/pstack/skills/poteto-mode/scripts/support.mjs +93 -0
  79. package/dist/pstack/skills/poteto-mode/scripts/watch-pr/cli.mjs +123 -0
  80. package/dist/pstack/skills/poteto-mode/scripts/watch-pr/cli.test.mjs +217 -0
  81. package/dist/pstack/skills/poteto-mode/scripts/watch-pr/fakes.test-helper.mjs +119 -0
  82. package/dist/pstack/skills/poteto-mode/scripts/watch-pr/github.mjs +626 -0
  83. package/dist/pstack/skills/poteto-mode/scripts/watch-pr/github.test.mjs +521 -0
  84. package/dist/pstack/skills/poteto-mode/scripts/watch-pr/policy.mjs +657 -0
  85. package/dist/pstack/skills/poteto-mode/scripts/watch-pr/policy.test.mjs +523 -0
  86. package/dist/pstack/skills/poteto-mode/scripts/watch-pr/render.mjs +106 -0
  87. package/dist/pstack/skills/poteto-mode/scripts/watch-pr/types.mjs +9 -0
  88. package/dist/pstack/skills/poteto-mode/scripts/watch-pr/watch-pr.mjs +5 -0
  89. package/dist/pstack/skills/poteto-mode/scripts/worktree-audit.mjs +668 -0
  90. package/dist/pstack/skills/poteto-mode/scripts/worktree-audit.test.mjs +134 -0
  91. package/{assets → dist/pstack}/skills/principle-attack-the-premise/SKILL.md +1 -3
  92. package/{assets → dist/pstack}/skills/principle-boundary-discipline/SKILL.md +1 -3
  93. package/{assets → dist/pstack}/skills/principle-build-the-lever/SKILL.md +0 -3
  94. package/dist/pstack/skills/principle-encode-lessons-in-structure/SKILL.md +11 -0
  95. package/dist/pstack/skills/principle-exhaust-the-design-space/SKILL.md +9 -0
  96. package/{assets → dist/pstack}/skills/principle-experience-first/SKILL.md +1 -3
  97. package/dist/{assets → pstack}/skills/principle-explain-the-number/SKILL.md +3 -4
  98. package/dist/{assets → pstack}/skills/principle-fix-root-causes/SKILL.md +1 -3
  99. package/{assets → dist/pstack}/skills/principle-foundational-thinking/SKILL.md +0 -2
  100. package/dist/{assets → pstack}/skills/principle-guard-the-context-window/SKILL.md +0 -2
  101. package/dist/{assets → pstack}/skills/principle-laziness-protocol/SKILL.md +1 -3
  102. package/dist/{assets → pstack}/skills/principle-make-operations-idempotent/SKILL.md +1 -3
  103. package/dist/{assets → pstack}/skills/principle-migrate-callers-then-delete-legacy-apis/SKILL.md +1 -3
  104. package/{assets → dist/pstack}/skills/principle-minimize-reader-load/SKILL.md +1 -3
  105. package/{assets → dist/pstack}/skills/principle-model-the-domain/SKILL.md +1 -3
  106. package/{assets → dist/pstack}/skills/principle-never-block-on-the-human/SKILL.md +1 -3
  107. package/dist/{assets → pstack}/skills/principle-outcome-oriented-execution/SKILL.md +1 -3
  108. package/{assets → dist/pstack}/skills/principle-prove-it-works/SKILL.md +3 -3
  109. package/dist/{assets → pstack}/skills/principle-redesign-from-first-principles/SKILL.md +1 -3
  110. package/{assets → dist/pstack}/skills/principle-separate-before-serializing-shared-state/SKILL.md +1 -3
  111. package/dist/{assets → pstack}/skills/principle-sequence-verifiable-units/SKILL.md +1 -3
  112. package/dist/{assets → pstack}/skills/principle-subtract-before-you-add/SKILL.md +1 -3
  113. package/{assets → dist/pstack}/skills/principle-test-behavior-not-implementation/SKILL.md +1 -3
  114. package/{assets → dist/pstack}/skills/principle-type-system-discipline/SKILL.md +1 -3
  115. package/dist/{assets → pstack}/skills/recall/SKILL.md +4 -4
  116. package/dist/pstack/skills/reflect/SKILL.md +71 -0
  117. package/{assets → dist/pstack}/skills/reflect/references/divergent-reviewer.md +1 -1
  118. package/{assets → dist/pstack}/skills/reflect/references/judgment-reviewer.md +1 -1
  119. package/{assets → dist/pstack}/skills/reflect/references/synthesizer.md +3 -3
  120. package/dist/{assets → pstack}/skills/reflect/references/tooling-reviewer.md +1 -1
  121. package/dist/pstack/skills/setup-pstack/SKILL.md +80 -0
  122. package/{assets → dist/pstack}/skills/sharpen/SKILL.md +1 -3
  123. package/{assets → dist/pstack}/skills/show-me-your-work/SKILL.md +3 -3
  124. package/dist/pstack/skills/show-me-your-work/scripts/log.mjs +106 -0
  125. package/dist/pstack/skills/show-me-your-work/scripts/log.test.mjs +56 -0
  126. package/dist/pstack/skills/statechart/SKILL.md +82 -0
  127. package/dist/pstack/skills/statechart/references/render.md +93 -0
  128. package/dist/pstack/skills/statechart/scripts/backends/cfg.mjs +31 -0
  129. package/dist/pstack/skills/statechart/scripts/backends/mermaid.mjs +186 -0
  130. package/dist/pstack/skills/statechart/scripts/backends/plain-text.mjs +62 -0
  131. package/dist/pstack/skills/statechart/scripts/backends/report.mjs +84 -0
  132. package/dist/pstack/skills/statechart/scripts/frontends/config.mjs +268 -0
  133. package/dist/pstack/skills/statechart/scripts/frontends/dot.mjs +67 -0
  134. package/dist/pstack/skills/statechart/scripts/frontends/marks.mjs +94 -0
  135. package/dist/pstack/skills/statechart/scripts/frontends/messages.mjs +48 -0
  136. package/dist/pstack/skills/statechart/scripts/frontends/spec.mjs +101 -0
  137. package/dist/pstack/skills/statechart/scripts/frontends/trace.mjs +39 -0
  138. package/dist/pstack/skills/statechart/scripts/frontends/value.mjs +180 -0
  139. package/dist/pstack/skills/statechart/scripts/frontends/verdict.mjs +40 -0
  140. package/dist/pstack/skills/statechart/scripts/frontends/view.mjs +99 -0
  141. package/dist/pstack/skills/statechart/scripts/ir.mjs +277 -0
  142. package/dist/pstack/skills/statechart/scripts/passes/annotate.mjs +92 -0
  143. package/dist/pstack/skills/statechart/scripts/passes/label.mjs +210 -0
  144. package/dist/pstack/skills/statechart/scripts/passes/lift.mjs +84 -0
  145. package/dist/pstack/skills/statechart/scripts/passes/loop-check.mjs +47 -0
  146. package/dist/pstack/skills/statechart/scripts/passes/paths.mjs +72 -0
  147. package/dist/pstack/skills/statechart/scripts/passes/reach.mjs +135 -0
  148. package/dist/pstack/skills/statechart/scripts/passes/region-check.mjs +82 -0
  149. package/dist/pstack/skills/statechart/scripts/passes/regions.mjs +268 -0
  150. package/dist/pstack/skills/statechart/scripts/pipeline.mjs +72 -0
  151. package/dist/pstack/skills/statechart/scripts/run.mjs +440 -0
  152. package/dist/pstack/skills/statechart/scripts/statechart.mjs +155 -0
  153. package/dist/pstack/skills/statechart/scripts/statechart.test.mjs +198 -0
  154. package/dist/pstack/skills/statechart/scripts/worker.mjs +31 -0
  155. package/dist/pstack/skills/swarm/SKILL.md +43 -0
  156. package/{assets → dist/pstack}/skills/tdd/SKILL.md +1 -3
  157. package/{assets → dist/pstack}/skills/teach/SKILL.md +3 -3
  158. package/{assets → dist/pstack}/skills/technical-writing/SKILL.md +2 -2
  159. package/{assets → dist/pstack}/skills/typescript-best-practices/SKILL.md +1 -2
  160. package/{assets → dist/pstack}/skills/unslop/SKILL.md +0 -2
  161. package/dist/{assets → pstack}/skills/why/SKILL.md +9 -9
  162. package/dist/script.d.mts +91 -0
  163. package/dist/script.mjs +485 -0
  164. package/dist/skill.d.mts +38 -0
  165. package/dist/skill.mjs +183 -0
  166. package/dist/skills/authored/decision-audit/SKILL.md +99 -0
  167. package/dist/skills/authored/decision-audit/SKILL.zh.md +99 -0
  168. package/dist/skills/authored/decision-audit/references/recover-commit.md +17 -0
  169. package/dist/skills/authored/decision-audit/references/recover-commit.zh.md +17 -0
  170. package/dist/skills/authored/decision-write/SKILL.md +131 -0
  171. package/dist/skills/authored/decision-write/SKILL.zh.md +131 -0
  172. package/dist/skills/authored/decision-write/references/land.md +48 -0
  173. package/dist/skills/authored/decision-write/references/land.zh.md +48 -0
  174. package/dist/skills/authored/setup-project-docs/SKILL.md +58 -0
  175. package/dist/skills/authored/setup-project-docs/SKILL.zh.md +58 -0
  176. package/dist/skills/authored/setup-project-docs/references/decision-conventions.md +11 -0
  177. package/dist/skills/authored/setup-project-docs/references/decision-conventions.zh.md +11 -0
  178. package/dist/skills/vendored/retro/SKILL.md +44 -0
  179. package/dist/skills/vendored/retro/agents/openai.yaml +5 -0
  180. package/dist/skills/vendored/writing-for-agents/SKILL-MECHANICS.md +22 -0
  181. package/dist/skills/vendored/writing-for-agents/SKILL.md +81 -0
  182. package/dist/skills/vendored/writing-for-agents/agents/openai.yaml +3 -0
  183. package/dist/subagent.d.mts +175 -106
  184. package/dist/subagent.mjs +1012 -344
  185. package/locale/en.json +7 -0
  186. package/locale/zh.json +7 -0
  187. package/package.json +61 -50
  188. package/assets/agents/poteto-agent.md +0 -8
  189. package/assets/docs/guide/02-poteto-mode.md +0 -139
  190. package/assets/docs/guide/05-build-and-clean.md +0 -83
  191. package/assets/docs/guide/06-verify-and-ship.md +0 -152
  192. package/assets/docs/guide/09-make-it-yours.md +0 -100
  193. package/assets/docs/harness/dsh.md +0 -65
  194. package/assets/docs/pstack-models.example.md +0 -23
  195. package/assets/skills/arena/SKILL.md +0 -50
  196. package/assets/skills/benchmark-checklist/SKILL.md +0 -41
  197. package/assets/skills/blast-radius/SKILL.md +0 -52
  198. package/assets/skills/correct/SKILL.md +0 -34
  199. package/assets/skills/how/SKILL.md +0 -38
  200. package/assets/skills/in-your-own-words/SKILL.md +0 -9
  201. package/assets/skills/interrogate/SKILL.md +0 -69
  202. package/assets/skills/interrogate/references/code-quality-review.md +0 -47
  203. package/assets/skills/interrogate/references/lead-judgment.md +0 -39
  204. package/assets/skills/interrogate/references/reviewer-prompt.md +0 -62
  205. package/assets/skills/interrogate/references/rubric.md +0 -77
  206. package/assets/skills/maintain-verification-skill/SKILL.md +0 -41
  207. package/assets/skills/poteto-help/references/prompting.md +0 -51
  208. package/assets/skills/poteto-help/references/recipes.md +0 -51
  209. package/assets/skills/poteto-mode/playbooks/authoring-a-skill.md +0 -12
  210. package/assets/skills/poteto-mode/playbooks/autonomous-run.md +0 -13
  211. package/assets/skills/poteto-mode/playbooks/autopilot-stack.md +0 -12
  212. package/assets/skills/poteto-mode/playbooks/eval.md +0 -25
  213. package/assets/skills/poteto-mode/playbooks/opening-a-pr.md +0 -34
  214. package/assets/skills/poteto-mode/playbooks/orchestrate.md +0 -112
  215. package/assets/skills/poteto-mode/playbooks/perf-issue.md +0 -25
  216. package/assets/skills/poteto-mode/playbooks/refactoring.md +0 -16
  217. package/assets/skills/poteto-mode/playbooks/shipping.md +0 -12
  218. package/assets/skills/poteto-mode/playbooks/worktree-cleanup.md +0 -12
  219. package/assets/skills/poteto-mode/scripts/bootstrap.ts +0 -62
  220. package/assets/skills/poteto-mode/scripts/bun.lock +0 -67
  221. package/assets/skills/poteto-mode/scripts/check-plan.test.ts +0 -96
  222. package/assets/skills/poteto-mode/scripts/orch/orch.test.ts +0 -761
  223. package/assets/skills/poteto-mode/scripts/orch/orch.ts +0 -590
  224. package/assets/skills/poteto-mode/scripts/orch/store.ts +0 -1677
  225. package/assets/skills/poteto-mode/scripts/package.json +0 -16
  226. package/assets/skills/poteto-mode/scripts/watch-pr/cli.test.ts +0 -224
  227. package/assets/skills/poteto-mode/scripts/watch-pr/cli.ts +0 -223
  228. package/assets/skills/poteto-mode/scripts/watch-pr/fakes.test-helper.ts +0 -129
  229. package/assets/skills/poteto-mode/scripts/watch-pr/github.test.ts +0 -436
  230. package/assets/skills/poteto-mode/scripts/watch-pr/github.ts +0 -718
  231. package/assets/skills/poteto-mode/scripts/watch-pr/policy.test.ts +0 -420
  232. package/assets/skills/poteto-mode/scripts/watch-pr/policy.ts +0 -836
  233. package/assets/skills/poteto-mode/scripts/watch-pr/render.ts +0 -169
  234. package/assets/skills/poteto-mode/scripts/watch-pr/tsconfig.json +0 -13
  235. package/assets/skills/poteto-mode/scripts/watch-pr/types.compile.ts +0 -93
  236. package/assets/skills/poteto-mode/scripts/watch-pr/types.ts +0 -413
  237. package/assets/skills/poteto-mode/scripts/watch-pr/watch-pr +0 -6
  238. package/assets/skills/poteto-mode/scripts/worktree-audit.sh +0 -127
  239. package/assets/skills/principle-encode-lessons-in-structure/SKILL.md +0 -13
  240. package/assets/skills/principle-exhaust-the-design-space/SKILL.md +0 -11
  241. package/assets/skills/principle-explain-the-number/SKILL.md +0 -19
  242. package/assets/skills/principle-fix-root-causes/SKILL.md +0 -23
  243. package/assets/skills/principle-guard-the-context-window/SKILL.md +0 -14
  244. package/assets/skills/principle-laziness-protocol/SKILL.md +0 -12
  245. package/assets/skills/principle-make-operations-idempotent/SKILL.md +0 -24
  246. package/assets/skills/principle-migrate-callers-then-delete-legacy-apis/SKILL.md +0 -16
  247. package/assets/skills/principle-outcome-oriented-execution/SKILL.md +0 -23
  248. package/assets/skills/principle-redesign-from-first-principles/SKILL.md +0 -18
  249. package/assets/skills/principle-sequence-verifiable-units/SKILL.md +0 -19
  250. package/assets/skills/principle-subtract-before-you-add/SKILL.md +0 -20
  251. package/assets/skills/recall/SKILL.md +0 -37
  252. package/assets/skills/reflect/SKILL.md +0 -70
  253. package/assets/skills/reflect/references/tooling-reviewer.md +0 -48
  254. package/assets/skills/setup-pstack/SKILL.md +0 -76
  255. package/assets/skills/show-me-your-work/scripts/log.sh +0 -42
  256. package/assets/skills/swarm/SKILL.md +0 -41
  257. package/assets/skills/why/SKILL.md +0 -100
  258. package/dist/README.md +0 -159
  259. package/dist/assets/agents/comment-sicko.md +0 -32
  260. package/dist/assets/agents/poteto-agent.md +0 -8
  261. package/dist/assets/docs/guide/01-setup.md +0 -64
  262. package/dist/assets/docs/guide/03-understand.md +0 -79
  263. package/dist/assets/docs/guide/04-design.md +0 -133
  264. package/dist/assets/docs/guide/07-overnight.md +0 -122
  265. package/dist/assets/docs/guide/08-principles.md +0 -72
  266. package/dist/assets/docs/guide/10-recipes-and-pitfalls.md +0 -180
  267. package/dist/assets/docs/guide/README.md +0 -38
  268. package/dist/assets/docs/harness/dsh.md +0 -65
  269. package/dist/assets/docs/pstack-models.example.md +0 -23
  270. package/dist/assets/skills/architect/SKILL.md +0 -81
  271. package/dist/assets/skills/architect/references/design-red-flags.md +0 -57
  272. package/dist/assets/skills/architect/references/rationale-template.md +0 -35
  273. package/dist/assets/skills/architect/references/runner-prompt.md +0 -20
  274. package/dist/assets/skills/arena/SKILL.md +0 -50
  275. package/dist/assets/skills/automate-me/SKILL.md +0 -105
  276. package/dist/assets/skills/bro/SKILL.md +0 -9
  277. package/dist/assets/skills/create-formal-verification-skill/SKILL.md +0 -43
  278. package/dist/assets/skills/create-verification-skill/SKILL.md +0 -46
  279. package/dist/assets/skills/create-verification-skill/references/feature-map-example/README.md +0 -47
  280. package/dist/assets/skills/create-verification-skill/references/feature-map-example/create-note.md +0 -39
  281. package/dist/assets/skills/create-verification-skill/references/feature-map-example/search.md +0 -45
  282. package/dist/assets/skills/figure-it-out/SKILL.md +0 -54
  283. package/dist/assets/skills/how/references/explainer-prompt.md +0 -55
  284. package/dist/assets/skills/how/references/explorer-prompt.md +0 -35
  285. package/dist/assets/skills/in-your-own-words/SKILL.md +0 -9
  286. package/dist/assets/skills/interrogate/SKILL.md +0 -69
  287. package/dist/assets/skills/interrogate/references/code-quality-review.md +0 -47
  288. package/dist/assets/skills/interrogate/references/lead-judgment.md +0 -39
  289. package/dist/assets/skills/interrogate/references/reviewer-prompt.md +0 -62
  290. package/dist/assets/skills/interrogate/references/rubric.md +0 -77
  291. package/dist/assets/skills/ketchup/SKILL.md +0 -45
  292. package/dist/assets/skills/maintain-formal-verification-skill/SKILL.md +0 -60
  293. package/dist/assets/skills/no-comments/SKILL.md +0 -26
  294. package/dist/assets/skills/poteto-help/SKILL.md +0 -161
  295. package/dist/assets/skills/poteto-mode/SKILL.md +0 -153
  296. package/dist/assets/skills/poteto-mode/playbooks/autopilot-full.md +0 -25
  297. package/dist/assets/skills/poteto-mode/playbooks/autopilot-stack.md +0 -12
  298. package/dist/assets/skills/poteto-mode/playbooks/babysit.md +0 -23
  299. package/dist/assets/skills/poteto-mode/playbooks/bug-fix.md +0 -15
  300. package/dist/assets/skills/poteto-mode/playbooks/feature.md +0 -21
  301. package/dist/assets/skills/poteto-mode/playbooks/hillclimb.md +0 -21
  302. package/dist/assets/skills/poteto-mode/playbooks/investigation.md +0 -14
  303. package/dist/assets/skills/poteto-mode/playbooks/multi-phase-plan.md +0 -155
  304. package/dist/assets/skills/poteto-mode/playbooks/orchestrate.md +0 -112
  305. package/dist/assets/skills/poteto-mode/playbooks/pause-safely.md +0 -10
  306. package/dist/assets/skills/poteto-mode/playbooks/prototype.md +0 -14
  307. package/dist/assets/skills/poteto-mode/playbooks/runtime-forensics.md +0 -11
  308. package/dist/assets/skills/poteto-mode/playbooks/session-pickup.md +0 -11
  309. package/dist/assets/skills/poteto-mode/playbooks/trace-forensics.md +0 -14
  310. package/dist/assets/skills/poteto-mode/playbooks/visual-parity.md +0 -11
  311. package/dist/assets/skills/poteto-mode/references/bugbot-triage.md +0 -142
  312. package/dist/assets/skills/poteto-mode/scripts/bootstrap.ts +0 -62
  313. package/dist/assets/skills/poteto-mode/scripts/bun.lock +0 -67
  314. package/dist/assets/skills/poteto-mode/scripts/check-plan.mjs +0 -205
  315. package/dist/assets/skills/poteto-mode/scripts/orch/orch.test.ts +0 -761
  316. package/dist/assets/skills/poteto-mode/scripts/orch/orch.ts +0 -590
  317. package/dist/assets/skills/poteto-mode/scripts/orch/store.ts +0 -1677
  318. package/dist/assets/skills/poteto-mode/scripts/package.json +0 -16
  319. package/dist/assets/skills/poteto-mode/scripts/watch-pr/cli.test.ts +0 -224
  320. package/dist/assets/skills/poteto-mode/scripts/watch-pr/cli.ts +0 -223
  321. package/dist/assets/skills/poteto-mode/scripts/watch-pr/fakes.test-helper.ts +0 -129
  322. package/dist/assets/skills/poteto-mode/scripts/watch-pr/github.test.ts +0 -436
  323. package/dist/assets/skills/poteto-mode/scripts/watch-pr/github.ts +0 -718
  324. package/dist/assets/skills/poteto-mode/scripts/watch-pr/policy.test.ts +0 -420
  325. package/dist/assets/skills/poteto-mode/scripts/watch-pr/policy.ts +0 -836
  326. package/dist/assets/skills/poteto-mode/scripts/watch-pr/render.ts +0 -169
  327. package/dist/assets/skills/poteto-mode/scripts/watch-pr/tsconfig.json +0 -13
  328. package/dist/assets/skills/poteto-mode/scripts/watch-pr/types.compile.ts +0 -93
  329. package/dist/assets/skills/poteto-mode/scripts/watch-pr/types.ts +0 -413
  330. package/dist/assets/skills/poteto-mode/scripts/watch-pr/watch-pr +0 -6
  331. package/dist/assets/skills/poteto-mode/scripts/worktree-audit.sh +0 -127
  332. package/dist/assets/skills/principle-attack-the-premise/SKILL.md +0 -23
  333. package/dist/assets/skills/principle-boundary-discipline/SKILL.md +0 -36
  334. package/dist/assets/skills/principle-build-the-lever/SKILL.md +0 -26
  335. package/dist/assets/skills/principle-encode-lessons-in-structure/SKILL.md +0 -13
  336. package/dist/assets/skills/principle-exhaust-the-design-space/SKILL.md +0 -11
  337. package/dist/assets/skills/principle-experience-first/SKILL.md +0 -21
  338. package/dist/assets/skills/principle-foundational-thinking/SKILL.md +0 -23
  339. package/dist/assets/skills/principle-minimize-reader-load/SKILL.md +0 -20
  340. package/dist/assets/skills/principle-model-the-domain/SKILL.md +0 -26
  341. package/dist/assets/skills/principle-never-block-on-the-human/SKILL.md +0 -17
  342. package/dist/assets/skills/principle-prove-it-works/SKILL.md +0 -24
  343. package/dist/assets/skills/principle-separate-before-serializing-shared-state/SKILL.md +0 -18
  344. package/dist/assets/skills/principle-test-behavior-not-implementation/SKILL.md +0 -22
  345. package/dist/assets/skills/principle-type-system-discipline/SKILL.md +0 -15
  346. package/dist/assets/skills/reflect/SKILL.md +0 -70
  347. package/dist/assets/skills/reflect/references/divergent-reviewer.md +0 -38
  348. package/dist/assets/skills/reflect/references/judgment-reviewer.md +0 -37
  349. package/dist/assets/skills/reflect/references/synthesizer.md +0 -56
  350. package/dist/assets/skills/setup-pstack/SKILL.md +0 -76
  351. package/dist/assets/skills/sharpen/SKILL.md +0 -18
  352. package/dist/assets/skills/show-me-your-work/SKILL.md +0 -84
  353. package/dist/assets/skills/show-me-your-work/references/decision-log-template.tsv +0 -1
  354. package/dist/assets/skills/show-me-your-work/scripts/log.sh +0 -42
  355. package/dist/assets/skills/swarm/SKILL.md +0 -41
  356. package/dist/assets/skills/tdd/SKILL.md +0 -44
  357. package/dist/assets/skills/teach/SKILL.md +0 -23
  358. package/dist/assets/skills/technical-writing/SKILL.md +0 -108
  359. package/dist/assets/skills/typescript-best-practices/SKILL.md +0 -32
  360. package/dist/assets/skills/typescript-best-practices/references/patterns.md +0 -328
  361. package/dist/assets/skills/unslop/SKILL.md +0 -64
  362. package/dist/assets/skills/why/references/epistemics.md +0 -71
  363. package/dist/assets/skills/why/references/investigator-prompt.md +0 -84
  364. package/dist/assets/skills/why/references/source-playbook.md +0 -17
  365. package/dist/assets/skills/why/references/sources/code-archaeology.md +0 -51
  366. package/dist/assets/skills/why/references/sources/databricks.md +0 -70
  367. package/dist/assets/skills/why/references/sources/datadog.md +0 -97
  368. package/dist/assets/skills/why/references/sources/incident-postmortem.md +0 -5
  369. package/dist/assets/skills/why/references/sources/linear.md +0 -48
  370. package/dist/assets/skills/why/references/sources/notion.md +0 -55
  371. package/dist/assets/skills/why/references/sources/sentry.md +0 -66
  372. package/dist/assets/skills/why/references/sources/slack.md +0 -17
  373. package/dist/assets/skills/why/references/synthesizer-prompt.md +0 -129
  374. package/dist/cordis.patch.yml +0 -20
  375. package/dist/index.mjs.map +0 -1
  376. package/dist/paths-Bbai4CaT.mjs +0 -16
  377. package/dist/paths-Bbai4CaT.mjs.map +0 -1
  378. package/dist/subagent.mjs.map +0 -1
  379. /package/{assets → dist/pstack}/docs/guide/03-understand.md +0 -0
  380. /package/{assets → dist/pstack}/docs/guide/08-principles.md +0 -0
  381. /package/{assets → dist/pstack}/docs/guide/README.md +0 -0
  382. /package/{assets → dist/pstack}/skills/architect/references/design-red-flags.md +0 -0
  383. /package/{assets → dist/pstack}/skills/architect/references/rationale-template.md +0 -0
  384. /package/{assets → dist/pstack}/skills/architect/references/runner-prompt.md +0 -0
  385. /package/{assets → dist/pstack}/skills/create-verification-skill/references/feature-map-example/README.md +0 -0
  386. /package/{assets → dist/pstack}/skills/create-verification-skill/references/feature-map-example/create-note.md +0 -0
  387. /package/{assets → dist/pstack}/skills/create-verification-skill/references/feature-map-example/search.md +0 -0
  388. /package/{assets → dist/pstack}/skills/how/references/explorer-prompt.md +0 -0
  389. /package/{assets → dist/pstack}/skills/poteto-mode/playbooks/investigation.md +0 -0
  390. /package/{assets → dist/pstack}/skills/poteto-mode/playbooks/pause-safely.md +0 -0
  391. /package/{assets → dist/pstack}/skills/poteto-mode/playbooks/trace-forensics.md +0 -0
  392. /package/{assets → dist/pstack}/skills/poteto-mode/references/bugbot-triage.md +0 -0
  393. /package/{assets → dist/pstack}/skills/show-me-your-work/references/decision-log-template.tsv +0 -0
  394. /package/{assets → dist/pstack}/skills/typescript-best-practices/references/patterns.md +0 -0
  395. /package/{assets → dist/pstack}/skills/why/references/epistemics.md +0 -0
  396. /package/{assets → dist/pstack}/skills/why/references/investigator-prompt.md +0 -0
  397. /package/{assets → dist/pstack}/skills/why/references/source-playbook.md +0 -0
  398. /package/{assets → dist/pstack}/skills/why/references/sources/code-archaeology.md +0 -0
  399. /package/{assets → dist/pstack}/skills/why/references/sources/databricks.md +0 -0
  400. /package/{assets → dist/pstack}/skills/why/references/sources/datadog.md +0 -0
  401. /package/{assets → dist/pstack}/skills/why/references/sources/incident-postmortem.md +0 -0
  402. /package/{assets → dist/pstack}/skills/why/references/sources/linear.md +0 -0
  403. /package/{assets → dist/pstack}/skills/why/references/sources/notion.md +0 -0
  404. /package/{assets → dist/pstack}/skills/why/references/sources/sentry.md +0 -0
  405. /package/{assets → dist/pstack}/skills/why/references/sources/slack.md +0 -0
  406. /package/{assets → dist/pstack}/skills/why/references/synthesizer-prompt.md +0 -0
@@ -1,11 +1,11 @@
1
1
  ### Worktree and simulator cleanup
2
2
 
3
- 1. Snapshot and audit. Record `df -h /`, then run `scripts/worktree-audit.sh [-b <pr-base-ref>] [repo-path]` (principle-build-the-lever). Without `-b` it checks `MERGED` against `origin/HEAD`, so pass `-b origin/<branch>` when PRs target another branch. It reads paths from `git worktree list`, never hand-typed, since a hand-typed `myrepo-worktrees/x` misses one that lives at `.worktrees/myrepo/x` (principle-encode-lessons-in-structure). It classifies each worktree by size, age, merge state, uncommitted work, PR state, and the newest chat that touched it, then suggests a bucket. The transcript scan is slow, so background it.
3
+ 1. Snapshot and audit. Record `df -h /`, then run `scripts/worktree-audit.sh [-b <pr-base-ref>] [repo-path]` (principle-build-the-lever). Without `-b` it checks `MERGED` against `origin/HEAD`, so pass `-b origin/<branch>` when PRs target another branch. It reads paths from `git worktree list`, never hand-typed, since a hand-typed `myrepo-worktrees/x` misses one that lives at `.cursor/worktrees/myrepo/x` (principle-encode-lessons-in-structure). It classifies each worktree by size, age, merge state, uncommitted work, PR state, and the newest chat that touched it, then suggests a bucket. The transcript scan is slow, so background it.
4
4
  2. The bucket is advice, not permission. The pinned and active chats are the real artifact (principle-prove-it-works). Get that set from the user or sidebar and cross-check every candidate. The lever has marked `safe` a worktree the user had pinned, so the pinned set wins.
5
5
  3. Verify usage before deleting. For every `verify-recent-chat` row, or anything you doubt, fan subagents out to read the transcripts and report whether the chat is pinned or ongoing and which worktrees it touches (principle-guard-the-context-window, transcripts are bulk). A pinned chat spawns arena and repro trees into sibling worktrees via background subagents, and those are in use even when their names never hit the sidebar. Pick each subagent's reasoning level and fast or standard speed for the job, per the Subagents section.
6
6
  4. Pause on irreversible loss. `wip:N` is N tracked uncommitted edits. Show the diff and get a decision first, since removing a clean worktree is recoverable from its branch but uncommitted work is gone. `scratch:N` is untracked throwaway, safe to drop, but name the files. Per Autonomy, clean and merged and not-in-use proceeds. `wip` and in-use pause.
7
7
  5. Prune the confirmed set. Per path, `git worktree remove --force <path>`. If the dir survives on ignored build artifacts, `rm -rf` it, then `git worktree prune`. Branch refs survive, so no commits are lost. Confirm with `df -h /` and re-list.
8
- 6. Simulators and other reclaimers. Simulators are usually the next-biggest win. `xcrun simctl --set testing delete all` (XCTestDevices clones), `xcrun simctl delete unavailable`, and `xcrun simctl runtime list` then `runtime delete <id>` for old runtimes. More when needed: Xcode `DerivedData` and `iOS DeviceSupport`, package caches (pnpm, uv, brew, yarn). Clear only caches the user has not said to keep.
8
+ 6. Simulators and other reclaimers. Simulators are usually the next-biggest win. `xcrun simctl --set testing delete all` (XCTestDevices clones), `xcrun simctl delete unavailable`, and `xcrun simctl runtime list` then `runtime delete <id>` for old runtimes. More when needed: Xcode `DerivedData` and `iOS DeviceSupport`, `~/Library/Application Support/Cursor` (`state.vscdb.backup`, and `snapshots/roots/<root>` where a `<root>` named for a folder you opened as a workspace balloons), package caches (pnpm, uv, brew, yarn). Clear only caches the user has not said to keep.
9
9
 
10
10
  This is the one playbook that deletes user state with no code review to catch a slip, so the gates above are the review.
11
11
 
@@ -1,9 +1,8 @@
1
1
  #!/usr/bin/env node
2
2
  import fs from "node:fs";
3
3
  import process from "node:process";
4
-
5
- const RULE =
6
- "Tests alone are not sufficient verification. A PR is verified only when its unit, live, and perf boxes are all checked.";
4
+ // runtime/skills/poteto-mode/scripts/check-plan.mjs
5
+ const RULE = "Tests alone are not sufficient verification. A PR is verified only when its unit, live, and perf boxes are all checked.";
7
6
  const LANES = /Ten lanes on `[^`<>]+` at the PR head/;
8
7
  const SUB_BLOCKS = [
9
8
  "Depends on.",
@@ -14,49 +13,54 @@ const SUB_BLOCKS = [
14
13
  "Verify, live.",
15
14
  "Verify, perf.",
16
15
  "Review gate.",
17
- "Merge.",
16
+ "Merge."
18
17
  ];
19
- const PROGRAM_H3 = ["Arm the program", "Spawn owners", "PR mechanics", "Verdict and merge", "Boot recipe"];
20
- const PROGRAM_MARKERS = ["git show origin/main:", "schedule_create 1h", "status message"];
18
+ const PROGRAM_H3 = [
19
+ "Arm the program",
20
+ "Spawn owners",
21
+ "PR mechanics",
22
+ "Verdict and merge",
23
+ "Boot recipe"
24
+ ];
25
+ const PROGRAM_MARKERS = ["git show origin/main:", "status message"];
26
+ const TICK_MARKERS = ["create_goal", "schedule_create"];
21
27
  const HOW_TO_READ_MARKERS = [
22
28
  "One box is one unit of work",
23
29
  "names the evidence",
24
30
  "Check a box only when its evidence exists",
25
31
  "playbooks/",
26
- RULE,
32
+ RULE
33
+ ];
34
+ const PERF_ITEMS = [
35
+ "Metric.",
36
+ "Probe.",
37
+ "Baseline.",
38
+ "Rule."
27
39
  ];
28
- const PERF_ITEMS = ["Metric.", "Probe.", "Baseline.", "Rule."];
29
40
  const BOX = /^\s*- \[[ x]\] (.*)$/;
30
-
31
41
  const file = process.argv[2];
32
42
  if (!file) {
33
43
  console.error("Usage: node check-plan.mjs <plan.md>");
34
44
  process.exit(2);
35
45
  }
36
-
37
46
  const raw = fs.readFileSync(file, "utf8").split(/\r?\n/);
38
47
  const problems = [];
39
48
  const fail = (line, message) => problems.push(`${file}:${line}: ${message}`);
40
-
41
49
  let start = 0;
42
- if (raw[0] === "---") {
43
- start = raw.indexOf("---", 1) + 1;
44
- }
45
-
50
+ if (raw[0] === "---") start = raw.indexOf("---", 1) + 1;
46
51
  const lines = [];
47
52
  let fence = null;
48
53
  const openingFence = (text) => {
49
54
  const match = text.match(/^ {0,3}(`{3,}|~{3,})(.*)$/);
50
- if (!match || (match[1][0] === "`" && match[2].includes("`"))) return null;
51
- return { char: match[1][0], length: match[1].length };
55
+ if (!match || match[1][0] === "`" && match[2].includes("`")) return null;
56
+ return {
57
+ char: match[1][0],
58
+ length: match[1].length
59
+ };
52
60
  };
53
61
  const closingFence = (text, opening) => {
54
62
  const match = text.match(/^ {0,3}(`+|~+)[ \t]*$/);
55
- return Boolean(
56
- match &&
57
- match[1][0] === opening.char &&
58
- match[1].length >= opening.length,
59
- );
63
+ return Boolean(match && match[1][0] === opening.char && match[1].length >= opening.length);
60
64
  };
61
65
  for (let i = start; i < raw.length; i++) {
62
66
  const text = raw[i];
@@ -69,42 +73,45 @@ for (let i = start; i < raw.length; i++) {
69
73
  fence = openingFence(text);
70
74
  code = Boolean(fence);
71
75
  }
72
- lines.push({ n, text, code });
76
+ lines.push({
77
+ n,
78
+ text,
79
+ code
80
+ });
73
81
  if (code) continue;
74
- const prose = text
75
- .replace(/`[^`]*`/g, "`")
76
- .replace(/!\[[^\]]*\]\([^)]*\)/g, "")
77
- .replace(/\]\([^)]*\)/g, "]");
82
+ const prose = text.replace(/(?<!`)(`+)(?!`)(.*?)(?<!`)\1(?!`)/g, "`").replace(/!\[[^\]]*\]\([^)]*\)/g, "").replace(/\]\([^)]*\)/g, "]");
78
83
  if (/[\u2013\u2014]/.test(prose)) fail(n, "long dash");
79
84
  if (/[\u2018\u2019\u201c\u201d]/.test(prose)) fail(n, "curly quote");
80
85
  if (/: \S/.test(prose)) fail(n, "mid-sentence colon");
81
86
  }
82
-
83
- const h2 = (l) => (!l.code && l.text.startsWith("## ") ? l.text.slice(3).trim() : null);
87
+ const h2 = (l) => !l.code && l.text.startsWith("## ") ? l.text.slice(3).trim() : null;
84
88
  const sections = [];
85
89
  for (const l of lines) {
86
90
  const title = h2(l);
87
- if (title !== null) sections.push({ title, n: l.n, body: [] });
91
+ if (title !== null) sections.push({
92
+ title,
93
+ n: l.n,
94
+ body: []
95
+ });
88
96
  else if (sections.length) sections.at(-1).body.push(l);
89
97
  }
90
98
  const find = (title) => sections.find((s) => s.title === title);
91
99
  const bodyText = (s) => s.body.map((l) => l.text).join("\n");
92
- const boxes = (ls) => ls.filter((l) => !l.code && BOX.test(l.text)).map((l) => ({ n: l.n, text: l.text.match(BOX)[1] }));
93
-
100
+ const boxes = (ls) => ls.filter((l) => !l.code && BOX.test(l.text)).map((l) => ({
101
+ n: l.n,
102
+ text: l.text.match(BOX)[1]
103
+ }));
94
104
  const h1 = lines.findIndex((l) => !l.code && l.text.startsWith("# "));
95
105
  if (h1 === -1) fail(1, "no H1 title");
96
106
  const howToRead = find("How to read this");
97
- if (!howToRead) fail(1, 'no "## How to read this" section');
107
+ if (!howToRead) fail(1, "no \"## How to read this\" section");
98
108
  if (h1 !== -1 && howToRead) {
99
109
  const intro = lines.slice(h1 + 1).filter((l) => l.n < howToRead.n && l.text.trim() !== "");
100
110
  if (intro.length >= 10) fail(lines[h1].n, `intro is ${intro.length} lines, under ten required`);
101
- for (const marker of HOW_TO_READ_MARKERS) {
102
- if (!bodyText(howToRead).includes(marker)) fail(howToRead.n, `How to read this lacks "${marker}"`);
103
- }
111
+ for (const marker of HOW_TO_READ_MARKERS) if (!bodyText(howToRead).includes(marker)) fail(howToRead.n, `How to read this lacks "${marker}"`);
104
112
  }
105
-
106
113
  const program = find("Program checklist");
107
- if (!program) fail(1, 'no "## Program checklist" section');
114
+ if (!program) fail(1, "no \"## Program checklist\" section");
108
115
  else {
109
116
  const h3s = program.body.filter((l) => !l.code && l.text.startsWith("### ")).map((l) => l.text.slice(4).trim());
110
117
  let cursor = 0;
@@ -113,65 +120,73 @@ else {
113
120
  if (at === -1) fail(program.n, `Program checklist lacks "### ${name}" in order`);
114
121
  else cursor = at + 1;
115
122
  }
116
- for (const marker of PROGRAM_MARKERS) {
117
- if (!bodyText(program).includes(marker)) fail(program.n, `Program checklist lacks "${marker}"`);
118
- }
123
+ for (const marker of PROGRAM_MARKERS) if (!bodyText(program).includes(marker)) fail(program.n, `Program checklist lacks "${marker}"`);
124
+ const programText = bodyText(program);
125
+ if (!programText.includes("/loop 1h") && !TICK_MARKERS.every((marker) => programText.includes(marker))) fail(program.n, `Program checklist lacks "/loop 1h" or both "create_goal" and "schedule_create"`);
119
126
  }
120
-
121
127
  const close = find("Close the program");
122
- if (!close) fail(1, 'no "## Close the program" section');
128
+ if (!close) fail(1, "no \"## Close the program\" section");
123
129
  const programIndex = sections.indexOf(program);
124
130
  const closeIndex = sections.indexOf(close);
125
131
  const prSections = programIndex === -1 || closeIndex === -1 ? [] : sections.slice(programIndex + 1, closeIndex);
126
132
  if (prSections.length === 0) fail(1, "no PR sections between Program checklist and Close the program");
127
-
128
133
  const report = [];
129
134
  for (const pr of prSections) {
130
135
  const heads = [];
131
136
  for (const l of pr.body) {
132
137
  if (l.code) continue;
133
138
  const m = l.text.match(/^\*\*([^*]+)\*\*(.*)$/);
134
- if (m && SUB_BLOCKS.includes(m[1])) heads.push({ name: m[1], n: l.n, rest: m[2].trim(), lines: [] });
139
+ if (m && SUB_BLOCKS.includes(m[1])) heads.push({
140
+ name: m[1],
141
+ n: l.n,
142
+ rest: m[2].trim(),
143
+ lines: []
144
+ });
135
145
  else if (heads.length) heads.at(-1).lines.push(l);
136
146
  }
137
147
  const names = heads.map((h) => h.name);
138
- if (names.join("|") !== SUB_BLOCKS.join("|")) {
139
- fail(pr.n, `${pr.title}: sub-blocks are [${names.join(", ")}], expected [${SUB_BLOCKS.join(", ")}]`);
140
- }
148
+ if (names.join("|") !== SUB_BLOCKS.join("|")) fail(pr.n, `${pr.title}: sub-blocks are [${names.join(", ")}], expected [${SUB_BLOCKS.join(", ")}]`);
141
149
  const block = (name) => heads.find((h) => h.name === name);
142
150
  const counts = {};
143
151
  for (const h of heads) counts[h.name] = boxes(h.lines).length;
144
-
145
152
  const depends = block("Depends on.");
146
153
  if (depends && depends.rest === "") fail(depends.n, `${pr.title}: Depends on names nothing`);
147
- for (const name of ["Files.", "Build.", "You see.", "Verify, unit.", "Merge."]) {
154
+ for (const name of [
155
+ "Files.",
156
+ "Build.",
157
+ "You see.",
158
+ "Verify, unit.",
159
+ "Merge."
160
+ ]) {
148
161
  const b = block(name);
149
162
  if (b && boxes(b.lines).length === 0) fail(b.n, `${pr.title}: ${name} has no box`);
150
163
  }
151
- for (const name of ["Verify, unit.", "Verify, live.", "Verify, perf."]) {
164
+ for (const name of [
165
+ "Verify, unit.",
166
+ "Verify, live.",
167
+ "Verify, perf."
168
+ ]) {
152
169
  const b = block(name);
153
170
  if (b && !b.rest.startsWith(RULE)) fail(b.n, `${pr.title}: ${name} does not open with the rule`);
154
171
  }
155
-
156
172
  const live = block("Verify, live.");
157
173
  if (live) {
158
174
  if (!LANES.test(live.rest)) fail(live.n, `${pr.title}: Verify, live lacks "Ten lanes on \`<swarm workers model>\` at the PR head" with the model filled in`);
159
- const lanes = boxes(live.lines).map((b) => ({ ...b, m: b.text.match(/^Lane (\d+)\. /) }));
175
+ const lanes = boxes(live.lines).map((b) => ({
176
+ ...b,
177
+ m: b.text.match(/^Lane (\d+)\. /)
178
+ }));
160
179
  const numbers = lanes.filter((b) => b.m).map((b) => Number(b.m[1])).sort((a, b) => a - b);
161
180
  if (numbers.join(",") !== "1,2,3,4,5,6,7,8,9,10") fail(live.n, `${pr.title}: lanes are [${numbers.join(",")}], expected 1 to 10`);
162
- for (const lane of lanes) {
163
- if (!lane.m) fail(lane.n, `${pr.title}: live box is not a lane`);
164
- else if (!/Save `[^`]+`/.test(lane.text)) fail(lane.n, `${pr.title}: lane ${lane.m[1]} names no screenshot`);
165
- else if (!lane.text.includes("Pass when")) fail(lane.n, `${pr.title}: lane ${lane.m[1]} has no pass predicate`);
166
- }
181
+ for (const lane of lanes) if (!lane.m) fail(lane.n, `${pr.title}: live box is not a lane`);
182
+ else if (!/Save `[^`]+`/.test(lane.text)) fail(lane.n, `${pr.title}: lane ${lane.m[1]} names no screenshot`);
183
+ else if (!lane.text.includes("Pass when")) fail(lane.n, `${pr.title}: lane ${lane.m[1]} has no pass predicate`);
167
184
  }
168
-
169
185
  const perf = block("Verify, perf.");
170
186
  if (perf) {
171
187
  const items = boxes(perf.lines).map((b) => b.text.split(" ")[0]);
172
188
  if (items.join("|") !== PERF_ITEMS.join("|")) fail(perf.n, `${pr.title}: perf boxes are [${items.join(", ")}], expected [${PERF_ITEMS.join(", ")}]`);
173
189
  }
174
-
175
190
  const gate = block("Review gate.");
176
191
  if (gate) {
177
192
  const gateBoxes = boxes(gate.lines);
@@ -180,26 +195,24 @@ for (const pr of prSections) {
180
195
  } else {
181
196
  const text = gate.lines.map((l) => l.text).join("\n");
182
197
  if (gateBoxes.length === 0) fail(gate.n, `${pr.title}: Review gate has no box`);
183
- for (const word of ["screenshot", "video", "operator"]) {
184
- if (!text.includes(word)) fail(gate.n, `${pr.title}: Review gate lacks "${word}"`);
185
- }
198
+ for (const word of [
199
+ "screenshot",
200
+ "video",
201
+ "operator"
202
+ ]) if (!text.includes(word)) fail(gate.n, `${pr.title}: Review gate lacks "${word}"`);
186
203
  }
187
204
  }
188
-
189
205
  const total = boxes(pr.body).length;
190
206
  const cells = SUB_BLOCKS.filter((s) => s !== "Depends on.").map((s) => `${s.replace(/[ ,.]+/g, "-").replace(/-$/, "").toLowerCase()}=${counts[s] ?? 0}`);
191
207
  report.push(`${pr.title} boxes=${total} ${cells.join(" ")}`);
192
208
  }
193
-
194
209
  if (closeIndex !== -1) {
195
210
  const tail = sections.slice(closeIndex + 1);
196
- for (const s of tail) {
197
- if (!s.title.startsWith("Appendix")) fail(s.n, `"## ${s.title}" after Close the program is not an appendix`);
198
- }
199
- if (!tail.some((s) => s.title.includes("Prototype evidence"))) fail(close.n, 'no "## Appendix ... Prototype evidence" section');
211
+ for (const s of tail) if (!s.title.startsWith("Appendix")) fail(s.n, `"## ${s.title}" after Close the program is not an appendix`);
212
+ if (!tail.some((s) => s.title.includes("Prototype evidence"))) fail(close.n, "no \"## Appendix ... Prototype evidence\" section");
200
213
  }
201
-
202
214
  for (const line of report) console.log(line);
203
215
  console.log(`${prSections.length} PR sections, ${problems.length} problems`);
204
216
  for (const p of problems) console.error(p);
205
217
  process.exit(problems.length ? 1 : 0);
218
+ export {};
@@ -1,13 +1,13 @@
1
+ import { expect } from "./expect.mjs";
2
+ import "./support.mjs";
1
3
  import { mkdtempSync, rmSync, writeFileSync } from "node:fs";
2
4
  import { tmpdir } from "node:os";
3
5
  import { join } from "node:path";
4
6
  import { spawnSync } from "node:child_process";
5
- import { expect, test } from "bun:test";
6
-
7
- const checker = join(import.meta.dir, "check-plan.mjs");
8
- const rule =
9
- "Tests alone are not sufficient verification. A PR is verified only when its unit, live, and perf boxes are all checked.";
10
-
7
+ import { test } from "node:test";
8
+ // runtime/skills/poteto-mode/scripts/check-plan.test.ts
9
+ const checker = join(import.meta.dirname, "check-plan.mjs");
10
+ const rule = "Tests alone are not sufficient verification. A PR is verified only when its unit, live, and perf boxes are all checked.";
11
11
  const validPlan = `# Demo
12
12
 
13
13
  ## How to read this
@@ -20,7 +20,7 @@ ${rule}
20
20
  ### PR mechanics
21
21
  ### Verdict and merge
22
22
  ### Boot recipe
23
- \`git show origin/main:\` schedule_create 1h status message
23
+ \`git show origin/main:\` \`create_goal\` \`schedule_create\` status message
24
24
 
25
25
  ## PR 1
26
26
  **Depends on.** None.
@@ -49,8 +49,7 @@ Close.
49
49
  ## Appendix Prototype evidence
50
50
  Recorded.
51
51
  `;
52
-
53
- const runPlan = (example: string, expectedExit: number) => {
52
+ const runPlan = (example, expectedExit) => {
54
53
  const directory = mkdtempSync(join(tmpdir(), "check-plan-test-"));
55
54
  const file = join(directory, "plan.md");
56
55
  writeFileSync(file, validPlan + example);
@@ -59,38 +58,71 @@ const runPlan = (example: string, expectedExit: number) => {
59
58
  expect(result.status).toBe(expectedExit);
60
59
  return result;
61
60
  } finally {
62
- rmSync(directory, { recursive: true, force: true });
61
+ rmSync(directory, {
62
+ recursive: true,
63
+ force: true
64
+ });
63
65
  }
64
66
  };
65
-
66
67
  test("accepts ordinary, indented, and longer closing fences", () => {
67
- for (const indent of ["", " ", " ", " "])
68
- runPlan(`${indent}\`\`\`markdown\n## Example only\n${indent}\`\`\`\n`, 0);
68
+ for (const indent of [
69
+ "",
70
+ " ",
71
+ " ",
72
+ " "
73
+ ]) runPlan(`${indent}\`\`\`markdown\n## Example only\n${indent}\`\`\`\n`, 0);
69
74
  runPlan("```markdown\n## Example only\n````\n", 0);
70
75
  });
71
-
72
76
  test("accepts nested backticks and tilde info strings", () => {
73
77
  runPlan("````markdown\n```markdown\n## Example only\n```\n````\n", 0);
74
78
  runPlan("~~~markdown `info`\n## Example only\n ~~~\n", 0);
75
79
  });
76
-
77
80
  test("keeps mismatched, shorter, and suffixed closers inside the fence", () => {
78
81
  runPlan("````markdown\n~~~\n## Example only\n````\n", 0);
79
82
  runPlan("````markdown\n```\n## Example only\n````\n", 0);
80
83
  runPlan("````markdown\n``` info\n## Example only\n````\n", 0);
81
84
  });
82
-
83
85
  test("rejects headings and prose outside a proper close", () => {
84
- for (const suffix of [" ", "\t"]) {
86
+ for (const suffix of [" ", " "]) {
85
87
  const heading = runPlan(`\`\`\`markdown\n## Example only\n\`\`\`${suffix}\n## Example only\n`, 1);
86
- expect(heading.stderr).toContain('"## Example only" after Close the program is not an appendix');
88
+ expect(heading.stderr).toContain("\"## Example only\" after Close the program is not an appendix");
87
89
  }
88
-
89
90
  const prose = runPlan("```markdown\nThis prose has a mid-sentence colon: inside code\n```\nThis prose has a mid-sentence colon: bad.\n", 1);
90
91
  expect(prose.stderr).toContain("mid-sentence colon");
91
92
  });
92
-
93
93
  test("rejects backtick info strings containing a backtick", () => {
94
94
  const result = runPlan("```markdown `invalid`\n## Example only\n```\n", 1);
95
- expect(result.stderr).toContain('"## Example only" after Close the program is not an appendix');
95
+ expect(result.stderr).toContain("\"## Example only\" after Close the program is not an appendix");
96
+ });
97
+ test("ignores prose punctuation inside matching multi-backtick code spans", () => {
98
+ for (const count of [
99
+ 2,
100
+ 3,
101
+ 4
102
+ ]) {
103
+ const delimiter = "`".repeat(count);
104
+ runPlan(`Use ${delimiter}echo \`x\`: “quoted” — example${delimiter}.\n`, 0);
105
+ }
106
+ });
107
+ test("checks prose following a multi-backtick span and unmatched delimiters", () => {
108
+ const outside = runPlan("Use ``echo `x`: y``. Bad: prose.\n", 1);
109
+ expect(outside.stderr).toContain("mid-sentence colon");
110
+ const unmatched = runPlan("Use ``unclosed: bad` here.\n", 1);
111
+ expect(unmatched.stderr).toContain("mid-sentence colon");
112
+ });
113
+ test("accepts the upstream /loop tick or the DSH goal plus schedule tick", () => {
114
+ const upstream = validPlan.replace("`git show origin/main:` `create_goal` `schedule_create` status message", "`git show origin/main:` /loop 1h status message");
115
+ const directory = mkdtempSync(join(tmpdir(), "check-plan-test-"));
116
+ const file = join(directory, "plan.md");
117
+ writeFileSync(file, upstream);
118
+ try {
119
+ const result = spawnSync("node", [checker, file], { encoding: "utf8" });
120
+ expect(result.status).toBe(0);
121
+ } finally {
122
+ rmSync(directory, {
123
+ recursive: true,
124
+ force: true
125
+ });
126
+ }
96
127
  });
128
+ export {};
@@ -0,0 +1,254 @@
1
+ import { inspect } from "node:util";
2
+ // runtime/skills/poteto-mode/scripts/expect.ts
3
+ /**
4
+ * A small `expect` for `node:test`.
5
+ *
6
+ * The five upstream test files were written against `bun:test`. Their assertions
7
+ * are ordinary value comparisons, so this module supplies exactly the matchers
8
+ * they use rather than a general test framework. It is deliberately not a drop-in
9
+ * replacement: a matcher that is not listed here fails to compile, which keeps the
10
+ * port auditable against the calls that actually exist.
11
+ *
12
+ * Covered: `toBe`, `toEqual`, `toContain`, `toMatch`, `toThrow`, `toBeNull`,
13
+ * `toBeUndefined`, `toBeInstanceOf`, `toHaveLength`, `toEndWith`, `toMatchObject`,
14
+ * `.not` on each, and `rejects` / `resolves` for promises.
15
+ *
16
+ * Two differences from `bun:test`, stated so a failure is not misread:
17
+ *
18
+ * - `toEqual` is structural for arrays and plain objects, `Object.is` otherwise.
19
+ * A class instance only equals itself; `toBeInstanceOf` is the matcher for type
20
+ * identity. The ported tests compare plain data, which is why this is enough.
21
+ * - A failure throws `AssertionError` with the two values rendered, not Bun's
22
+ * coloured diff.
23
+ */
24
+ /** Raised by every failing assertion. */
25
+ var AssertionError = class extends Error {
26
+ constructor(message) {
27
+ super(message);
28
+ this.name = "AssertionError";
29
+ }
30
+ };
31
+ function display(value) {
32
+ if (typeof value === "function") return `[Function ${value.name || "anonymous"}]`;
33
+ return inspect(value, {
34
+ depth: 3,
35
+ breakLength: 120,
36
+ maxArrayLength: 20
37
+ });
38
+ }
39
+ function messageOf(error) {
40
+ if (error instanceof Error) return `${error.name}: ${error.message}`;
41
+ return String(error);
42
+ }
43
+ /** Structural equality for the shapes the ported tests compare. */
44
+ function deepEqual(left, right) {
45
+ if (Object.is(left, right)) return true;
46
+ if (left instanceof Date || right instanceof Date) return left instanceof Date && right instanceof Date && left.getTime() === right.getTime();
47
+ if (Array.isArray(left) || Array.isArray(right)) {
48
+ if (!Array.isArray(left) || !Array.isArray(right) || left.length !== right.length) return false;
49
+ return left.every((item, index) => deepEqual(item, right[index]));
50
+ }
51
+ if (left === null || right === null || typeof left !== "object" || typeof right !== "object") return false;
52
+ const leftProto = Object.getPrototypeOf(left);
53
+ if (leftProto !== Object.getPrototypeOf(right)) return false;
54
+ if (leftProto !== Object.prototype && leftProto !== null) return false;
55
+ const leftKeys = Object.keys(left);
56
+ const rightKeys = Object.keys(right);
57
+ if (leftKeys.length !== rightKeys.length) return false;
58
+ return leftKeys.every((key) => deepEqual(left[key], right[key]));
59
+ }
60
+ function contains(haystack, needle) {
61
+ if (typeof haystack === "string") return haystack.includes(String(needle));
62
+ if (Array.isArray(haystack)) return haystack.some((item) => deepEqual(item, needle));
63
+ if (haystack instanceof Set) return [...haystack].some((item) => deepEqual(item, needle));
64
+ return false;
65
+ }
66
+ /**
67
+ * Whether `expected` is a partial description of `actual`.
68
+ *
69
+ * `bun:test`'s `toMatchObject` is recursive: every key in `expected` must exist and
70
+ * match, arrays match element by element with the same partial rule, and extra keys
71
+ * in `actual` are allowed. That is what lets an assertion name only the fields it
72
+ * cares about, which several ported cases rely on.
73
+ */
74
+ function matchesObject(actual, expected) {
75
+ if (Array.isArray(expected)) {
76
+ if (!Array.isArray(actual) || actual.length !== expected.length) return false;
77
+ return expected.every((item, index) => matchesObject(actual[index], item));
78
+ }
79
+ if (expected instanceof Date) return deepEqual(actual, expected);
80
+ if (expected === null || typeof expected !== "object") return deepEqual(actual, expected);
81
+ if (actual === null || typeof actual !== "object") return false;
82
+ return Object.entries(expected).every(([key, value]) => matchesObject(actual[key], value));
83
+ }
84
+ function thrownBy(call) {
85
+ try {
86
+ call();
87
+ return { thrown: false };
88
+ } catch (error) {
89
+ return {
90
+ thrown: true,
91
+ error
92
+ };
93
+ }
94
+ }
95
+ function buildMatchers(actual, negate) {
96
+ /**
97
+ * Fail when `ok` is not what the matcher asked for.
98
+ *
99
+ * `negate` inverts the requirement, so `.not.toContain(x)` passes on a haystack
100
+ * that does not contain `x` and fails when it does.
101
+ */
102
+ const check = (ok, matcher, expected) => {
103
+ if (ok === !negate) return;
104
+ const relation = negate ? `not to ${matcher}` : matcher;
105
+ throw new AssertionError(`expected ${display(actual)} ${relation} ${display(expected)}`);
106
+ };
107
+ const checkPlain = (ok, matcher) => {
108
+ if (ok === !negate) return;
109
+ throw new AssertionError(`expected ${display(actual)} ${negate ? `not to ${matcher}` : matcher}`);
110
+ };
111
+ const matchers = {
112
+ toBe(expected) {
113
+ check(Object.is(actual, expected), "toBe", expected);
114
+ },
115
+ toEqual(expected) {
116
+ check(deepEqual(actual, expected), "toEqual", expected);
117
+ },
118
+ toContain(expected) {
119
+ check(contains(actual, expected), "toContain", expected);
120
+ },
121
+ toMatch(expected) {
122
+ const text = String(actual);
123
+ check(typeof expected === "string" ? text.includes(expected) : expected.test(text), "toMatch", expected);
124
+ },
125
+ toThrow(expected) {
126
+ if (typeof actual !== "function") throw new AssertionError(`toThrow needs a function, received ${display(actual)}`);
127
+ const result = thrownBy(actual);
128
+ if (!result.thrown) {
129
+ checkPlain(false, "toThrow");
130
+ return;
131
+ }
132
+ if (expected === void 0) {
133
+ checkPlain(true, "toThrow");
134
+ return;
135
+ }
136
+ const message = messageOf(result.error);
137
+ const ok = typeof expected === "string" ? message.includes(expected) : expected instanceof RegExp ? expected.test(message) : result.error instanceof expected;
138
+ check(ok, "toThrow", expected);
139
+ },
140
+ toBeNull() {
141
+ checkPlain(actual === null, "toBeNull");
142
+ },
143
+ toBeUndefined() {
144
+ checkPlain(actual === void 0, "toBeUndefined");
145
+ },
146
+ toBeInstanceOf(expected) {
147
+ check(actual instanceof expected, "toBeInstanceOf", expected);
148
+ },
149
+ toHaveLength(expected) {
150
+ const length = actual?.length;
151
+ check(length === expected, "toHaveLength", expected);
152
+ },
153
+ toEndWith(expected) {
154
+ check(String(actual).endsWith(expected), "toEndWith", expected);
155
+ },
156
+ toMatchObject(expected) {
157
+ check(matchesObject(actual, expected), "toMatchObject", expected);
158
+ }
159
+ };
160
+ Object.defineProperties(matchers, {
161
+ not: {
162
+ get: () => buildMatchers(actual, !negate),
163
+ enumerable: true
164
+ },
165
+ rejects: {
166
+ get: () => buildAsyncMatchers(actual, "rejects", negate),
167
+ enumerable: true
168
+ },
169
+ resolves: {
170
+ get: () => buildAsyncMatchers(actual, "resolves", negate),
171
+ enumerable: true
172
+ }
173
+ });
174
+ return matchers;
175
+ }
176
+ /**
177
+ * Compare against a settled promise.
178
+ *
179
+ * `rejects` reads the rejection reason and fails when the promise resolved;
180
+ * `resolves` is the mirror. Each matcher awaits the settlement, which is what
181
+ * makes `await expect(promise).rejects.toThrow(...)` wait before it compares.
182
+ */
183
+ function buildAsyncMatchers(actual, mode, negate) {
184
+ if (typeof actual?.then !== "function") throw new AssertionError(`expected a promise, received ${display(actual)}`);
185
+ const wantRejection = mode === "rejects" !== negate;
186
+ const settle = async () => {
187
+ let resolved;
188
+ let rejected;
189
+ await Promise.resolve(actual).then((value) => {
190
+ resolved = { value };
191
+ }, (error) => {
192
+ rejected = { error };
193
+ });
194
+ if (wantRejection) {
195
+ if (resolved !== void 0) throw new AssertionError(`expected the promise to reject, it resolved to ${display(resolved.value)}`);
196
+ return rejected?.error;
197
+ }
198
+ if (rejected !== void 0) throw new AssertionError(`expected the promise to resolve, it rejected with ${messageOf(rejected.error)}`);
199
+ return resolved?.value;
200
+ };
201
+ /**
202
+ * Run one matcher against the settled value.
203
+ *
204
+ * `toThrow` and `toBeInstanceOf` both read the rejection reason, so a thrown
205
+ * reason is turned back into a thunk for `toThrow` rather than special-cased
206
+ * twice. `negate` is already folded into the settlement mode, so the inner
207
+ * matchers run un-negated.
208
+ */
209
+ const wrap = async (name, expected) => {
210
+ const subject = await settle();
211
+ if (name === "toThrow") {
212
+ buildMatchers(() => {
213
+ throw subject;
214
+ }, false).toThrow(expected);
215
+ return;
216
+ }
217
+ if (name === "toBeNull") {
218
+ buildMatchers(subject, false).toBeNull();
219
+ return;
220
+ }
221
+ if (name === "toBeUndefined") {
222
+ buildMatchers(subject, false).toBeUndefined();
223
+ return;
224
+ }
225
+ const matchers = buildMatchers(subject, false);
226
+ const matcher = matchers[name];
227
+ if (typeof matcher !== "function") throw new AssertionError(`unknown matcher ${name}`);
228
+ matcher.call(matchers, expected);
229
+ };
230
+ const matchers = {
231
+ toBe: (expected) => wrap("toBe", expected),
232
+ toEqual: (expected) => wrap("toEqual", expected),
233
+ toContain: (expected) => wrap("toContain", expected),
234
+ toMatch: (expected) => wrap("toMatch", expected),
235
+ toThrow: (expected) => wrap("toThrow", expected),
236
+ toBeNull: () => wrap("toBeNull"),
237
+ toBeUndefined: () => wrap("toBeUndefined"),
238
+ toBeInstanceOf: (expected) => wrap("toBeInstanceOf", expected),
239
+ toHaveLength: (expected) => wrap("toHaveLength", expected),
240
+ toEndWith: (expected) => wrap("toEndWith", expected),
241
+ toMatchObject: (expected) => wrap("toMatchObject", expected)
242
+ };
243
+ Object.defineProperty(matchers, "not", {
244
+ get: () => buildAsyncMatchers(actual, mode, !negate),
245
+ enumerable: true
246
+ });
247
+ return matchers;
248
+ }
249
+ const expect = Object.assign((actual) => buildMatchers(actual, false), {
250
+ not: (actual) => buildMatchers(actual, true),
251
+ rejects: (actual) => buildAsyncMatchers(actual, "rejects", false),
252
+ resolves: (actual) => buildAsyncMatchers(actual, "resolves", false)
253
+ });
254
+ export { AssertionError, deepEqual, expect };