@therocketcode/gsd-core 1.4.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 (568) hide show
  1. package/.claude-plugin/plugin.json +23 -0
  2. package/GEMINI.md +53 -0
  3. package/LICENSE +21 -0
  4. package/README.ja-JP.md +125 -0
  5. package/README.ko-KR.md +125 -0
  6. package/README.md +144 -0
  7. package/README.pt-BR.md +125 -0
  8. package/README.zh-CN.md +125 -0
  9. package/agents/gsd-advisor-researcher.md +108 -0
  10. package/agents/gsd-ai-researcher.md +114 -0
  11. package/agents/gsd-assumptions-analyzer.md +105 -0
  12. package/agents/gsd-code-fixer.md +668 -0
  13. package/agents/gsd-code-reviewer.md +387 -0
  14. package/agents/gsd-codebase-mapper.md +853 -0
  15. package/agents/gsd-debug-session-manager.md +314 -0
  16. package/agents/gsd-debugger.md +1452 -0
  17. package/agents/gsd-doc-classifier.md +168 -0
  18. package/agents/gsd-doc-synthesizer.md +204 -0
  19. package/agents/gsd-doc-verifier.md +217 -0
  20. package/agents/gsd-doc-writer.md +616 -0
  21. package/agents/gsd-domain-researcher.md +147 -0
  22. package/agents/gsd-eval-auditor.md +191 -0
  23. package/agents/gsd-eval-planner.md +154 -0
  24. package/agents/gsd-executor.md +785 -0
  25. package/agents/gsd-framework-selector.md +160 -0
  26. package/agents/gsd-integration-checker.md +470 -0
  27. package/agents/gsd-intel-updater.md +342 -0
  28. package/agents/gsd-nyquist-auditor.md +203 -0
  29. package/agents/gsd-pattern-mapper.md +335 -0
  30. package/agents/gsd-phase-researcher.md +867 -0
  31. package/agents/gsd-plan-checker.md +978 -0
  32. package/agents/gsd-planner.md +1204 -0
  33. package/agents/gsd-project-researcher.md +611 -0
  34. package/agents/gsd-research-synthesizer.md +259 -0
  35. package/agents/gsd-roadmapper.md +688 -0
  36. package/agents/gsd-security-auditor.md +155 -0
  37. package/agents/gsd-ui-auditor.md +495 -0
  38. package/agents/gsd-ui-checker.md +309 -0
  39. package/agents/gsd-ui-researcher.md +374 -0
  40. package/agents/gsd-user-profiler.md +171 -0
  41. package/agents/gsd-verifier.md +923 -0
  42. package/assets/gsd-logo-2000-transparent.png +0 -0
  43. package/assets/gsd-logo-2000-transparent.svg +17 -0
  44. package/assets/gsd-logo-2000.png +0 -0
  45. package/assets/gsd-logo-2000.svg +21 -0
  46. package/assets/terminal.svg +68 -0
  47. package/bin/install.js +12726 -0
  48. package/bin/lib/ui-safety-gate.cjs +107 -0
  49. package/commands/gsd/add-tests.md +42 -0
  50. package/commands/gsd/ai-integration-phase.md +37 -0
  51. package/commands/gsd/audit-fix.md +34 -0
  52. package/commands/gsd/audit-milestone.md +37 -0
  53. package/commands/gsd/audit-uat.md +24 -0
  54. package/commands/gsd/autonomous.md +48 -0
  55. package/commands/gsd/capture.md +62 -0
  56. package/commands/gsd/cleanup.md +24 -0
  57. package/commands/gsd/code-review.md +59 -0
  58. package/commands/gsd/complete-milestone.md +143 -0
  59. package/commands/gsd/config.md +56 -0
  60. package/commands/gsd/debug.md +52 -0
  61. package/commands/gsd/discover-product.md +65 -0
  62. package/commands/gsd/discuss-phase.md +77 -0
  63. package/commands/gsd/docs-update.md +49 -0
  64. package/commands/gsd/eval-review.md +33 -0
  65. package/commands/gsd/execute-phase.md +66 -0
  66. package/commands/gsd/explore.md +27 -0
  67. package/commands/gsd/extract-learnings.md +23 -0
  68. package/commands/gsd/fast.md +31 -0
  69. package/commands/gsd/forensics.md +57 -0
  70. package/commands/gsd/graphify.md +204 -0
  71. package/commands/gsd/health.md +31 -0
  72. package/commands/gsd/help.md +28 -0
  73. package/commands/gsd/import.md +45 -0
  74. package/commands/gsd/inbox.md +39 -0
  75. package/commands/gsd/ingest-docs.md +42 -0
  76. package/commands/gsd/manager.md +45 -0
  77. package/commands/gsd/map-codebase.md +83 -0
  78. package/commands/gsd/milestone-summary.md +51 -0
  79. package/commands/gsd/model-domain.md +65 -0
  80. package/commands/gsd/mvp-phase.md +45 -0
  81. package/commands/gsd/new-milestone.md +45 -0
  82. package/commands/gsd/new-project.md +47 -0
  83. package/commands/gsd/ns-context.md +23 -0
  84. package/commands/gsd/ns-ideate.md +24 -0
  85. package/commands/gsd/ns-manage.md +29 -0
  86. package/commands/gsd/ns-project.md +22 -0
  87. package/commands/gsd/ns-review.md +26 -0
  88. package/commands/gsd/ns-workflow.md +28 -0
  89. package/commands/gsd/pause-work.md +43 -0
  90. package/commands/gsd/phase.md +56 -0
  91. package/commands/gsd/plan-phase.md +64 -0
  92. package/commands/gsd/plan-review-convergence.md +59 -0
  93. package/commands/gsd/pr-branch.md +26 -0
  94. package/commands/gsd/profile-user.md +46 -0
  95. package/commands/gsd/progress.md +48 -0
  96. package/commands/gsd/quick.md +174 -0
  97. package/commands/gsd/recommend-architecture.md +64 -0
  98. package/commands/gsd/resume-work.md +30 -0
  99. package/commands/gsd/review-backlog.md +63 -0
  100. package/commands/gsd/review.md +42 -0
  101. package/commands/gsd/secure-phase.md +36 -0
  102. package/commands/gsd/settings.md +29 -0
  103. package/commands/gsd/ship.md +24 -0
  104. package/commands/gsd/sketch.md +60 -0
  105. package/commands/gsd/spec-phase.md +63 -0
  106. package/commands/gsd/spike.md +57 -0
  107. package/commands/gsd/stats.md +20 -0
  108. package/commands/gsd/surface.md +155 -0
  109. package/commands/gsd/testing-strategy.md +65 -0
  110. package/commands/gsd/thread.md +24 -0
  111. package/commands/gsd/ui-phase.md +35 -0
  112. package/commands/gsd/ui-review.md +33 -0
  113. package/commands/gsd/ultraplan-phase.md +34 -0
  114. package/commands/gsd/undo.md +35 -0
  115. package/commands/gsd/update.md +49 -0
  116. package/commands/gsd/validate-phase.md +36 -0
  117. package/commands/gsd/verify-work.md +39 -0
  118. package/commands/gsd/workspace.md +52 -0
  119. package/commands/gsd/workstreams.md +70 -0
  120. package/gemini-extension.json +6 -0
  121. package/gsd-core/bin/check-latest-version.cjs +161 -0
  122. package/gsd-core/bin/gsd-tools.cjs +1928 -0
  123. package/gsd-core/bin/lib/active-workstream-store.cjs +291 -0
  124. package/gsd-core/bin/lib/adr-parser.cjs +399 -0
  125. package/gsd-core/bin/lib/agent-command-router.cjs +68 -0
  126. package/gsd-core/bin/lib/artifacts.cjs +51 -0
  127. package/gsd-core/bin/lib/audit.cjs +743 -0
  128. package/gsd-core/bin/lib/check-command-router.cjs +343 -0
  129. package/gsd-core/bin/lib/cjs-command-router-adapter.cjs +81 -0
  130. package/gsd-core/bin/lib/cli-exit.cjs +42 -0
  131. package/gsd-core/bin/lib/clock.cjs +95 -0
  132. package/gsd-core/bin/lib/clusters.cjs +132 -0
  133. package/gsd-core/bin/lib/code-review-flags.cjs +59 -0
  134. package/gsd-core/bin/lib/command-aliases.cjs +809 -0
  135. package/gsd-core/bin/lib/command-arg-projection.cjs +55 -0
  136. package/gsd-core/bin/lib/command-routing-hub.cjs +300 -0
  137. package/gsd-core/bin/lib/commands.cjs +1203 -0
  138. package/gsd-core/bin/lib/config-schema.cjs +29 -0
  139. package/gsd-core/bin/lib/config-types.cjs +19 -0
  140. package/gsd-core/bin/lib/config.cjs +738 -0
  141. package/gsd-core/bin/lib/configuration.cjs +239 -0
  142. package/gsd-core/bin/lib/context-utilization.cjs +48 -0
  143. package/gsd-core/bin/lib/core.cjs +2051 -0
  144. package/gsd-core/bin/lib/decisions.cjs +118 -0
  145. package/gsd-core/bin/lib/docs.cjs +252 -0
  146. package/gsd-core/bin/lib/drift.cjs +364 -0
  147. package/gsd-core/bin/lib/fallow-runner.cjs +115 -0
  148. package/gsd-core/bin/lib/frontmatter.cjs +442 -0
  149. package/gsd-core/bin/lib/gap-checker.cjs +257 -0
  150. package/gsd-core/bin/lib/graphify.cjs +496 -0
  151. package/gsd-core/bin/lib/gsd2-import.cjs +456 -0
  152. package/gsd-core/bin/lib/init-command-router.cjs +62 -0
  153. package/gsd-core/bin/lib/init.cjs +1815 -0
  154. package/gsd-core/bin/lib/install-profiles.cjs +584 -0
  155. package/gsd-core/bin/lib/installer-migration-authoring.cjs +122 -0
  156. package/gsd-core/bin/lib/installer-migration-report.cjs +350 -0
  157. package/gsd-core/bin/lib/installer-migrations/000-first-time-baseline.cjs +218 -0
  158. package/gsd-core/bin/lib/installer-migrations/001-legacy-orphan-files.cjs +48 -0
  159. package/gsd-core/bin/lib/installer-migrations/002-codex-legacy-hooks-json.cjs +94 -0
  160. package/gsd-core/bin/lib/installer-migrations/003-rename-get-shit-done-to-gsd-core.cjs +108 -0
  161. package/gsd-core/bin/lib/installer-migrations.cjs +823 -0
  162. package/gsd-core/bin/lib/intel.cjs +590 -0
  163. package/gsd-core/bin/lib/learnings.cjs +270 -0
  164. package/gsd-core/bin/lib/legacy-cleanup.cjs +253 -0
  165. package/gsd-core/bin/lib/milestone.cjs +373 -0
  166. package/gsd-core/bin/lib/model-catalog.cjs +154 -0
  167. package/gsd-core/bin/lib/model-profiles.cjs +24 -0
  168. package/gsd-core/bin/lib/observability/event.cjs +51 -0
  169. package/gsd-core/bin/lib/observability/logger.cjs +146 -0
  170. package/gsd-core/bin/lib/observability/redaction.cjs +48 -0
  171. package/gsd-core/bin/lib/package-identity.cjs +35 -0
  172. package/gsd-core/bin/lib/package-legitimacy.cjs +368 -0
  173. package/gsd-core/bin/lib/phase-command-router.cjs +189 -0
  174. package/gsd-core/bin/lib/phase-lifecycle.cjs +74 -0
  175. package/gsd-core/bin/lib/phase.cjs +1307 -0
  176. package/gsd-core/bin/lib/phases-command-router.cjs +43 -0
  177. package/gsd-core/bin/lib/plan-scan.cjs +91 -0
  178. package/gsd-core/bin/lib/planning-workspace.cjs +245 -0
  179. package/gsd-core/bin/lib/profile-output.cjs +1120 -0
  180. package/gsd-core/bin/lib/profile-pipeline.cjs +517 -0
  181. package/gsd-core/bin/lib/project-root.cjs +119 -0
  182. package/gsd-core/bin/lib/prompt-budget.cjs +305 -0
  183. package/gsd-core/bin/lib/research-provider.cjs +137 -0
  184. package/gsd-core/bin/lib/research-store.cjs +167 -0
  185. package/gsd-core/bin/lib/review-reviewer-selection.cjs +121 -0
  186. package/gsd-core/bin/lib/roadmap-command-router.cjs +166 -0
  187. package/gsd-core/bin/lib/roadmap-upgrade.cjs +476 -0
  188. package/gsd-core/bin/lib/roadmap.cjs +600 -0
  189. package/gsd-core/bin/lib/runtime-artifact-layout.cjs +312 -0
  190. package/gsd-core/bin/lib/runtime-config-adapter-registry.cjs +56 -0
  191. package/gsd-core/bin/lib/runtime-homes.cjs +190 -0
  192. package/gsd-core/bin/lib/runtime-name-policy.cjs +96 -0
  193. package/gsd-core/bin/lib/runtime-slash.cjs +119 -0
  194. package/gsd-core/bin/lib/schema-detect.cjs +159 -0
  195. package/gsd-core/bin/lib/secrets.cjs +34 -0
  196. package/gsd-core/bin/lib/security.cjs +480 -0
  197. package/gsd-core/bin/lib/semver-compare.cjs +42 -0
  198. package/gsd-core/bin/lib/shell-command-projection.cjs +533 -0
  199. package/gsd-core/bin/lib/state-command-router.cjs +160 -0
  200. package/gsd-core/bin/lib/state-document.cjs +259 -0
  201. package/gsd-core/bin/lib/state.cjs +2010 -0
  202. package/gsd-core/bin/lib/surface.cjs +449 -0
  203. package/gsd-core/bin/lib/task-command-router.cjs +85 -0
  204. package/gsd-core/bin/lib/template.cjs +237 -0
  205. package/gsd-core/bin/lib/uat.cjs +297 -0
  206. package/gsd-core/bin/lib/ui-safety-gate.cjs +98 -0
  207. package/gsd-core/bin/lib/update-context.cjs +218 -0
  208. package/gsd-core/bin/lib/validate-command-router.cjs +91 -0
  209. package/gsd-core/bin/lib/validate.cjs +112 -0
  210. package/gsd-core/bin/lib/verification-command-router.cjs +31 -0
  211. package/gsd-core/bin/lib/verification.cjs +193 -0
  212. package/gsd-core/bin/lib/verify-command-router.cjs +44 -0
  213. package/gsd-core/bin/lib/verify.cjs +1451 -0
  214. package/gsd-core/bin/lib/workstream-inventory-builder.cjs +81 -0
  215. package/gsd-core/bin/lib/workstream-inventory.cjs +147 -0
  216. package/gsd-core/bin/lib/workstream-name-policy.cjs +91 -0
  217. package/gsd-core/bin/lib/workstream.cjs +380 -0
  218. package/gsd-core/bin/lib/worktree-base-ref.cjs +325 -0
  219. package/gsd-core/bin/lib/worktree-safety.cjs +943 -0
  220. package/gsd-core/bin/shared/config-defaults.manifest.json +98 -0
  221. package/gsd-core/bin/shared/config-schema.manifest.json +192 -0
  222. package/gsd-core/bin/shared/model-catalog.json +149 -0
  223. package/gsd-core/bin/shared/runtime-aliases.manifest.json +75 -0
  224. package/gsd-core/bin/verify-reapply-patches.cjs +349 -0
  225. package/gsd-core/contexts/dev.md +21 -0
  226. package/gsd-core/contexts/research.md +22 -0
  227. package/gsd-core/contexts/review.md +23 -0
  228. package/gsd-core/references/agent-contracts.md +79 -0
  229. package/gsd-core/references/ai-evals.md +156 -0
  230. package/gsd-core/references/ai-frameworks.md +186 -0
  231. package/gsd-core/references/architecture-decision.md +74 -0
  232. package/gsd-core/references/artifact-types.md +131 -0
  233. package/gsd-core/references/auth-in-tests.md +91 -0
  234. package/gsd-core/references/autonomous-smart-discuss.md +277 -0
  235. package/gsd-core/references/checkpoints.md +814 -0
  236. package/gsd-core/references/common-bug-patterns.md +114 -0
  237. package/gsd-core/references/context-budget.md +85 -0
  238. package/gsd-core/references/continuation-format.md +253 -0
  239. package/gsd-core/references/db-test-isolation.md +54 -0
  240. package/gsd-core/references/debugger-philosophy.md +76 -0
  241. package/gsd-core/references/decimal-phase-calculation.md +64 -0
  242. package/gsd-core/references/doc-conflict-engine.md +91 -0
  243. package/gsd-core/references/domain-modeling.md +80 -0
  244. package/gsd-core/references/domain-probes.md +125 -0
  245. package/gsd-core/references/e2e-tiering.md +35 -0
  246. package/gsd-core/references/execute-mvp-tdd.md +81 -0
  247. package/gsd-core/references/executor-examples.md +110 -0
  248. package/gsd-core/references/few-shot-examples/plan-checker.md +73 -0
  249. package/gsd-core/references/few-shot-examples/verifier.md +109 -0
  250. package/gsd-core/references/flaky-test-checklist.md +22 -0
  251. package/gsd-core/references/gate-prompts.md +100 -0
  252. package/gsd-core/references/gates.md +70 -0
  253. package/gsd-core/references/git-integration.md +298 -0
  254. package/gsd-core/references/git-planning-commit.md +40 -0
  255. package/gsd-core/references/ios-scaffold.md +123 -0
  256. package/gsd-core/references/mandatory-initial-read.md +2 -0
  257. package/gsd-core/references/model-profile-resolution.md +38 -0
  258. package/gsd-core/references/model-profiles.md +245 -0
  259. package/gsd-core/references/mvp-concepts.md +49 -0
  260. package/gsd-core/references/phase-argument-parsing.md +61 -0
  261. package/gsd-core/references/planner-antipatterns.md +89 -0
  262. package/gsd-core/references/planner-chunked.md +49 -0
  263. package/gsd-core/references/planner-gap-closure.md +62 -0
  264. package/gsd-core/references/planner-graphify-auto-update.md +67 -0
  265. package/gsd-core/references/planner-human-verify-mode.md +57 -0
  266. package/gsd-core/references/planner-interface-context.md +62 -0
  267. package/gsd-core/references/planner-load-graph-context.md +36 -0
  268. package/gsd-core/references/planner-mvp-mode.md +53 -0
  269. package/gsd-core/references/planner-reviews.md +39 -0
  270. package/gsd-core/references/planner-revision.md +87 -0
  271. package/gsd-core/references/planner-source-audit.md +73 -0
  272. package/gsd-core/references/planning-config.md +473 -0
  273. package/gsd-core/references/product-discovery.md +49 -0
  274. package/gsd-core/references/project-skills-discovery.md +19 -0
  275. package/gsd-core/references/questioning.md +162 -0
  276. package/gsd-core/references/realistic-test-data.md +44 -0
  277. package/gsd-core/references/research-documentation-lookup.md +29 -0
  278. package/gsd-core/references/research-philosophy.md +29 -0
  279. package/gsd-core/references/research-verification-protocol.md +27 -0
  280. package/gsd-core/references/revision-loop.md +97 -0
  281. package/gsd-core/references/scout-codebase.md +51 -0
  282. package/gsd-core/references/skeleton-template.md +48 -0
  283. package/gsd-core/references/sketch-interactivity.md +41 -0
  284. package/gsd-core/references/sketch-theme-system.md +94 -0
  285. package/gsd-core/references/sketch-tooling.md +45 -0
  286. package/gsd-core/references/sketch-variant-patterns.md +81 -0
  287. package/gsd-core/references/spidr-splitting.md +69 -0
  288. package/gsd-core/references/tdd.md +330 -0
  289. package/gsd-core/references/test-containers.md +55 -0
  290. package/gsd-core/references/test-strategy.md +75 -0
  291. package/gsd-core/references/thinking-models-debug.md +44 -0
  292. package/gsd-core/references/thinking-models-execution.md +50 -0
  293. package/gsd-core/references/thinking-models-planning.md +62 -0
  294. package/gsd-core/references/thinking-models-research.md +50 -0
  295. package/gsd-core/references/thinking-models-verification.md +55 -0
  296. package/gsd-core/references/thinking-partner.md +96 -0
  297. package/gsd-core/references/ui-brand.md +162 -0
  298. package/gsd-core/references/universal-anti-patterns.md +63 -0
  299. package/gsd-core/references/user-profiling.md +681 -0
  300. package/gsd-core/references/user-story-template.md +58 -0
  301. package/gsd-core/references/verification-overrides.md +227 -0
  302. package/gsd-core/references/verification-patterns.md +612 -0
  303. package/gsd-core/references/verify-mvp-mode.md +85 -0
  304. package/gsd-core/references/workstream-flag.md +111 -0
  305. package/gsd-core/references/worktree-branch-check.md +38 -0
  306. package/gsd-core/references/worktree-path-safety.md +67 -0
  307. package/gsd-core/templates/AI-SPEC.md +246 -0
  308. package/gsd-core/templates/DEBUG.md +169 -0
  309. package/gsd-core/templates/README.md +77 -0
  310. package/gsd-core/templates/SECURITY.md +61 -0
  311. package/gsd-core/templates/UAT.md +265 -0
  312. package/gsd-core/templates/UI-SPEC.md +100 -0
  313. package/gsd-core/templates/VALIDATION.md +76 -0
  314. package/gsd-core/templates/adr.md +58 -0
  315. package/gsd-core/templates/claude-md.md +145 -0
  316. package/gsd-core/templates/codebase/architecture.md +255 -0
  317. package/gsd-core/templates/codebase/concerns.md +310 -0
  318. package/gsd-core/templates/codebase/conventions.md +307 -0
  319. package/gsd-core/templates/codebase/integrations.md +280 -0
  320. package/gsd-core/templates/codebase/stack.md +186 -0
  321. package/gsd-core/templates/codebase/structure.md +285 -0
  322. package/gsd-core/templates/codebase/testing.md +480 -0
  323. package/gsd-core/templates/config.json +62 -0
  324. package/gsd-core/templates/context.md +352 -0
  325. package/gsd-core/templates/continue-here.md +78 -0
  326. package/gsd-core/templates/copilot-instructions.md +7 -0
  327. package/gsd-core/templates/debug-subagent-prompt.md +91 -0
  328. package/gsd-core/templates/dev-preferences.md +21 -0
  329. package/gsd-core/templates/discovery.md +146 -0
  330. package/gsd-core/templates/discussion-log.md +63 -0
  331. package/gsd-core/templates/domain-model.md +54 -0
  332. package/gsd-core/templates/milestone-archive.md +123 -0
  333. package/gsd-core/templates/milestone.md +115 -0
  334. package/gsd-core/templates/phase-prompt.md +610 -0
  335. package/gsd-core/templates/planner-subagent-prompt.md +117 -0
  336. package/gsd-core/templates/product-brief.md +55 -0
  337. package/gsd-core/templates/project.md +186 -0
  338. package/gsd-core/templates/requirements.md +231 -0
  339. package/gsd-core/templates/research-project/ARCHITECTURE.md +204 -0
  340. package/gsd-core/templates/research-project/FEATURES.md +147 -0
  341. package/gsd-core/templates/research-project/PITFALLS.md +200 -0
  342. package/gsd-core/templates/research-project/STACK.md +120 -0
  343. package/gsd-core/templates/research-project/SUMMARY.md +170 -0
  344. package/gsd-core/templates/research.md +592 -0
  345. package/gsd-core/templates/retrospective.md +54 -0
  346. package/gsd-core/templates/roadmap.md +202 -0
  347. package/gsd-core/templates/spec.md +307 -0
  348. package/gsd-core/templates/state.md +195 -0
  349. package/gsd-core/templates/summary-complex.md +59 -0
  350. package/gsd-core/templates/summary-minimal.md +41 -0
  351. package/gsd-core/templates/summary-standard.md +48 -0
  352. package/gsd-core/templates/summary.md +248 -0
  353. package/gsd-core/templates/test-strategy.md +50 -0
  354. package/gsd-core/templates/user-profile.md +146 -0
  355. package/gsd-core/templates/user-setup.md +311 -0
  356. package/gsd-core/templates/verification-report.md +322 -0
  357. package/gsd-core/workflows/_runtime-launcher.snippet.sh +1 -0
  358. package/gsd-core/workflows/add-backlog.md +91 -0
  359. package/gsd-core/workflows/add-phase.md +113 -0
  360. package/gsd-core/workflows/add-tests.md +355 -0
  361. package/gsd-core/workflows/add-todo.md +161 -0
  362. package/gsd-core/workflows/ai-integration-phase.md +295 -0
  363. package/gsd-core/workflows/analyze-dependencies.md +96 -0
  364. package/gsd-core/workflows/audit-fix.md +178 -0
  365. package/gsd-core/workflows/audit-milestone.md +360 -0
  366. package/gsd-core/workflows/audit-uat.md +110 -0
  367. package/gsd-core/workflows/autonomous.md +797 -0
  368. package/gsd-core/workflows/check-todos.md +180 -0
  369. package/gsd-core/workflows/cleanup.md +195 -0
  370. package/gsd-core/workflows/code-review-fix.md +502 -0
  371. package/gsd-core/workflows/code-review.md +658 -0
  372. package/gsd-core/workflows/complete-milestone.md +855 -0
  373. package/gsd-core/workflows/debug.md +237 -0
  374. package/gsd-core/workflows/diagnose-issues.md +245 -0
  375. package/gsd-core/workflows/discover-product.md +112 -0
  376. package/gsd-core/workflows/discovery-phase.md +291 -0
  377. package/gsd-core/workflows/discuss-phase/modes/advisor.md +176 -0
  378. package/gsd-core/workflows/discuss-phase/modes/all.md +28 -0
  379. package/gsd-core/workflows/discuss-phase/modes/analyze.md +44 -0
  380. package/gsd-core/workflows/discuss-phase/modes/auto.md +57 -0
  381. package/gsd-core/workflows/discuss-phase/modes/batch.md +52 -0
  382. package/gsd-core/workflows/discuss-phase/modes/chain.md +98 -0
  383. package/gsd-core/workflows/discuss-phase/modes/default.md +141 -0
  384. package/gsd-core/workflows/discuss-phase/modes/power.md +44 -0
  385. package/gsd-core/workflows/discuss-phase/modes/text.md +55 -0
  386. package/gsd-core/workflows/discuss-phase/templates/checkpoint.json +18 -0
  387. package/gsd-core/workflows/discuss-phase/templates/context.md +136 -0
  388. package/gsd-core/workflows/discuss-phase/templates/discussion-log.md +50 -0
  389. package/gsd-core/workflows/discuss-phase-assumptions.md +675 -0
  390. package/gsd-core/workflows/discuss-phase-power.md +291 -0
  391. package/gsd-core/workflows/discuss-phase.md +499 -0
  392. package/gsd-core/workflows/do.md +111 -0
  393. package/gsd-core/workflows/docs-update.md +1176 -0
  394. package/gsd-core/workflows/edit-phase.md +295 -0
  395. package/gsd-core/workflows/eval-review.md +156 -0
  396. package/gsd-core/workflows/execute-phase/steps/codebase-drift-gate.md +95 -0
  397. package/gsd-core/workflows/execute-phase/steps/per-plan-worktree-gate.md +94 -0
  398. package/gsd-core/workflows/execute-phase/steps/post-merge-gate.md +117 -0
  399. package/gsd-core/workflows/execute-phase.md +1752 -0
  400. package/gsd-core/workflows/execute-plan.md +526 -0
  401. package/gsd-core/workflows/explore.md +146 -0
  402. package/gsd-core/workflows/extract-learnings.md +243 -0
  403. package/gsd-core/workflows/fast.md +124 -0
  404. package/gsd-core/workflows/forensics.md +279 -0
  405. package/gsd-core/workflows/graduation.md +196 -0
  406. package/gsd-core/workflows/health.md +224 -0
  407. package/gsd-core/workflows/help/modes/brief.md +22 -0
  408. package/gsd-core/workflows/help/modes/default.md +50 -0
  409. package/gsd-core/workflows/help/modes/full.md +789 -0
  410. package/gsd-core/workflows/help/modes/topic.md +74 -0
  411. package/gsd-core/workflows/help.md +24 -0
  412. package/gsd-core/workflows/import.md +256 -0
  413. package/gsd-core/workflows/inbox.md +387 -0
  414. package/gsd-core/workflows/ingest-docs.md +340 -0
  415. package/gsd-core/workflows/insert-phase.md +152 -0
  416. package/gsd-core/workflows/list-phase-assumptions.md +178 -0
  417. package/gsd-core/workflows/list-workspaces.md +57 -0
  418. package/gsd-core/workflows/manager.md +393 -0
  419. package/gsd-core/workflows/map-codebase.md +446 -0
  420. package/gsd-core/workflows/milestone-summary.md +224 -0
  421. package/gsd-core/workflows/model-domain.md +162 -0
  422. package/gsd-core/workflows/mvp-phase.md +222 -0
  423. package/gsd-core/workflows/new-milestone.md +635 -0
  424. package/gsd-core/workflows/new-project.md +1555 -0
  425. package/gsd-core/workflows/new-workspace.md +240 -0
  426. package/gsd-core/workflows/next.md +299 -0
  427. package/gsd-core/workflows/node-repair.md +92 -0
  428. package/gsd-core/workflows/note.md +158 -0
  429. package/gsd-core/workflows/pause-work.md +244 -0
  430. package/gsd-core/workflows/plan-milestone-gaps.md +281 -0
  431. package/gsd-core/workflows/plan-phase.md +1814 -0
  432. package/gsd-core/workflows/plan-review-convergence.md +346 -0
  433. package/gsd-core/workflows/plant-seed.md +230 -0
  434. package/gsd-core/workflows/pr-branch.md +157 -0
  435. package/gsd-core/workflows/profile-user.md +453 -0
  436. package/gsd-core/workflows/progress.md +699 -0
  437. package/gsd-core/workflows/quick.md +1017 -0
  438. package/gsd-core/workflows/reapply-patches.md +426 -0
  439. package/gsd-core/workflows/recommend-architecture.md +135 -0
  440. package/gsd-core/workflows/remove-phase.md +156 -0
  441. package/gsd-core/workflows/remove-workspace.md +108 -0
  442. package/gsd-core/workflows/resume-project.md +332 -0
  443. package/gsd-core/workflows/review.md +748 -0
  444. package/gsd-core/workflows/scan.md +107 -0
  445. package/gsd-core/workflows/secure-phase.md +182 -0
  446. package/gsd-core/workflows/session-report.md +146 -0
  447. package/gsd-core/workflows/settings-advanced.md +810 -0
  448. package/gsd-core/workflows/settings-integrations.md +312 -0
  449. package/gsd-core/workflows/settings.md +566 -0
  450. package/gsd-core/workflows/ship.md +405 -0
  451. package/gsd-core/workflows/sketch-wrap-up.md +286 -0
  452. package/gsd-core/workflows/sketch.md +361 -0
  453. package/gsd-core/workflows/spec-phase.md +263 -0
  454. package/gsd-core/workflows/spike-wrap-up.md +307 -0
  455. package/gsd-core/workflows/spike.md +453 -0
  456. package/gsd-core/workflows/stats.md +80 -0
  457. package/gsd-core/workflows/sync-skills.md +182 -0
  458. package/gsd-core/workflows/testing-strategy.md +122 -0
  459. package/gsd-core/workflows/thread.md +222 -0
  460. package/gsd-core/workflows/transition.md +694 -0
  461. package/gsd-core/workflows/ui-phase.md +328 -0
  462. package/gsd-core/workflows/ui-review.md +193 -0
  463. package/gsd-core/workflows/ultraplan-phase.md +199 -0
  464. package/gsd-core/workflows/undo.md +314 -0
  465. package/gsd-core/workflows/update.md +496 -0
  466. package/gsd-core/workflows/validate-phase.md +181 -0
  467. package/gsd-core/workflows/verify-phase.md +544 -0
  468. package/gsd-core/workflows/verify-work.md +781 -0
  469. package/hooks/dist/gsd-check-update-worker.js +108 -0
  470. package/hooks/dist/gsd-check-update.js +66 -0
  471. package/hooks/dist/gsd-config-reload.js +133 -0
  472. package/hooks/dist/gsd-context-monitor.js +195 -0
  473. package/hooks/dist/gsd-cursor-post-tool.js +75 -0
  474. package/hooks/dist/gsd-cursor-session-start.js +52 -0
  475. package/hooks/dist/gsd-graphify-update.sh +158 -0
  476. package/hooks/dist/gsd-phase-boundary.sh +47 -0
  477. package/hooks/dist/gsd-prompt-guard.js +97 -0
  478. package/hooks/dist/gsd-read-guard.js +101 -0
  479. package/hooks/dist/gsd-read-injection-scanner.js +203 -0
  480. package/hooks/dist/gsd-session-state.sh +59 -0
  481. package/hooks/dist/gsd-statusline.js +566 -0
  482. package/hooks/dist/gsd-update-banner.js +138 -0
  483. package/hooks/dist/gsd-validate-commit.sh +57 -0
  484. package/hooks/dist/gsd-workflow-guard.js +167 -0
  485. package/hooks/dist/gsd-worktree-path-guard.js +169 -0
  486. package/hooks/dist/lib/git-cmd.js +150 -0
  487. package/hooks/dist/lib/gsd-graphify-rebuild.sh +65 -0
  488. package/hooks/dist/managed-hooks-registry.cjs +38 -0
  489. package/hooks/gsd-check-update-worker.js +108 -0
  490. package/hooks/gsd-check-update.js +66 -0
  491. package/hooks/gsd-config-reload.js +133 -0
  492. package/hooks/gsd-context-monitor.js +195 -0
  493. package/hooks/gsd-cursor-post-tool.js +75 -0
  494. package/hooks/gsd-cursor-session-start.js +52 -0
  495. package/hooks/gsd-graphify-update.sh +158 -0
  496. package/hooks/gsd-phase-boundary.sh +47 -0
  497. package/hooks/gsd-prompt-guard.js +97 -0
  498. package/hooks/gsd-read-guard.js +101 -0
  499. package/hooks/gsd-read-injection-scanner.js +203 -0
  500. package/hooks/gsd-session-state.sh +59 -0
  501. package/hooks/gsd-statusline.js +566 -0
  502. package/hooks/gsd-update-banner.js +138 -0
  503. package/hooks/gsd-validate-commit.sh +57 -0
  504. package/hooks/gsd-workflow-guard.js +167 -0
  505. package/hooks/gsd-worktree-path-guard.js +169 -0
  506. package/hooks/hooks.json +69 -0
  507. package/hooks/lib/git-cmd.js +150 -0
  508. package/hooks/lib/gsd-graphify-rebuild.sh +65 -0
  509. package/hooks/managed-hooks-registry.cjs +38 -0
  510. package/package.json +115 -0
  511. package/scripts/affected-tests-lib.cjs +542 -0
  512. package/scripts/audit-workflow-script-paths.cjs +73 -0
  513. package/scripts/base64-scan.sh +351 -0
  514. package/scripts/build-hooks.js +247 -0
  515. package/scripts/changeset/README.md +129 -0
  516. package/scripts/changeset/cli.cjs +590 -0
  517. package/scripts/changeset/github-release-notes.cjs +199 -0
  518. package/scripts/changeset/lint.cjs +111 -0
  519. package/scripts/changeset/new.cjs +137 -0
  520. package/scripts/changeset/parse.cjs +114 -0
  521. package/scripts/changeset/render.cjs +34 -0
  522. package/scripts/changeset/serialize.cjs +130 -0
  523. package/scripts/check-alias-drift.cjs +114 -0
  524. package/scripts/check-env.cjs +312 -0
  525. package/scripts/check-npm-integrity.cjs +215 -0
  526. package/scripts/ci-guard-runner.cjs +22 -0
  527. package/scripts/ci-prepare-test-scope.cjs +51 -0
  528. package/scripts/ci-rebase-check.cjs +86 -0
  529. package/scripts/ci-test-scope.cjs +431 -0
  530. package/scripts/command-contract-helpers.cjs +64 -0
  531. package/scripts/diff-touches-shipped-paths.cjs +155 -0
  532. package/scripts/fix-slash-commands.cjs +147 -0
  533. package/scripts/gen-inventory-manifest.cjs +115 -0
  534. package/scripts/gen-research-agents.cjs +276 -0
  535. package/scripts/generate-package-identity.cjs +125 -0
  536. package/scripts/issue-dedupe.cjs +278 -0
  537. package/scripts/lib/allowlist-ratchet.cjs +136 -0
  538. package/scripts/lib/cli-exit.cjs +56 -0
  539. package/scripts/lint-command-contract.cjs +114 -0
  540. package/scripts/lint-descriptions.cjs +87 -0
  541. package/scripts/lint-docs-required.cjs +222 -0
  542. package/scripts/lint-legacy-dir-name.cjs +160 -0
  543. package/scripts/lint-package-identity-drift.cjs +141 -0
  544. package/scripts/lint-pr-check-project-dir.cjs +99 -0
  545. package/scripts/lint-shell-command-projection-drift.cjs +62 -0
  546. package/scripts/lint-skill-deps.cjs +185 -0
  547. package/scripts/lint-test-file-count.allowlist.json +135 -0
  548. package/scripts/lint-test-file-count.cjs +246 -0
  549. package/scripts/mutation-matrix.cjs +222 -0
  550. package/scripts/pr-template-policy.cjs +268 -0
  551. package/scripts/prompt-injection-scan.sh +207 -0
  552. package/scripts/release-notes/discord-release-summary.cjs +373 -0
  553. package/scripts/release-notes/format-github-release-notes.cjs +261 -0
  554. package/scripts/release-tarball-smoke.cjs +629 -0
  555. package/scripts/research-profiles.cjs +149 -0
  556. package/scripts/run-affected-tests.cjs +7 -0
  557. package/scripts/run-cross-platform-tests.cjs +67 -0
  558. package/scripts/run-tests.cjs +315 -0
  559. package/scripts/secret-scan-lint.sh +231 -0
  560. package/scripts/secret-scan.sh +358 -0
  561. package/scripts/setup-branch-protection.sh +236 -0
  562. package/scripts/strip-prose-atrefs.cjs +106 -0
  563. package/scripts/sync-manifest-versions.cjs +119 -0
  564. package/scripts/sync-rulesets.sh +34 -0
  565. package/scripts/sync-runtime-launcher.cjs +399 -0
  566. package/scripts/test-failure-reasons.cjs +34 -0
  567. package/scripts/verify-npm-publish.cjs +240 -0
  568. package/scripts/workflow-policy.cjs +450 -0
@@ -0,0 +1,480 @@
1
+ "use strict";
2
+ /**
3
+ * Security — Input validation, path traversal prevention, and prompt injection guards
4
+ *
5
+ * This module centralizes security checks for GSD tooling. Because GSD generates
6
+ * markdown files that become LLM system prompts (agent instructions, workflow state,
7
+ * phase plans), any user-controlled text that flows into these files is a potential
8
+ * indirect prompt injection vector.
9
+ *
10
+ * Threat model:
11
+ * 1. Path traversal: user-supplied file paths escape the project directory
12
+ * 2. Prompt injection: malicious text in arguments/PRDs embeds LLM instructions
13
+ * 3. Shell metacharacter injection: user text interpreted by shell
14
+ * 4. JSON injection: malformed JSON crashes or corrupts state
15
+ * 5. Regex DoS: crafted input causes catastrophic backtracking
16
+ *
17
+ * ADR-457 build-at-publish: the hand-written bin/lib/security.cjs collapsed
18
+ * to a TypeScript source of truth. Behaviour is preserved byte-for-behaviour
19
+ * from the prior hand-written .cjs; only types are added.
20
+ */
21
+ var __importDefault = (this && this.__importDefault) || function (mod) {
22
+ return (mod && mod.__esModule) ? mod : { "default": mod };
23
+ };
24
+ Object.defineProperty(exports, "__esModule", { value: true });
25
+ exports.MARKDOWN_LINK_PATTERNS = exports.INJECTION_PATTERNS = void 0;
26
+ exports.validatePath = validatePath;
27
+ exports.loadTrustedGlobalRoots = loadTrustedGlobalRoots;
28
+ exports.requireSafePath = requireSafePath;
29
+ exports.scanForInjection = scanForInjection;
30
+ exports.sanitizeForPrompt = sanitizeForPrompt;
31
+ exports.sanitizeForDisplay = sanitizeForDisplay;
32
+ exports.validateShellArg = validateShellArg;
33
+ exports.safeJsonParse = safeJsonParse;
34
+ exports.validatePhaseNumber = validatePhaseNumber;
35
+ exports.validateFieldName = validateFieldName;
36
+ exports.validatePromptStructure = validatePromptStructure;
37
+ exports.scanEntropyAnomalies = scanEntropyAnomalies;
38
+ const node_fs_1 = __importDefault(require("node:fs"));
39
+ const node_os_1 = __importDefault(require("node:os"));
40
+ const node_path_1 = __importDefault(require("node:path"));
41
+ // ─── Path Traversal Prevention ──────────────────────────────────────────────
42
+ /**
43
+ * Validate that a file path resolves within an allowed base directory.
44
+ * Prevents path traversal attacks via ../ sequences, symlinks, or absolute paths.
45
+ */
46
+ function validatePath(filePath, baseDir, opts = {}) {
47
+ if (!filePath || typeof filePath !== 'string') {
48
+ return { safe: false, resolved: '', error: 'Empty or invalid file path' };
49
+ }
50
+ if (!baseDir || typeof baseDir !== 'string') {
51
+ return { safe: false, resolved: '', error: 'Empty or invalid base directory' };
52
+ }
53
+ if (filePath.includes('\0')) {
54
+ return { safe: false, resolved: '', error: 'Path contains null bytes' };
55
+ }
56
+ let resolvedBase;
57
+ try {
58
+ resolvedBase = node_fs_1.default.realpathSync(node_path_1.default.resolve(baseDir));
59
+ }
60
+ catch {
61
+ resolvedBase = node_path_1.default.resolve(baseDir);
62
+ }
63
+ let resolvedPath;
64
+ if (node_path_1.default.isAbsolute(filePath)) {
65
+ if (!opts.allowAbsolute) {
66
+ return { safe: false, resolved: '', error: 'Absolute paths not allowed' };
67
+ }
68
+ resolvedPath = node_path_1.default.resolve(filePath);
69
+ }
70
+ else {
71
+ resolvedPath = node_path_1.default.resolve(baseDir, filePath);
72
+ }
73
+ try {
74
+ resolvedPath = node_fs_1.default.realpathSync(resolvedPath);
75
+ }
76
+ catch {
77
+ const parentDir = node_path_1.default.dirname(resolvedPath);
78
+ try {
79
+ const realParent = node_fs_1.default.realpathSync(parentDir);
80
+ resolvedPath = node_path_1.default.join(realParent, node_path_1.default.basename(resolvedPath));
81
+ }
82
+ catch {
83
+ // Parent doesn't exist either — keep the resolved path as-is
84
+ }
85
+ }
86
+ const normalizedBase = resolvedBase + node_path_1.default.sep;
87
+ const normalizedPath = resolvedPath + node_path_1.default.sep;
88
+ if (resolvedPath !== resolvedBase && !normalizedPath.startsWith(normalizedBase)) {
89
+ return {
90
+ safe: false,
91
+ resolved: resolvedPath,
92
+ error: `Path escapes allowed directory: ${resolvedPath} is outside ${resolvedBase}`,
93
+ };
94
+ }
95
+ return { safe: true, resolved: resolvedPath };
96
+ }
97
+ /**
98
+ * Load the opt-in trusted global roots allowlist from config.
99
+ *
100
+ * Reads `config.agent_skills_security.trusted_global_roots` (an array of
101
+ * path strings). Each entry is canonicalized via realpathSync: non-strings
102
+ * are dropped, leading `~/` is expanded to `os.homedir()`, entries that are
103
+ * not absolute after expansion are dropped (project-relative paths are
104
+ * rejected as a security boundary), and entries that do not exist on disk are
105
+ * dropped (a non-existent root is not trustworthy). The canonical realpath is
106
+ * used for all subsequent checks and as the stored value — this closes the
107
+ * case-insensitive bypass on macOS APFS (`/users/alice` vs `/Users/alice`)
108
+ * and ensures trust doesn't drift across re-invocations if a root is
109
+ * re-created at a different target. Results are de-duplicated by canonical path.
110
+ */
111
+ function loadTrustedGlobalRoots(config) {
112
+ const roots = config?.['agent_skills_security'];
113
+ const raw = roots?.['trusted_global_roots'];
114
+ if (!Array.isArray(raw))
115
+ return [];
116
+ // Compute canonical homedir once for case-insensitive-safe comparison.
117
+ let realHome;
118
+ try {
119
+ realHome = node_fs_1.default.realpathSync(node_os_1.default.homedir());
120
+ }
121
+ catch {
122
+ realHome = node_os_1.default.homedir();
123
+ }
124
+ const seen = new Set();
125
+ const result = [];
126
+ for (const entry of raw) {
127
+ if (typeof entry !== 'string')
128
+ continue;
129
+ let expanded;
130
+ if (entry === '~') {
131
+ expanded = node_os_1.default.homedir();
132
+ }
133
+ else if (entry.startsWith('~/')) {
134
+ expanded = node_path_1.default.join(node_os_1.default.homedir(), entry.slice(2));
135
+ }
136
+ else {
137
+ expanded = entry;
138
+ }
139
+ if (!node_path_1.default.isAbsolute(expanded))
140
+ continue; // reject project-relative
141
+ // Canonicalize: resolve symlinks and normalise case. If the path doesn't
142
+ // exist or can't be read, skip it — a non-existent root is not trustworthy.
143
+ let real;
144
+ try {
145
+ real = node_fs_1.default.realpathSync(expanded);
146
+ }
147
+ catch {
148
+ continue; // non-existent or unreadable — skip
149
+ }
150
+ // Reject dangerously broad roots: filesystem root (e.g. '/' or 'C:\' or UNC '\\server\share').
151
+ // Normalize both sides by stripping trailing path separators before comparing so that
152
+ // Windows UNC shares (where path.parse().root includes a trailing separator) are caught.
153
+ const stripTrailingSep = (p) => p.replace(/[\\/]+$/, '');
154
+ if (stripTrailingSep(node_path_1.default.parse(real).root) === stripTrailingSep(real))
155
+ continue;
156
+ // Reject homedir itself (canonical compare closes case-insensitive bypass).
157
+ // Apply stripTrailingSep for robustness on platforms where realpathSync may
158
+ // or may not include a trailing separator on the homedir path.
159
+ if (stripTrailingSep(real) === stripTrailingSep(realHome))
160
+ continue;
161
+ if (seen.has(real))
162
+ continue;
163
+ seen.add(real);
164
+ result.push(real);
165
+ }
166
+ return result;
167
+ }
168
+ /**
169
+ * Validate a file path and throw on traversal attempt.
170
+ * Convenience wrapper around validatePath for use in CLI commands.
171
+ */
172
+ function requireSafePath(filePath, baseDir, label, opts = {}) {
173
+ const result = validatePath(filePath, baseDir, opts);
174
+ if (!result.safe) {
175
+ throw new Error(`${label || 'Path'} validation failed: ${result.error}`);
176
+ }
177
+ return result.resolved;
178
+ }
179
+ // ─── Prompt Injection Detection ────────────────────────────────────────────────────
180
+ /**
181
+ * Patterns that indicate prompt injection attempts in user-supplied text.
182
+ * These patterns catch common indirect prompt injection techniques where
183
+ * an attacker embeds LLM instructions in text that will be read by an agent.
184
+ *
185
+ * Note: This is defense-in-depth — not a complete solution. The primary defense
186
+ * is proper input/output boundaries in agent prompts.
187
+ */
188
+ exports.INJECTION_PATTERNS = [
189
+ // Direct instruction override attempts
190
+ /ignore\s+(all\s+)?previous\s+instructions/i,
191
+ /ignore\s+(all\s+)?above\s+instructions/i,
192
+ /disregard\s+(all\s+)?previous/i,
193
+ /forget\s+(all\s+)?(your\s+)?instructions/i,
194
+ /override\s+(system|previous)\s+(prompt|instructions)/i,
195
+ // Role/identity manipulation
196
+ /you\s+are\s+now\s+(?:a|an|the)\s+/i,
197
+ /act\s+as\s+(?:a|an|the)\s+(?!plan|phase|wave)/i,
198
+ /pretend\s+(?:you(?:'re| are)\s+|to\s+be\s+)/i,
199
+ /from\s+now\s+on,?\s+you\s+(?:are|will|should|must)/i,
200
+ // System prompt extraction
201
+ /(?:print|output|reveal|show|display|repeat)\s+(?:your\s+)?(?:system\s+)?(?:prompt|instructions)/i,
202
+ /what\s+(?:are|is)\s+your\s+(?:system\s+)?(?:prompt|instructions)/i,
203
+ // Hidden instruction markers (XML/HTML tags that mimic system messages)
204
+ // Note: <instructions> is excluded — GSD uses it as legitimate prompt structure
205
+ // Requires > to close the tag (not just whitespace) to avoid matching generic types like Promise<User | null>
206
+ /<\/?(?:system|assistant|human)>/i,
207
+ /\[SYSTEM\]/i,
208
+ /\[\/?(INST)\]/i,
209
+ /<<\s*SYS\s*>>/i,
210
+ // Exfiltration attempts
211
+ /(?:send|post|fetch|curl|wget)\s+(?:to|from)\s+https?:\/\//i,
212
+ /(?:base64|btoa|encode)\s+(?:and\s+)?(?:send|exfiltrate|output)/i,
213
+ // Tool manipulation
214
+ /(?:run|execute|call|invoke)\s+(?:the\s+)?(?:bash|shell|exec|spawn)\s+(?:tool|command)/i,
215
+ ];
216
+ // Explicit safe-list for data: MIME types that are benign in link targets.
217
+ // Note: image/svg+xml is intentionally NOT in this list (SVG can host <script>).
218
+ const DATA_URI_SAFE_MIME_RE = /^data:(image\/(png|jpe?g|gif|webp|bmp|ico|avif|heic)|font\/(woff2?|otf|ttf))(;[^,]*)?,/i;
219
+ exports.MARKDOWN_LINK_PATTERNS = [
220
+ {
221
+ pattern: /\]\(\s*javascript:/i,
222
+ ruleId: 'MD-LINK-JS-SCHEME',
223
+ },
224
+ {
225
+ pattern: /\]\(\s*data:/i,
226
+ ruleId: 'MD-LINK-DATA-SCHEME',
227
+ safePredicate: (line) => {
228
+ const m = line.match(/\]\(\s*(data:[^)]*)/i);
229
+ if (!m)
230
+ return false;
231
+ return DATA_URI_SAFE_MIME_RE.test(m[1]);
232
+ },
233
+ },
234
+ {
235
+ pattern: /\]\(\s*https?:\/\/[^/\s]+:[^/@\s]+@/i,
236
+ ruleId: 'MD-LINK-USERINFO',
237
+ },
238
+ {
239
+ pattern: /[?&](token|access_token|id_token|refresh_token|api_key|apikey|secret|password|client_secret|code)=/i,
240
+ ruleId: 'MD-LINK-TOKEN-IN-QUERY',
241
+ },
242
+ ];
243
+ const OBFUSCATION_PATTERN_ENTRIES = [
244
+ {
245
+ pattern: /\b(\w\s){4,}\w\b/,
246
+ message: 'Character-spacing obfuscation pattern detected (e.g. "i g n o r e")',
247
+ },
248
+ {
249
+ pattern: /<\/?(system|human|assistant|user)\s*>/i,
250
+ message: 'Delimiter injection pattern: <system>/<human>/<assistant>/<user> tag detected',
251
+ },
252
+ {
253
+ pattern: /0x[0-9a-fA-F]{16,}/,
254
+ message: 'Long hex sequence detected — possible encoded payload',
255
+ },
256
+ ];
257
+ /**
258
+ * Scan text for potential prompt injection patterns.
259
+ * Returns an array of findings (empty = clean).
260
+ */
261
+ function scanForInjection(text, opts = {}) {
262
+ if (!text || typeof text !== 'string') {
263
+ return { clean: true, findings: [], structuredFindings: [] };
264
+ }
265
+ const findings = [];
266
+ const structuredFindings = [];
267
+ for (const pattern of exports.INJECTION_PATTERNS) {
268
+ if (pattern.test(text)) {
269
+ findings.push(`Matched injection pattern: ${pattern.source}`);
270
+ }
271
+ }
272
+ for (const entry of OBFUSCATION_PATTERN_ENTRIES) {
273
+ if (entry.pattern.test(text)) {
274
+ findings.push(entry.message);
275
+ }
276
+ }
277
+ const lines = text.split('\n');
278
+ for (const entry of exports.MARKDOWN_LINK_PATTERNS) {
279
+ for (let i = 0; i < lines.length; i++) {
280
+ const line = lines[i];
281
+ const m = line.match(entry.pattern);
282
+ if (!m)
283
+ continue;
284
+ if (entry.safePredicate && entry.safePredicate(line))
285
+ continue;
286
+ const matchText = m[0];
287
+ findings.push(`Matched markdown link pattern [${entry.ruleId}]: ${matchText}`);
288
+ structuredFindings.push({
289
+ ruleId: entry.ruleId,
290
+ file: opts.file,
291
+ line: i + 1,
292
+ match: matchText,
293
+ });
294
+ }
295
+ }
296
+ if (opts.strict) {
297
+ // Check for suspicious Unicode that could hide instructions
298
+ // (zero-width chars, RTL override, homoglyph attacks)
299
+ if (/[\u200B-\u200F\u2028-\u202F\uFEFF\u00AD]/.test(text)) {
300
+ findings.push('Contains suspicious zero-width or invisible Unicode characters');
301
+ }
302
+ // Layer 1: Unicode tag block U+E0000–E007F (2025 supply-chain attack vector)
303
+ // These characters are invisible and can embed hidden instructions
304
+ if (/[\uDB40\uDC00-\uDB40\uDC7F]/u.test(text) || /[\u{E0000}-\u{E007F}]/u.test(text)) {
305
+ findings.push('Contains Unicode tag block characters (U+E0000–E007F) — invisible instruction injection vector');
306
+ }
307
+ // Check for extremely long strings that could be prompt stuffing.
308
+ // Normalize CRLF → LF before measuring so Windows checkouts don't inflate the count.
309
+ const normalizedLength = text.replace(/\r\n/g, '\n').replace(/\r/g, '\n').length;
310
+ if (normalizedLength > 50000) {
311
+ findings.push(`Suspicious text length: ${normalizedLength} chars (potential prompt stuffing)`);
312
+ }
313
+ }
314
+ return { clean: findings.length === 0, findings, structuredFindings };
315
+ }
316
+ /**
317
+ * Sanitize text that will be embedded in agent prompts or planning documents.
318
+ * Strips known injection markers while preserving legitimate content.
319
+ */
320
+ function sanitizeForPrompt(text) {
321
+ if (!text || typeof text !== 'string')
322
+ return text;
323
+ let sanitized = text;
324
+ // Strip zero-width characters that could hide instructions
325
+ sanitized = sanitized.replace(/[\u200B-\u200F\u2028-\u202F\uFEFF\u00AD]/g, '');
326
+ // Neutralize XML/HTML tags that mimic system boundaries
327
+ // Note: <instructions> is excluded — GSD uses it as legitimate prompt structure
328
+ sanitized = sanitized.replace(/<(\/?)\s*(?:system|assistant|human|user)\s*>/gi, (_, slash) => `<${slash || ''}system-text>`);
329
+ // Neutralize [SYSTEM] / [INST] / [/INST] markers
330
+ sanitized = sanitized.replace(/\[(\/?)(SYSTEM|INST)\]/gi, (_, slash, tag) => `[${slash}${tag.toUpperCase()}-TEXT]`);
331
+ // Neutralize <<SYS>> and <</SYS>> markers (Llama-style delimiters)
332
+ sanitized = sanitized.replace(/<<\/?\s*SYS\s*>>/gi, '«SYS-TEXT»');
333
+ return sanitized;
334
+ }
335
+ /**
336
+ * Sanitize text that will be displayed back to the user.
337
+ * Removes protocol-like leak markers that should never surface in checkpoints.
338
+ */
339
+ function sanitizeForDisplay(text) {
340
+ if (!text || typeof text !== 'string')
341
+ return text;
342
+ let sanitized = sanitizeForPrompt(text);
343
+ const protocolLeakPatterns = [
344
+ /^\s*(?:assistant|user|system)\s+to=[^:\s]+:[^\n]+$/i,
345
+ /^\s*<\|(?:assistant|user|system)[^|]*\|>\s*$/i,
346
+ ];
347
+ sanitized = sanitized
348
+ .split('\n')
349
+ .filter(line => !protocolLeakPatterns.some(pattern => pattern.test(line)))
350
+ .join('\n');
351
+ return sanitized;
352
+ }
353
+ // ─── Shell Safety ───────────────────────────────────────────────────────────────────────
354
+ /**
355
+ * Validate that a string is safe to use as a shell argument when quoted.
356
+ */
357
+ function validateShellArg(value, label) {
358
+ if (!value || typeof value !== 'string') {
359
+ throw new Error(`${label || 'Argument'}: empty or invalid value`);
360
+ }
361
+ if (value.includes('\0')) {
362
+ throw new Error(`${label || 'Argument'}: contains null bytes`);
363
+ }
364
+ if (/[$`]/.test(value) && /\$\(|`/.test(value)) {
365
+ throw new Error(`${label || 'Argument'}: contains potential command substitution`);
366
+ }
367
+ return value;
368
+ }
369
+ // ─── JSON Safety ──────────────────────────────────────────────────────────────────────────
370
+ /**
371
+ * Safely parse JSON with error handling and optional size limits.
372
+ */
373
+ function safeJsonParse(text, opts = {}) {
374
+ const maxLength = opts.maxLength || 1048576;
375
+ const label = opts.label || 'JSON';
376
+ if (!text || typeof text !== 'string') {
377
+ return { ok: false, error: `${label}: empty or invalid input` };
378
+ }
379
+ if (text.length > maxLength) {
380
+ return { ok: false, error: `${label}: input exceeds ${maxLength} byte limit (got ${text.length})` };
381
+ }
382
+ try {
383
+ const value = JSON.parse(text);
384
+ return { ok: true, value };
385
+ }
386
+ catch (err) {
387
+ const msg = err instanceof Error ? err.message : String(err);
388
+ return { ok: false, error: `${label}: parse error — ${msg}` };
389
+ }
390
+ }
391
+ // ─── Phase/Argument Validation ─────────────────────────────────────────────────────────
392
+ /**
393
+ * Validate a phase number argument.
394
+ */
395
+ function validatePhaseNumber(phase) {
396
+ if (!phase || typeof phase !== 'string') {
397
+ return { valid: false, error: 'Phase number is required' };
398
+ }
399
+ const trimmed = phase.trim();
400
+ if (/^\d{1,4}[A-Z]?(?:\.\d{1,3})*$/i.test(trimmed)) {
401
+ return { valid: true, normalized: trimmed };
402
+ }
403
+ if (/^[A-Z][A-Z0-9]*(?:-[A-Z0-9]+){1,4}$/i.test(trimmed) && trimmed.length <= 30) {
404
+ return { valid: true, normalized: trimmed };
405
+ }
406
+ return { valid: false, error: `Invalid phase number format: "${trimmed}"` };
407
+ }
408
+ /**
409
+ * Validate a STATE.md field name to prevent injection into regex patterns.
410
+ */
411
+ function validateFieldName(field) {
412
+ if (!field || typeof field !== 'string') {
413
+ return { valid: false, error: 'Field name is required' };
414
+ }
415
+ if (/^[A-Za-z][A-Za-z0-9 _.\-/]{0,60}$/.test(field)) {
416
+ return { valid: true };
417
+ }
418
+ return { valid: false, error: `Invalid field name: "${field}"` };
419
+ }
420
+ // ─── Layer 3: Structural Schema Validation ──────────────────────────────────────────────────────────────────────────
421
+ const KNOWN_VALID_TAGS = new Set([
422
+ 'objective', 'process', 'step', 'success_criteria', 'critical_rules',
423
+ 'available_agent_types', 'purpose', 'required_reading',
424
+ ]);
425
+ /**
426
+ * Validate the XML structure of a prompt file.
427
+ */
428
+ function validatePromptStructure(text, fileType) {
429
+ if (!text || typeof text !== 'string') {
430
+ return { valid: true, violations: [] };
431
+ }
432
+ if (fileType !== 'agent' && fileType !== 'workflow') {
433
+ return { valid: true, violations: [] };
434
+ }
435
+ const violations = [];
436
+ const tagRegex = /<([A-Za-z][A-Za-z0-9_-]*)/g;
437
+ let match;
438
+ while ((match = tagRegex.exec(text)) !== null) {
439
+ const tag = match[1].toLowerCase();
440
+ if (!KNOWN_VALID_TAGS.has(tag)) {
441
+ violations.push(`Unknown XML tag in ${fileType} file: <${tag}>`);
442
+ }
443
+ }
444
+ return { valid: violations.length === 0, violations };
445
+ }
446
+ // ─── Layer 4: Paragraph-Level Entropy Anomaly Detection ─────────────────────────────────────────────────────────────────────
447
+ function shannonEntropy(text) {
448
+ if (!text || text.length === 0)
449
+ return 0;
450
+ const freq = {};
451
+ for (const ch of text) {
452
+ freq[ch] = (freq[ch] || 0) + 1;
453
+ }
454
+ const len = text.length;
455
+ let entropy = 0;
456
+ for (const count of Object.values(freq)) {
457
+ const p = count / len;
458
+ entropy -= p * Math.log2(p);
459
+ }
460
+ return entropy;
461
+ }
462
+ /**
463
+ * Scan text for paragraphs with anomalously high Shannon entropy.
464
+ */
465
+ function scanEntropyAnomalies(text) {
466
+ if (!text || typeof text !== 'string') {
467
+ return { clean: true, findings: [] };
468
+ }
469
+ const findings = [];
470
+ const paragraphs = text.split(/\n\n+/);
471
+ for (const para of paragraphs) {
472
+ if (para.length <= 50)
473
+ continue;
474
+ const entropy = shannonEntropy(para);
475
+ if (entropy > 5.5) {
476
+ findings.push(`High-entropy paragraph detected (${entropy.toFixed(2)} bits/char) — possible encoded payload`);
477
+ }
478
+ }
479
+ return { clean: findings.length === 0, findings };
480
+ }
@@ -0,0 +1,42 @@
1
+ "use strict";
2
+ /**
3
+ * Shared semver comparison utility (ADR-457 pilot: first hand-written
4
+ * bin/lib/*.cjs collapsed to a TypeScript source of truth).
5
+ *
6
+ * Logic is preserved byte-for-behaviour from the prior hand-written
7
+ * `gsd-core/bin/lib/semver-compare.cjs`; only types are added. The
8
+ * normalization policy here is locked by `tests/semver-compare.test.cjs` and
9
+ * consumed by update-check, statusline dev-install detection, and changeset
10
+ * range compare (`scripts/changeset/cli.cjs`).
11
+ */
12
+ Object.defineProperty(exports, "__esModule", { value: true });
13
+ exports.toNumericTuple = toNumericTuple;
14
+ exports.compareSemverCore = compareSemverCore;
15
+ exports.isSemverNewer = isSemverNewer;
16
+ exports.isStableTripletSemver = isStableTripletSemver;
17
+ function toNumericTuple(input) {
18
+ const cleaned = String(input == null ? '' : input).trim().replace(/^v/, '');
19
+ const base = cleaned.replace(/[-+].*$/, '');
20
+ const parts = base.split('.');
21
+ const major = Number.parseInt(parts[0], 10) || 0;
22
+ const minor = Number.parseInt(parts[1], 10) || 0;
23
+ const patch = Number.parseInt(parts[2], 10) || 0;
24
+ return [major, minor, patch];
25
+ }
26
+ function compareSemverCore(a, b) {
27
+ const [a0, a1, a2] = toNumericTuple(a);
28
+ const [b0, b1, b2] = toNumericTuple(b);
29
+ if (a0 !== b0)
30
+ return a0 > b0 ? 1 : -1;
31
+ if (a1 !== b1)
32
+ return a1 > b1 ? 1 : -1;
33
+ if (a2 !== b2)
34
+ return a2 > b2 ? 1 : -1;
35
+ return 0;
36
+ }
37
+ function isSemverNewer(a, b) {
38
+ return compareSemverCore(a, b) > 0;
39
+ }
40
+ function isStableTripletSemver(v) {
41
+ return /^\d+\.\d+\.\d+$/.test(String(v || '').replace(/^v/, ''));
42
+ }