prizmkit 1.1.99 → 1.1.101

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 (321) hide show
  1. package/bin/create-prizmkit.js +4 -4
  2. package/bundled/VERSION.json +3 -3
  3. package/bundled/dev-pipeline/.env.example +3 -3
  4. package/bundled/dev-pipeline/README.md +110 -90
  5. package/bundled/dev-pipeline/assets/prizm-dev-team-integration.md +1 -1
  6. package/bundled/dev-pipeline/cli.py +27 -0
  7. package/bundled/dev-pipeline/prizmkit_runtime/__init__.py +13 -0
  8. package/bundled/dev-pipeline/prizmkit_runtime/__main__.py +9 -0
  9. package/bundled/dev-pipeline/prizmkit_runtime/cli.py +193 -0
  10. package/bundled/dev-pipeline/prizmkit_runtime/commands.py +313 -0
  11. package/bundled/dev-pipeline/prizmkit_runtime/compat.py +32 -0
  12. package/bundled/dev-pipeline/prizmkit_runtime/config.py +410 -0
  13. package/bundled/dev-pipeline/prizmkit_runtime/daemon.py +478 -0
  14. package/bundled/dev-pipeline/prizmkit_runtime/gitops.py +734 -0
  15. package/bundled/dev-pipeline/prizmkit_runtime/heartbeat.py +256 -0
  16. package/bundled/dev-pipeline/prizmkit_runtime/interoperability.py +109 -0
  17. package/bundled/dev-pipeline/prizmkit_runtime/paths.py +110 -0
  18. package/bundled/dev-pipeline/prizmkit_runtime/processes.py +373 -0
  19. package/bundled/dev-pipeline/prizmkit_runtime/reset.py +389 -0
  20. package/bundled/dev-pipeline/prizmkit_runtime/runner_bookkeeping.py +51 -0
  21. package/bundled/dev-pipeline/prizmkit_runtime/runner_classification.py +179 -0
  22. package/bundled/dev-pipeline/prizmkit_runtime/runner_models.py +345 -0
  23. package/bundled/dev-pipeline/prizmkit_runtime/runner_prompts.py +118 -0
  24. package/bundled/dev-pipeline/prizmkit_runtime/runner_recovery.py +187 -0
  25. package/bundled/dev-pipeline/prizmkit_runtime/runner_status.py +147 -0
  26. package/bundled/dev-pipeline/prizmkit_runtime/runners.py +422 -0
  27. package/bundled/dev-pipeline/prizmkit_runtime/sessions.py +552 -0
  28. package/bundled/dev-pipeline/prizmkit_runtime/status.py +71 -0
  29. package/bundled/dev-pipeline/scripts/check-session-status.py +74 -1
  30. package/bundled/dev-pipeline/scripts/continuation.py +374 -0
  31. package/bundled/dev-pipeline/scripts/generate-bootstrap-prompt.py +64 -52
  32. package/bundled/dev-pipeline/scripts/generate-bugfix-prompt.py +35 -25
  33. package/bundled/dev-pipeline/scripts/generate-recovery-prompt.py +2 -2
  34. package/bundled/dev-pipeline/scripts/generate-refactor-prompt.py +15 -20
  35. package/bundled/dev-pipeline/scripts/parse-stream-progress.py +185 -16
  36. package/bundled/dev-pipeline/scripts/update-bug-status.py +214 -6
  37. package/bundled/dev-pipeline/scripts/update-feature-status.py +237 -6
  38. package/bundled/dev-pipeline/scripts/update-refactor-status.py +214 -6
  39. package/bundled/dev-pipeline/templates/agent-prompts/dev-implement.md +8 -2
  40. package/bundled/dev-pipeline/templates/bootstrap-prompt.md +4 -0
  41. package/bundled/dev-pipeline/templates/bootstrap-tier1.md +14 -5
  42. package/bundled/dev-pipeline/templates/bootstrap-tier2.md +16 -6
  43. package/bundled/dev-pipeline/templates/bootstrap-tier3.md +16 -6
  44. package/bundled/dev-pipeline/templates/bugfix-bootstrap-prompt.md +1 -1
  45. package/bundled/dev-pipeline/templates/refactor-bootstrap-prompt.md +3 -3
  46. package/bundled/dev-pipeline/templates/sections/context-budget-rules.md +2 -0
  47. package/bundled/dev-pipeline/templates/sections/log-size-awareness.md +13 -69
  48. package/bundled/dev-pipeline/templates/sections/phase-context-snapshot-agent-suffix.md +15 -7
  49. package/bundled/dev-pipeline/templates/sections/phase-implement-agent.md +42 -29
  50. package/bundled/dev-pipeline/templates/sections/phase-implement-full.md +41 -39
  51. package/bundled/dev-pipeline/templates/sections/test-failure-recovery-agent.md +4 -0
  52. package/bundled/dev-pipeline/templates/sections/test-failure-recovery-lite.md +4 -0
  53. package/bundled/dev-pipeline/templates/session-status-schema.json +1 -1
  54. package/bundled/dev-pipeline/tests/conftest.py +1 -0
  55. package/bundled/dev-pipeline/tests/test_auto_skip.py +932 -0
  56. package/bundled/dev-pipeline/tests/test_generate_bootstrap_prompt.py +207 -0
  57. package/bundled/dev-pipeline/tests/test_generate_bugfix_prompt.py +100 -0
  58. package/bundled/dev-pipeline/tests/test_generate_refactor_prompt.py +43 -0
  59. package/bundled/dev-pipeline/tests/test_python_runner_parity.py +1138 -0
  60. package/bundled/dev-pipeline/tests/test_unified_cli.py +1045 -0
  61. package/bundled/skills/_metadata.json +1 -1
  62. package/bundled/skills/bugfix-pipeline-launcher/SKILL.md +29 -34
  63. package/bundled/skills/bugfix-pipeline-launcher/references/configuration.md +6 -5
  64. package/bundled/skills/feature-pipeline-launcher/SKILL.md +29 -35
  65. package/bundled/skills/feature-pipeline-launcher/references/configuration.md +7 -6
  66. package/bundled/skills/feature-workflow/SKILL.md +3 -6
  67. package/bundled/skills/recovery-workflow/SKILL.md +23 -32
  68. package/bundled/skills/refactor-pipeline-launcher/SKILL.md +29 -35
  69. package/bundled/skills/refactor-pipeline-launcher/references/configuration.md +7 -6
  70. package/bundled/skills/refactor-workflow/SKILL.md +3 -6
  71. package/bundled/templates/hooks/commit-intent.json +2 -2
  72. package/bundled/templates/hooks/diff-prizm-docs.py +226 -0
  73. package/bundled/templates/hooks/prizm-pre-commit.py +45 -0
  74. package/bundled/templates/hooks/validate-prizm-docs.py +240 -0
  75. package/package.json +1 -1
  76. package/src/config.js +33 -12
  77. package/src/index.js +3 -6
  78. package/src/manifest.js +3 -2
  79. package/src/metadata.js +7 -18
  80. package/src/prompts.js +0 -12
  81. package/src/runtimes.js +18 -11
  82. package/src/scaffold.js +133 -116
  83. package/src/upgrade.js +1 -1
  84. package/bundled/dev-pipeline/launch-bugfix-daemon.sh +0 -500
  85. package/bundled/dev-pipeline/launch-feature-daemon.sh +0 -657
  86. package/bundled/dev-pipeline/launch-refactor-daemon.sh +0 -502
  87. package/bundled/dev-pipeline/lib/branch.sh +0 -326
  88. package/bundled/dev-pipeline/lib/common.sh +0 -1257
  89. package/bundled/dev-pipeline/lib/heartbeat.sh +0 -469
  90. package/bundled/dev-pipeline/reset-bug.sh +0 -395
  91. package/bundled/dev-pipeline/reset-feature.sh +0 -406
  92. package/bundled/dev-pipeline/reset-refactor.sh +0 -393
  93. package/bundled/dev-pipeline/run-bugfix.sh +0 -1315
  94. package/bundled/dev-pipeline/run-feature.sh +0 -1602
  95. package/bundled/dev-pipeline/run-recovery.sh +0 -648
  96. package/bundled/dev-pipeline/run-refactor.sh +0 -1348
  97. package/bundled/dev-pipeline/scripts/monitor-log.sh +0 -104
  98. package/bundled/dev-pipeline/tests/test-path-resolution.sh +0 -100
  99. package/bundled/dev-pipeline-windows/.env.example +0 -36
  100. package/bundled/dev-pipeline-windows/README.md +0 -30
  101. package/bundled/dev-pipeline-windows/SCHEMA_ANALYSIS.md +0 -533
  102. package/bundled/dev-pipeline-windows/assets/feature-list-example.json +0 -146
  103. package/bundled/dev-pipeline-windows/assets/prizm-dev-team-integration.md +0 -137
  104. package/bundled/dev-pipeline-windows/launch-bugfix-daemon.ps1 +0 -9
  105. package/bundled/dev-pipeline-windows/launch-feature-daemon.ps1 +0 -9
  106. package/bundled/dev-pipeline-windows/launch-refactor-daemon.ps1 +0 -9
  107. package/bundled/dev-pipeline-windows/lib/branch.ps1 +0 -235
  108. package/bundled/dev-pipeline-windows/lib/common.ps1 +0 -829
  109. package/bundled/dev-pipeline-windows/lib/daemon.ps1 +0 -140
  110. package/bundled/dev-pipeline-windows/lib/pipeline.ps1 +0 -967
  111. package/bundled/dev-pipeline-windows/lib/reset.ps1 +0 -87
  112. package/bundled/dev-pipeline-windows/reset-bug.ps1 +0 -9
  113. package/bundled/dev-pipeline-windows/reset-feature.ps1 +0 -9
  114. package/bundled/dev-pipeline-windows/reset-refactor.ps1 +0 -9
  115. package/bundled/dev-pipeline-windows/run-bugfix.ps1 +0 -9
  116. package/bundled/dev-pipeline-windows/run-feature.ps1 +0 -9
  117. package/bundled/dev-pipeline-windows/run-recovery.ps1 +0 -179
  118. package/bundled/dev-pipeline-windows/run-refactor.ps1 +0 -9
  119. package/bundled/dev-pipeline-windows/scripts/check-session-status.py +0 -228
  120. package/bundled/dev-pipeline-windows/scripts/detect-stuck.py +0 -530
  121. package/bundled/dev-pipeline-windows/scripts/generate-bootstrap-prompt.py +0 -2282
  122. package/bundled/dev-pipeline-windows/scripts/generate-bugfix-prompt.py +0 -767
  123. package/bundled/dev-pipeline-windows/scripts/generate-recovery-prompt.py +0 -805
  124. package/bundled/dev-pipeline-windows/scripts/generate-refactor-prompt.py +0 -845
  125. package/bundled/dev-pipeline-windows/scripts/init-bugfix-pipeline.py +0 -316
  126. package/bundled/dev-pipeline-windows/scripts/init-dev-team.py +0 -134
  127. package/bundled/dev-pipeline-windows/scripts/init-pipeline.py +0 -382
  128. package/bundled/dev-pipeline-windows/scripts/init-refactor-pipeline.py +0 -399
  129. package/bundled/dev-pipeline-windows/scripts/monitor-log.ps1 +0 -102
  130. package/bundled/dev-pipeline-windows/scripts/parse-stream-progress.py +0 -1232
  131. package/bundled/dev-pipeline-windows/scripts/patch-completion-notes.py +0 -191
  132. package/bundled/dev-pipeline-windows/scripts/prizmkit-test-gate.py +0 -446
  133. package/bundled/dev-pipeline-windows/scripts/update-bug-status.py +0 -913
  134. package/bundled/dev-pipeline-windows/scripts/update-checkpoint.py +0 -173
  135. package/bundled/dev-pipeline-windows/scripts/update-feature-status.py +0 -1558
  136. package/bundled/dev-pipeline-windows/scripts/update-refactor-status.py +0 -1119
  137. package/bundled/dev-pipeline-windows/scripts/utils.py +0 -542
  138. package/bundled/dev-pipeline-windows/templates/agent-prompts/critic-plan-challenge.md +0 -7
  139. package/bundled/dev-pipeline-windows/templates/agent-prompts/dev-fix.md +0 -7
  140. package/bundled/dev-pipeline-windows/templates/agent-prompts/dev-implement.md +0 -65
  141. package/bundled/dev-pipeline-windows/templates/agent-prompts/dev-resume.md +0 -5
  142. package/bundled/dev-pipeline-windows/templates/agent-prompts/reviewer-review.md +0 -7
  143. package/bundled/dev-pipeline-windows/templates/bootstrap-prompt.md +0 -73
  144. package/bundled/dev-pipeline-windows/templates/bootstrap-tier1.md +0 -589
  145. package/bundled/dev-pipeline-windows/templates/bootstrap-tier2.md +0 -710
  146. package/bundled/dev-pipeline-windows/templates/bootstrap-tier3.md +0 -791
  147. package/bundled/dev-pipeline-windows/templates/bug-fix-list-schema.json +0 -263
  148. package/bundled/dev-pipeline-windows/templates/bugfix-bootstrap-prompt.md +0 -326
  149. package/bundled/dev-pipeline-windows/templates/feature-list-schema.json +0 -237
  150. package/bundled/dev-pipeline-windows/templates/refactor-bootstrap-prompt.md +0 -340
  151. package/bundled/dev-pipeline-windows/templates/refactor-list-schema.json +0 -270
  152. package/bundled/dev-pipeline-windows/templates/sections/ac-verification-checklist.md +0 -7
  153. package/bundled/dev-pipeline-windows/templates/sections/checkpoint-system.md +0 -91
  154. package/bundled/dev-pipeline-windows/templates/sections/context-budget-rules.md +0 -34
  155. package/bundled/dev-pipeline-windows/templates/sections/critical-paths-agent.md +0 -10
  156. package/bundled/dev-pipeline-windows/templates/sections/critical-paths-full.md +0 -12
  157. package/bundled/dev-pipeline-windows/templates/sections/critical-paths-lite.md +0 -7
  158. package/bundled/dev-pipeline-windows/templates/sections/directory-convention-agent.md +0 -8
  159. package/bundled/dev-pipeline-windows/templates/sections/directory-convention-full.md +0 -9
  160. package/bundled/dev-pipeline-windows/templates/sections/directory-convention-lite.md +0 -6
  161. package/bundled/dev-pipeline-windows/templates/sections/failure-capture.md +0 -21
  162. package/bundled/dev-pipeline-windows/templates/sections/feature-context.md +0 -21
  163. package/bundled/dev-pipeline-windows/templates/sections/log-size-awareness.md +0 -78
  164. package/bundled/dev-pipeline-windows/templates/sections/phase-browser-verification-auto.md +0 -283
  165. package/bundled/dev-pipeline-windows/templates/sections/phase-browser-verification-opencli.md +0 -112
  166. package/bundled/dev-pipeline-windows/templates/sections/phase-browser-verification.md +0 -168
  167. package/bundled/dev-pipeline-windows/templates/sections/phase-commit-full.md +0 -82
  168. package/bundled/dev-pipeline-windows/templates/sections/phase-commit.md +0 -75
  169. package/bundled/dev-pipeline-windows/templates/sections/phase-context-snapshot-agent-suffix.md +0 -23
  170. package/bundled/dev-pipeline-windows/templates/sections/phase-context-snapshot-base.md +0 -14
  171. package/bundled/dev-pipeline-windows/templates/sections/phase-context-snapshot-lite-suffix.md +0 -19
  172. package/bundled/dev-pipeline-windows/templates/sections/phase-critic-plan-full.md +0 -63
  173. package/bundled/dev-pipeline-windows/templates/sections/phase-critic-plan.md +0 -42
  174. package/bundled/dev-pipeline-windows/templates/sections/phase-implement-agent.md +0 -44
  175. package/bundled/dev-pipeline-windows/templates/sections/phase-implement-full.md +0 -59
  176. package/bundled/dev-pipeline-windows/templates/sections/phase-implement-lite.md +0 -39
  177. package/bundled/dev-pipeline-windows/templates/sections/phase-plan-agent.md +0 -27
  178. package/bundled/dev-pipeline-windows/templates/sections/phase-plan-lite.md +0 -27
  179. package/bundled/dev-pipeline-windows/templates/sections/phase-prizmkit-test.md +0 -39
  180. package/bundled/dev-pipeline-windows/templates/sections/phase-review-agent.md +0 -35
  181. package/bundled/dev-pipeline-windows/templates/sections/phase-review-full.md +0 -35
  182. package/bundled/dev-pipeline-windows/templates/sections/phase-specify-plan-full.md +0 -73
  183. package/bundled/dev-pipeline-windows/templates/sections/phase0-init.md +0 -13
  184. package/bundled/dev-pipeline-windows/templates/sections/phase0-test-baseline.md +0 -21
  185. package/bundled/dev-pipeline-windows/templates/sections/session-context.md +0 -5
  186. package/bundled/dev-pipeline-windows/templates/sections/subagent-timeout-recovery.md +0 -6
  187. package/bundled/dev-pipeline-windows/templates/sections/task-contract.md +0 -34
  188. package/bundled/dev-pipeline-windows/templates/sections/test-failure-recovery-agent.md +0 -48
  189. package/bundled/dev-pipeline-windows/templates/sections/test-failure-recovery-lite.md +0 -48
  190. package/bundled/dev-pipeline-windows/templates/session-status-schema.json +0 -83
  191. package/bundled/skills-windows/app-planner/SKILL.md +0 -296
  192. package/bundled/skills-windows/app-planner/assets/app-design-guide.md +0 -101
  193. package/bundled/skills-windows/app-planner/references/architecture-decisions.md +0 -52
  194. package/bundled/skills-windows/app-planner/references/brainstorm-guide.md +0 -101
  195. package/bundled/skills-windows/app-planner/references/frontend-design-guide.md +0 -71
  196. package/bundled/skills-windows/app-planner/references/infrastructure-convention-discovery.md +0 -108
  197. package/bundled/skills-windows/app-planner/references/project-brief-guide.md +0 -82
  198. package/bundled/skills-windows/app-planner/references/project-conventions-discovery.md +0 -59
  199. package/bundled/skills-windows/app-planner/references/project-state-detection.md +0 -90
  200. package/bundled/skills-windows/app-planner/references/red-team-checklist.md +0 -40
  201. package/bundled/skills-windows/app-planner/references/rules/backend/derivation-rules.md +0 -619
  202. package/bundled/skills-windows/app-planner/references/rules/backend/fixed-rules.md +0 -285
  203. package/bundled/skills-windows/app-planner/references/rules/backend/question-bank.md +0 -249
  204. package/bundled/skills-windows/app-planner/references/rules/backend/question-manifest.json +0 -46
  205. package/bundled/skills-windows/app-planner/references/rules/backend/template.md +0 -173
  206. package/bundled/skills-windows/app-planner/references/rules/database/derivation-rules.md +0 -382
  207. package/bundled/skills-windows/app-planner/references/rules/database/fixed-rules.md +0 -211
  208. package/bundled/skills-windows/app-planner/references/rules/database/question-bank.md +0 -184
  209. package/bundled/skills-windows/app-planner/references/rules/database/question-manifest.json +0 -39
  210. package/bundled/skills-windows/app-planner/references/rules/database/template.md +0 -158
  211. package/bundled/skills-windows/app-planner/references/rules/frontend/derivation-rules.md +0 -820
  212. package/bundled/skills-windows/app-planner/references/rules/frontend/fixed-rules.md +0 -188
  213. package/bundled/skills-windows/app-planner/references/rules/frontend/question-bank.md +0 -319
  214. package/bundled/skills-windows/app-planner/references/rules/frontend/question-manifest.json +0 -51
  215. package/bundled/skills-windows/app-planner/references/rules/frontend/template.md +0 -339
  216. package/bundled/skills-windows/app-planner/references/rules/mobile/derivation-rules.md +0 -649
  217. package/bundled/skills-windows/app-planner/references/rules/mobile/fixed-rules.md +0 -290
  218. package/bundled/skills-windows/app-planner/references/rules/mobile/question-bank.md +0 -232
  219. package/bundled/skills-windows/app-planner/references/rules/mobile/question-manifest.json +0 -47
  220. package/bundled/skills-windows/app-planner/references/rules/mobile/template.md +0 -175
  221. package/bundled/skills-windows/app-planner/references/rules-configuration.md +0 -46
  222. package/bundled/skills-windows/bug-fix-workflow/SKILL.md +0 -379
  223. package/bundled/skills-windows/bug-fix-workflow/references/bug-diagnosis.md +0 -41
  224. package/bundled/skills-windows/bug-planner/SKILL.md +0 -402
  225. package/bundled/skills-windows/bug-planner/assets/bug-confirmation-template.md +0 -43
  226. package/bundled/skills-windows/bug-planner/references/critic-and-verification.md +0 -44
  227. package/bundled/skills-windows/bug-planner/references/error-recovery.md +0 -73
  228. package/bundled/skills-windows/bug-planner/references/input-formats.md +0 -53
  229. package/bundled/skills-windows/bug-planner/references/schema-validation.md +0 -25
  230. package/bundled/skills-windows/bug-planner/references/severity-rules.md +0 -16
  231. package/bundled/skills-windows/bug-planner/scripts/validate-bug-list.py +0 -322
  232. package/bundled/skills-windows/bugfix-pipeline-launcher/SKILL.md +0 -304
  233. package/bundled/skills-windows/bugfix-pipeline-launcher/references/configuration.md +0 -84
  234. package/bundled/skills-windows/feature-pipeline-launcher/SKILL.md +0 -381
  235. package/bundled/skills-windows/feature-pipeline-launcher/references/configuration.md +0 -67
  236. package/bundled/skills-windows/feature-pipeline-launcher/scripts/preflight-check.py +0 -462
  237. package/bundled/skills-windows/feature-planner/SKILL.md +0 -397
  238. package/bundled/skills-windows/feature-planner/assets/evaluation-guide.md +0 -64
  239. package/bundled/skills-windows/feature-planner/assets/planning-guide.md +0 -214
  240. package/bundled/skills-windows/feature-planner/references/browser-interaction.md +0 -59
  241. package/bundled/skills-windows/feature-planner/references/completeness-review.md +0 -57
  242. package/bundled/skills-windows/feature-planner/references/decomposition-patterns.md +0 -75
  243. package/bundled/skills-windows/feature-planner/references/error-recovery.md +0 -90
  244. package/bundled/skills-windows/feature-planner/references/incremental-feature-planning.md +0 -112
  245. package/bundled/skills-windows/feature-planner/references/new-project-planning.md +0 -85
  246. package/bundled/skills-windows/feature-planner/scripts/validate-and-generate.py +0 -1020
  247. package/bundled/skills-windows/feature-workflow/SKILL.md +0 -374
  248. package/bundled/skills-windows/feature-workflow/references/brainstorm-guide.md +0 -137
  249. package/bundled/skills-windows/prizm-kit/SKILL.md +0 -93
  250. package/bundled/skills-windows/prizmkit-code-review/SKILL.md +0 -161
  251. package/bundled/skills-windows/prizmkit-code-review/references/dev-agent-prompt.md +0 -30
  252. package/bundled/skills-windows/prizmkit-code-review/references/review-report-template.md +0 -31
  253. package/bundled/skills-windows/prizmkit-code-review/references/reviewer-agent-prompt.md +0 -66
  254. package/bundled/skills-windows/prizmkit-code-review/scripts/check_loop.py +0 -186
  255. package/bundled/skills-windows/prizmkit-committer/SKILL.md +0 -89
  256. package/bundled/skills-windows/prizmkit-deploy/SKILL.md +0 -444
  257. package/bundled/skills-windows/prizmkit-deploy/references/ci-cd-workflows.md +0 -115
  258. package/bundled/skills-windows/prizmkit-deploy/references/cloud-platform-deploy.md +0 -93
  259. package/bundled/skills-windows/prizmkit-deploy/references/data-safety-examples.md +0 -120
  260. package/bundled/skills-windows/prizmkit-deploy/references/database-setup.md +0 -46
  261. package/bundled/skills-windows/prizmkit-deploy/references/deploy-config-schema.md +0 -148
  262. package/bundled/skills-windows/prizmkit-deploy/references/deploy-history-schema.md +0 -62
  263. package/bundled/skills-windows/prizmkit-deploy/references/deployment-modes.md +0 -50
  264. package/bundled/skills-windows/prizmkit-deploy/references/direct-upload.md +0 -26
  265. package/bundled/skills-windows/prizmkit-deploy/references/dns-setup.md +0 -42
  266. package/bundled/skills-windows/prizmkit-deploy/references/docker-deploy.md +0 -31
  267. package/bundled/skills-windows/prizmkit-deploy/references/firewall-setup.md +0 -37
  268. package/bundled/skills-windows/prizmkit-deploy/references/live-validation-notes.md +0 -21
  269. package/bundled/skills-windows/prizmkit-deploy/references/nginx-blue-green.md +0 -59
  270. package/bundled/skills-windows/prizmkit-deploy/references/ssh-bootstrap-flow.md +0 -49
  271. package/bundled/skills-windows/prizmkit-deploy/references/ssh-execution-flow.md +0 -41
  272. package/bundled/skills-windows/prizmkit-deploy/references/ssh-takeover.md +0 -20
  273. package/bundled/skills-windows/prizmkit-deploy/references/ssl-setup.md +0 -56
  274. package/bundled/skills-windows/prizmkit-implement/SKILL.md +0 -71
  275. package/bundled/skills-windows/prizmkit-init/SKILL.md +0 -356
  276. package/bundled/skills-windows/prizmkit-init/assets/project-brief-template.md +0 -82
  277. package/bundled/skills-windows/prizmkit-init/references/config-schema.md +0 -70
  278. package/bundled/skills-windows/prizmkit-init/references/rules/layer-detection.md +0 -41
  279. package/bundled/skills-windows/prizmkit-init/references/tech-stack-catalog.md +0 -13
  280. package/bundled/skills-windows/prizmkit-init/references/update-supplement.md +0 -9
  281. package/bundled/skills-windows/prizmkit-plan/SKILL.md +0 -102
  282. package/bundled/skills-windows/prizmkit-plan/assets/plan-template.md +0 -115
  283. package/bundled/skills-windows/prizmkit-plan/assets/spec-template.md +0 -73
  284. package/bundled/skills-windows/prizmkit-plan/references/clarify-guide.md +0 -67
  285. package/bundled/skills-windows/prizmkit-plan/references/examples.md +0 -85
  286. package/bundled/skills-windows/prizmkit-plan/references/verification-checklist.md +0 -60
  287. package/bundled/skills-windows/prizmkit-prizm-docs/SKILL.md +0 -129
  288. package/bundled/skills-windows/prizmkit-prizm-docs/assets/prizm-docs-format.md +0 -613
  289. package/bundled/skills-windows/prizmkit-prizm-docs/references/op-init.md +0 -45
  290. package/bundled/skills-windows/prizmkit-prizm-docs/references/op-rebuild.md +0 -15
  291. package/bundled/skills-windows/prizmkit-prizm-docs/references/op-status.md +0 -14
  292. package/bundled/skills-windows/prizmkit-prizm-docs/references/op-update.md +0 -19
  293. package/bundled/skills-windows/prizmkit-prizm-docs/references/op-validate.md +0 -17
  294. package/bundled/skills-windows/prizmkit-retrospective/SKILL.md +0 -87
  295. package/bundled/skills-windows/prizmkit-retrospective/references/knowledge-injection-steps.md +0 -50
  296. package/bundled/skills-windows/prizmkit-retrospective/references/structural-sync-steps.md +0 -43
  297. package/bundled/skills-windows/prizmkit-test/SKILL.md +0 -227
  298. package/bundled/skills-windows/prizmkit-test/references/boundary-coverage-protocol.md +0 -220
  299. package/bundled/skills-windows/prizmkit-test/references/examples.md +0 -143
  300. package/bundled/skills-windows/prizmkit-test/references/service-boundary-test-catalog.md +0 -225
  301. package/bundled/skills-windows/prizmkit-test/references/test-generation-steps.md +0 -109
  302. package/bundled/skills-windows/prizmkit-test/references/test-report-template.md +0 -111
  303. package/bundled/skills-windows/prizmkit-test/scripts/validate_boundary_report.py +0 -347
  304. package/bundled/skills-windows/recovery-workflow/SKILL.md +0 -355
  305. package/bundled/skills-windows/recovery-workflow/evals/evals.json +0 -46
  306. package/bundled/skills-windows/recovery-workflow/references/detection.md +0 -58
  307. package/bundled/skills-windows/recovery-workflow/scripts/detect-recovery-state.py +0 -544
  308. package/bundled/skills-windows/refactor-pipeline-launcher/SKILL.md +0 -346
  309. package/bundled/skills-windows/refactor-pipeline-launcher/references/configuration.md +0 -72
  310. package/bundled/skills-windows/refactor-planner/SKILL.md +0 -398
  311. package/bundled/skills-windows/refactor-planner/assets/planning-guide.md +0 -292
  312. package/bundled/skills-windows/refactor-planner/references/behavior-preservation.md +0 -301
  313. package/bundled/skills-windows/refactor-planner/references/fast-path.md +0 -59
  314. package/bundled/skills-windows/refactor-planner/references/planning-phases.md +0 -135
  315. package/bundled/skills-windows/refactor-planner/references/refactor-scoping-guide.md +0 -221
  316. package/bundled/skills-windows/refactor-planner/scripts/validate-and-generate-refactor.py +0 -858
  317. package/bundled/skills-windows/refactor-workflow/SKILL.md +0 -343
  318. package/bundled/skills-windows/refactor-workflow/references/brainstorm-guide.md +0 -116
  319. package/bundled/templates/hooks/diff-prizm-docs.sh +0 -158
  320. package/bundled/templates/hooks/prizm-pre-commit.sh +0 -108
  321. package/bundled/templates/hooks/validate-prizm-docs.sh +0 -139
@@ -1,1119 +0,0 @@
1
- #!/usr/bin/env python3
2
- """Core state machine for updating refactor status in the refactor pipeline.
3
-
4
- Handles eight actions:
5
- - get_next: Find the next refactor to process based on dependency order, priority, complexity
6
- - start: Mark a refactor as in_progress when a session starts
7
- - update: Update a refactor's status based on session outcome
8
- - status: Print a formatted overview of all refactors
9
- - pause: Save pipeline state for graceful shutdown
10
- - reset: Reset a refactor to pending (status + retry count)
11
- - clean: Reset + delete session history + delete refactor artifacts
12
- - unskip: Reset skipped refactors and their downstream dependents back to pending
13
-
14
- Usage:
15
- python3 update-refactor-status.py \
16
- --refactor-list <path> --state-dir <path> \
17
- --action <get_next|start|update|status|pause|reset|clean|unskip> \
18
- [--refactor-id <id>] [--session-status <status>] \
19
- [--session-id <id>] [--max-retries <n>] [--max-infra-retries <n>]
20
- """
21
-
22
- import argparse
23
- import json
24
- import os
25
- import shutil
26
- import sys
27
- from datetime import datetime, timezone
28
-
29
- from utils import (
30
- load_json_file,
31
- write_json_file,
32
- error_out,
33
- pad_right,
34
- _build_progress_bar,
35
- )
36
-
37
-
38
- SESSION_STATUS_VALUES = [
39
- "success",
40
- "partial_resumable",
41
- "partial_not_resumable",
42
- "failed",
43
- "crashed",
44
- "timed_out",
45
- "infra_error",
46
- "commit_missing",
47
- "docs_missing",
48
- "merge_conflict",
49
- ]
50
-
51
- TERMINAL_STATUSES = {"completed", "failed", "skipped", "auto_skipped"}
52
-
53
- # Artifact directory names (relative to project root)
54
- REFACTOR_ARTIFACTS_REL = os.path.join(".prizmkit", "refactor")
55
- DEV_TEAM_DIR_NAME = ".dev-team"
56
-
57
- # Priority ordering (lower number = higher priority)
58
- PRIORITY_ORDER = {
59
- "critical": 0,
60
- "high": 1,
61
- "medium": 2,
62
- "low": 3,
63
- }
64
-
65
- # Complexity ordering (lower number = simpler, processed first)
66
- COMPLEXITY_ORDER = {
67
- "low": 0,
68
- "medium": 1,
69
- "high": 2,
70
- }
71
-
72
-
73
- def parse_args():
74
- parser = argparse.ArgumentParser(
75
- description="Core state machine for refactor pipeline status management."
76
- )
77
- parser.add_argument("--refactor-list", required=True, help="Path to the .prizmkit/plans/refactor-list.json file")
78
- parser.add_argument("--state-dir", required=True, help="Path to the state directory (default: .prizmkit/state/refactor)")
79
- parser.add_argument(
80
- "--action", required=True,
81
- choices=["get_next", "start", "update", "status", "pause", "reset", "clean", "unskip", "complete"],
82
- help="Action to perform",
83
- )
84
- parser.add_argument("--refactor-id", default=None, help="Refactor ID (required for 'update'/'reset'/'clean' actions)")
85
- parser.add_argument(
86
- "--session-status", default=None, choices=SESSION_STATUS_VALUES,
87
- help="Session outcome status (required for 'update' action)",
88
- )
89
- parser.add_argument("--session-id", default=None, help="Session ID (optional, for 'update' action)")
90
- parser.add_argument("--max-retries", type=int, default=3, help="Maximum code retry count (default: 3)")
91
- parser.add_argument("--max-infra-retries", type=int, default=3, help="Maximum infrastructure retry count (default: 3)")
92
- parser.add_argument("--project-root", default=None, help="Project root directory. Required for 'clean' action.")
93
- return parser.parse_args()
94
-
95
-
96
- def now_iso():
97
- return datetime.now(timezone.utc).strftime("%Y-%m-%dT%H:%M:%SZ")
98
-
99
-
100
- def _default_status(refactor_id):
101
- """Create a default refactor runtime status object (no status field)."""
102
- now = now_iso()
103
- return {
104
- "refactor_id": refactor_id,
105
- "retry_count": 0,
106
- "max_retries": 3,
107
- "max_infra_retries": 3,
108
- "infra_error_count": 0,
109
- "last_infra_error_session_id": None,
110
- "sessions": [],
111
- "last_session_id": None,
112
- "resume_from_phase": None,
113
- "created_at": now,
114
- "updated_at": now,
115
- }
116
-
117
-
118
- def load_refactor_status(state_dir, refactor_id):
119
- """Load runtime state from status.json for a refactor.
120
-
121
- Returns runtime fields only (retry_count, sessions, etc.).
122
- The 'status' field is NOT included — status lives exclusively
123
- in refactor-list.json.
124
- """
125
- status_path = os.path.join(state_dir, refactor_id, "status.json")
126
- if not os.path.isfile(status_path):
127
- return _default_status(refactor_id)
128
- data, err = load_json_file(status_path)
129
- if err:
130
- return _default_status(refactor_id)
131
- # Defensively remove status if present (legacy data)
132
- data.pop("status", None)
133
- return data
134
-
135
-
136
- def save_refactor_status(state_dir, refactor_id, status_data):
137
- """Write the status.json for a refactor (runtime fields only)."""
138
- # Defensively strip status — it belongs in refactor-list.json
139
- status_data.pop("status", None)
140
- status_path = os.path.join(state_dir, refactor_id, "status.json")
141
- return write_json_file(status_path, status_data)
142
-
143
-
144
- def get_refactor_status_from_list(refactor_list_path, refactor_id):
145
- """Read a single refactor's status from refactor-list.json."""
146
- data, err = load_json_file(refactor_list_path)
147
- if err:
148
- return "pending"
149
- for r in data.get("refactors", []):
150
- if isinstance(r, dict) and r.get("id") == refactor_id:
151
- return r.get("status", "pending")
152
- return "pending"
153
-
154
-
155
- def update_refactor_in_list(refactor_list_path, refactor_id, new_status):
156
- data, err = load_json_file(refactor_list_path)
157
- if err:
158
- return err
159
- refactors = data.get("refactors", [])
160
- found = False
161
- for refactor in refactors:
162
- if isinstance(refactor, dict) and refactor.get("id") == refactor_id:
163
- refactor["status"] = new_status
164
- found = True
165
- break
166
- if not found:
167
- return "Refactor '{}' not found in .prizmkit/plans/refactor-list.json".format(refactor_id)
168
- return write_json_file(refactor_list_path, data)
169
-
170
-
171
- # ---------------------------------------------------------------------------
172
- # Action: get_next
173
- # ---------------------------------------------------------------------------
174
-
175
-
176
- def _dependencies_met(refactor, completed_set):
177
- """Check if all dependencies for a refactor are in terminal (completed) status."""
178
- deps = refactor.get("dependencies", [])
179
- if not deps or not isinstance(deps, list):
180
- return True
181
- return all(dep in completed_set for dep in deps)
182
-
183
-
184
- def _count_unmet_deps(refactor, completed_set):
185
- """Count how many dependencies are not yet completed."""
186
- deps = refactor.get("dependencies", [])
187
- if not deps or not isinstance(deps, list):
188
- return 0
189
- return sum(1 for dep in deps if dep not in completed_set)
190
-
191
-
192
- def action_get_next(refactor_list_data, state_dir):
193
- """Find the next refactor to process.
194
-
195
- Priority logic:
196
- 1. Skip terminal statuses (completed, failed, skipped)
197
- 2. Only consider refactors whose dependencies are all completed
198
- 3. Prefer in_progress refactors (interrupted session resume) over pending
199
- 4. Sort by: dependency order (no-dependency items first),
200
- then priority (critical > high > medium > low),
201
- then complexity (low first)
202
- """
203
- refactors = refactor_list_data.get("refactors", [])
204
- if not refactors:
205
- print("PIPELINE_COMPLETE")
206
- return
207
-
208
- # Build status map from refactor-list.json (single source of truth)
209
- status_map = {}
210
- status_data_map = {}
211
- for r in refactors:
212
- if not isinstance(r, dict):
213
- continue
214
- rid = r.get("id")
215
- if not rid:
216
- continue
217
- status_map[rid] = r.get("status", "pending")
218
- rs = load_refactor_status(state_dir, rid)
219
- status_data_map[rid] = rs
220
-
221
- completed_set = {rid for rid, st in status_map.items() if st in TERMINAL_STATUSES}
222
-
223
- # Check if all refactors are terminal
224
- non_terminal = [
225
- r for r in refactors
226
- if isinstance(r, dict) and r.get("id")
227
- and status_map.get(r["id"], "pending") not in TERMINAL_STATUSES
228
- ]
229
- if not non_terminal:
230
- print("PIPELINE_COMPLETE")
231
- return
232
-
233
- # Filter to only those with met dependencies
234
- eligible = [r for r in non_terminal if _dependencies_met(r, completed_set)]
235
- if not eligible:
236
- print("PIPELINE_BLOCKED")
237
- return
238
-
239
- # Separate in_progress from pending
240
- in_progress_refactors = []
241
- pending_refactors = []
242
- for r in eligible:
243
- rid = r.get("id")
244
- rstatus = status_map.get(rid, "pending")
245
- if rstatus == "in_progress":
246
- in_progress_refactors.append(r)
247
- elif rstatus == "pending":
248
- pending_refactors.append(r)
249
-
250
- def sort_key(r):
251
- unmet = _count_unmet_deps(r, completed_set)
252
- priority = PRIORITY_ORDER.get(r.get("priority", "medium"), 2)
253
- complexity = COMPLEXITY_ORDER.get(r.get("complexity", "medium"), 1)
254
- return (unmet, priority, complexity)
255
-
256
- if in_progress_refactors:
257
- candidates = sorted(in_progress_refactors, key=sort_key)
258
- elif pending_refactors:
259
- candidates = sorted(pending_refactors, key=sort_key)
260
- else:
261
- print("PIPELINE_BLOCKED")
262
- return
263
-
264
- chosen = candidates[0]
265
- chosen_id = chosen["id"]
266
- chosen_status_data = status_data_map.get(chosen_id, {})
267
-
268
- result = {
269
- "refactor_id": chosen_id,
270
- "title": chosen.get("title", ""),
271
- "type": chosen.get("type", "restructure"),
272
- "priority": chosen.get("priority", "medium"),
273
- "complexity": chosen.get("complexity", "medium"),
274
- "retry_count": chosen_status_data.get("retry_count", 0),
275
- "infra_error_count": chosen_status_data.get("infra_error_count", 0),
276
- "resume_from_phase": chosen_status_data.get("resume_from_phase", None),
277
- }
278
- print(json.dumps(result, indent=2, ensure_ascii=False))
279
-
280
-
281
- # ---------------------------------------------------------------------------
282
- # Action: update
283
- # ---------------------------------------------------------------------------
284
-
285
- def action_update(args, refactor_list_path, state_dir):
286
- refactor_id = args.refactor_id
287
- session_status = args.session_status
288
- session_id = args.session_id
289
- max_retries = args.max_retries
290
- max_infra_retries = args.max_infra_retries
291
-
292
- if not refactor_id:
293
- error_out("--refactor-id is required for 'update' action")
294
- return
295
- if not session_status:
296
- error_out("--session-status is required for 'update' action")
297
- return
298
-
299
- rs = load_refactor_status(state_dir, refactor_id)
300
-
301
- # Track what status we write to refactor-list.json
302
- new_status = get_refactor_status_from_list(refactor_list_path, refactor_id)
303
-
304
- if session_status == "success":
305
- rs["infra_error_count"] = 0
306
- rs["last_infra_error_session_id"] = None
307
- new_status = "completed"
308
- rs["resume_from_phase"] = None
309
- err = update_refactor_in_list(refactor_list_path, refactor_id, "completed")
310
- if err:
311
- error_out("Failed to update .prizmkit/plans/refactor-list.json: {}".format(err))
312
- return
313
- elif session_status in ("commit_missing", "docs_missing", "merge_conflict"):
314
- rs["retry_count"] = rs.get("retry_count", 0) + 1
315
-
316
- if rs["retry_count"] >= max_retries:
317
- new_status = "failed"
318
- else:
319
- new_status = "pending"
320
-
321
- rs["degraded_reason"] = session_status
322
- rs["resume_from_phase"] = None
323
- rs["sessions"] = []
324
- rs["last_session_id"] = None
325
-
326
- err = update_refactor_in_list(refactor_list_path, refactor_id, new_status)
327
- if err:
328
- error_out("Failed to update .prizmkit/plans/refactor-list.json: {}".format(err))
329
- return
330
- elif session_status == "infra_error":
331
- # AI CLI/provider outage, auth failure, gateway error, etc.
332
- # Infra failures do not consume the code retry budget, but they still
333
- # need their own bounded budget so a flaky provider cannot loop forever.
334
- infra_error_count = rs.get("infra_error_count", 0) + 1
335
- rs["infra_error_count"] = infra_error_count
336
- rs["last_infra_error_session_id"] = session_id
337
- rs["max_infra_retries"] = max_infra_retries
338
- rs["degraded_reason"] = "infra_error"
339
- if session_id:
340
- rs["last_session_id"] = session_id
341
- rs["resume_from_phase"] = None
342
-
343
- if infra_error_count >= max_infra_retries:
344
- new_status = "failed"
345
- if session_id:
346
- rs["last_failed_session_id"] = session_id
347
- else:
348
- new_status = "pending"
349
-
350
- err = update_refactor_in_list(refactor_list_path, refactor_id, new_status)
351
- if err:
352
- error_out("Failed to update .prizmkit/plans/refactor-list.json: {}".format(err))
353
- return
354
- else:
355
- rs["retry_count"] = rs.get("retry_count", 0) + 1
356
-
357
- cleaned = cleanup_refactor_artifacts(
358
- state_dir=state_dir,
359
- refactor_id=refactor_id,
360
- project_root=args.project_root,
361
- )
362
-
363
- if rs["retry_count"] >= max_retries:
364
- new_status = "failed"
365
- else:
366
- new_status = "pending"
367
-
368
- rs["resume_from_phase"] = None
369
- rs["sessions"] = []
370
- rs["last_session_id"] = None
371
-
372
- err = update_refactor_in_list(refactor_list_path, refactor_id, new_status)
373
- if err:
374
- error_out("Failed to update .prizmkit/plans/refactor-list.json: {}".format(err))
375
- return
376
-
377
- if session_status == "success" and session_id:
378
- sessions = rs.get("sessions", [])
379
- if session_id not in sessions:
380
- sessions.append(session_id)
381
- rs["sessions"] = sessions
382
- rs["last_session_id"] = session_id
383
-
384
- rs["updated_at"] = now_iso()
385
-
386
- err = save_refactor_status(state_dir, refactor_id, rs)
387
- if err:
388
- error_out("Failed to save refactor status: {}".format(err))
389
- return
390
-
391
- # Auto-skip downstream refactors when this refactor is marked as failed or skipped
392
- auto_skipped_refactors = []
393
- if new_status in ("failed", "skipped"):
394
- auto_skipped_refactors = auto_skip_blocked_refactors(
395
- refactor_list_path, state_dir, refactor_id
396
- )
397
-
398
- summary = {
399
- "action": "update",
400
- "refactor_id": refactor_id,
401
- "session_status": session_status,
402
- "new_status": new_status,
403
- "retry_count": rs["retry_count"],
404
- "infra_error_count": rs.get("infra_error_count", 0),
405
- "max_infra_retries": max_infra_retries,
406
- "resume_from_phase": rs.get("resume_from_phase"),
407
- "updated_at": rs["updated_at"],
408
- }
409
- if auto_skipped_refactors:
410
- summary["auto_skipped"] = [info["refactor_id"] for info in auto_skipped_refactors]
411
- if session_status in ("commit_missing", "docs_missing", "merge_conflict"):
412
- summary["degraded_reason"] = session_status
413
- summary["restart_policy"] = "finalization_retry"
414
- elif session_status == "infra_error":
415
- summary["restart_policy"] = "infra_retry"
416
- summary["infra_error_count"] = rs.get("infra_error_count", 0)
417
- summary["artifacts_preserved"] = True
418
- elif session_status != "success":
419
- summary["restart_policy"] = "full_restart"
420
- summary["cleanup_performed"] = cleaned
421
-
422
- print(json.dumps(summary, indent=2, ensure_ascii=False))
423
-
424
-
425
- def _default_project_root():
426
- env = os.environ.get("PROJECT_ROOT")
427
- if env:
428
- return os.path.abspath(env)
429
- script_dir = os.path.dirname(os.path.abspath(__file__))
430
- pipeline_dir = os.path.dirname(script_dir)
431
- pipeline_parent = os.path.dirname(pipeline_dir)
432
- if os.path.basename(pipeline_parent) == ".prizmkit":
433
- return os.path.dirname(pipeline_parent)
434
- return pipeline_parent
435
-
436
-
437
- def cleanup_refactor_artifacts(state_dir, refactor_id, project_root=None):
438
- """Delete intermediate artifacts for a failed refactor run."""
439
- if not project_root:
440
- project_root = _default_project_root()
441
-
442
- cleaned = []
443
-
444
- # 1) Remove all session history
445
- sessions_dir = os.path.join(state_dir, refactor_id, "sessions")
446
- sessions_deleted = 0
447
- if os.path.isdir(sessions_dir):
448
- for entry in os.listdir(sessions_dir):
449
- entry_path = os.path.join(sessions_dir, entry)
450
- if os.path.isdir(entry_path):
451
- shutil.rmtree(entry_path)
452
- sessions_deleted += 1
453
- cleaned.append("Deleted {} session(s) from {}".format(sessions_deleted, sessions_dir))
454
-
455
- # 2) Remove transient files under refactor dir (keep status.json)
456
- refactor_dir = os.path.join(state_dir, refactor_id)
457
- if os.path.isdir(refactor_dir):
458
- for entry in os.listdir(refactor_dir):
459
- if entry == "status.json" or entry == "sessions":
460
- continue
461
- entry_path = os.path.join(refactor_dir, entry)
462
- if os.path.isdir(entry_path):
463
- shutil.rmtree(entry_path)
464
- cleaned.append("Deleted directory {}".format(entry_path))
465
- elif os.path.isfile(entry_path):
466
- os.remove(entry_path)
467
- cleaned.append("Deleted file {}".format(entry_path))
468
-
469
- # 3) Remove refactor artifacts
470
- refactor_artifact_dir = os.path.join(project_root, REFACTOR_ARTIFACTS_REL, refactor_id)
471
- if os.path.isdir(refactor_artifact_dir):
472
- shutil.rmtree(refactor_artifact_dir)
473
- cleaned.append("Deleted {}".format(refactor_artifact_dir))
474
-
475
- # 4) Remove shared dev-team workspace
476
- dev_team_dir = os.path.join(project_root, DEV_TEAM_DIR_NAME)
477
- if os.path.isdir(dev_team_dir):
478
- shutil.rmtree(dev_team_dir)
479
- cleaned.append("Deleted {}".format(dev_team_dir))
480
-
481
- return cleaned
482
-
483
-
484
- def load_session_status(state_dir, refactor_id, session_id):
485
- session_status_path = os.path.join(state_dir, refactor_id, "sessions",
486
- session_id, "session-status.json"
487
- )
488
- data, err = load_json_file(session_status_path)
489
- if err:
490
- return None, err
491
- return data, None
492
-
493
-
494
- # ---------------------------------------------------------------------------
495
- # Auto-skip: cascade failure to blocked downstream refactors
496
- # ---------------------------------------------------------------------------
497
-
498
- def auto_skip_blocked_refactors(refactor_list_path, state_dir, failed_refactor_id):
499
- """Recursively mark all downstream refactors blocked by a failed refactor as auto_skipped.
500
-
501
- When a refactor is marked as failed, any refactor whose dependency chain includes
502
- the failed refactor can never be executed. This function propagates the failure
503
- by marking those blocked refactors as auto_skipped, allowing the pipeline to
504
- continue processing unblocked refactors and eventually reach PIPELINE_COMPLETE.
505
-
506
- Re-reads .prizmkit/plans/refactor-list.json from disk to get the latest state (including the
507
- just-written failed status from update_refactor_in_list).
508
-
509
- NOTE: This function performs a read-modify-write on .prizmkit/plans/refactor-list.json without
510
- file locking. The caller (action_update) also writes to .prizmkit/plans/refactor-list.json
511
- immediately before calling this. Safe for single-pipeline execution, but if
512
- multiple pipeline instances share the same .prizmkit/plans/refactor-list.json concurrently,
513
- a race condition may cause lost writes. Add file locking if parallel pipelines
514
- are introduced.
515
- """
516
- data, err = load_json_file(refactor_list_path)
517
- if err:
518
- return []
519
- refactors = data.get("refactors", [])
520
-
521
- # Build current status map
522
- status_map = {}
523
- for r in refactors:
524
- if isinstance(r, dict) and r.get("id"):
525
- status_map[r["id"]] = r.get("status", "pending")
526
-
527
- # Collect all refactors to auto-skip (recursive propagation)
528
- to_skip = set()
529
- changed = True
530
- while changed:
531
- changed = False
532
- for r in refactors:
533
- if not isinstance(r, dict):
534
- continue
535
- rid = r.get("id")
536
- if not rid or rid in to_skip:
537
- continue
538
- current = status_map.get(rid, "pending")
539
- if current in TERMINAL_STATUSES:
540
- continue
541
- deps = r.get("dependencies", [])
542
- for dep_id in deps:
543
- dep_status = status_map.get(dep_id, "pending")
544
- if dep_status in ("failed", "skipped", "auto_skipped") or dep_id in to_skip:
545
- to_skip.add(rid)
546
- status_map[rid] = "auto_skipped"
547
- changed = True
548
- break
549
-
550
- if not to_skip:
551
- return []
552
-
553
- # Batch-write to .prizmkit/plans/refactor-list.json
554
- for r in refactors:
555
- if isinstance(r, dict) and r.get("id") in to_skip:
556
- r["status"] = "auto_skipped"
557
- write_json_file(refactor_list_path, data)
558
-
559
- # Update timestamps in status.json for each auto-skipped refactor
560
- for rid in to_skip:
561
- rs = load_refactor_status(state_dir, rid)
562
- rs["updated_at"] = now_iso()
563
- save_refactor_status(state_dir, rid, rs)
564
-
565
- # Build blocking reason map for logging
566
- skipped_info = []
567
- for r in refactors:
568
- if not isinstance(r, dict):
569
- continue
570
- rid = r.get("id")
571
- if rid not in to_skip:
572
- continue
573
- deps = r.get("dependencies", [])
574
- blockers = [
575
- d for d in deps
576
- if d == failed_refactor_id or d in to_skip
577
- ]
578
- skipped_info.append({
579
- "refactor_id": rid,
580
- "title": r.get("title", ""),
581
- "blocked_by": blockers,
582
- })
583
-
584
- print(
585
- "[auto-skip] {} refactor(s) auto-skipped due to failed {}:".format(
586
- len(skipped_info), failed_refactor_id
587
- ),
588
- file=sys.stderr,
589
- )
590
- for info in skipped_info:
591
- print(
592
- " {} ({}) — blocked by {}".format(
593
- info["refactor_id"],
594
- info["title"],
595
- ", ".join(info["blocked_by"]),
596
- ),
597
- file=sys.stderr,
598
- )
599
-
600
- return skipped_info
601
-
602
-
603
- # ---------------------------------------------------------------------------
604
- # Action: status
605
- # ---------------------------------------------------------------------------
606
-
607
- COLOR_GREEN = "\033[92m"
608
- COLOR_YELLOW = "\033[93m"
609
- COLOR_RED = "\033[91m"
610
- COLOR_GRAY = "\033[90m"
611
- COLOR_MAGENTA = "\033[95m"
612
- COLOR_CYAN = "\033[96m"
613
- COLOR_BOLD = "\033[1m"
614
- COLOR_RESET = "\033[0m"
615
-
616
- BOX_WIDTH = 72
617
-
618
- TYPE_ICONS = {
619
- "extract": "📦",
620
- "rename": "🏷️",
621
- "restructure": "🏗️",
622
- "simplify": "✂️",
623
- "decouple": "🔗",
624
- "migrate": "🚀",
625
- }
626
-
627
- COMPLEXITY_BADGES = {
628
- "low": COLOR_GREEN + "[LOW]" + COLOR_RESET,
629
- "medium": COLOR_YELLOW + "[MED]" + COLOR_RESET,
630
- "high": COLOR_RED + "[HI]" + COLOR_RESET,
631
- }
632
-
633
-
634
- def action_status(refactor_list_data, state_dir):
635
- refactors = refactor_list_data.get("refactors", [])
636
- project_name = refactor_list_data.get("project_name", "Unknown")
637
-
638
- counts = {"completed": 0, "in_progress": 0, "failed": 0, "pending": 0, "skipped": 0, "auto_skipped": 0}
639
- refactor_lines = []
640
-
641
- for r in refactors:
642
- if not isinstance(r, dict):
643
- continue
644
- rid = r.get("id")
645
- title = r.get("title", "Untitled")
646
- rtype = r.get("type", "restructure")
647
- complexity = r.get("complexity", "medium")
648
- if not rid:
649
- continue
650
-
651
- rstatus = r.get("status", "pending")
652
- rs = load_refactor_status(state_dir, rid)
653
- retry_count = rs.get("retry_count", 0)
654
- max_retries_val = rs.get("max_retries", 3)
655
- resume_phase = rs.get("resume_from_phase")
656
-
657
- if rstatus in counts:
658
- counts[rstatus] += 1
659
- else:
660
- counts["pending"] += 1
661
-
662
- # Status icon
663
- if rstatus == "completed":
664
- icon = COLOR_GREEN + "[✓]" + COLOR_RESET
665
- elif rstatus == "in_progress":
666
- icon = COLOR_YELLOW + "[→]" + COLOR_RESET
667
- elif rstatus == "failed":
668
- icon = COLOR_RED + "[✗]" + COLOR_RESET
669
- elif rstatus == "skipped":
670
- icon = COLOR_GRAY + "[—]" + COLOR_RESET
671
- elif rstatus == "auto_skipped":
672
- icon = COLOR_GRAY + "[⊘]" + COLOR_RESET
673
- else:
674
- icon = COLOR_GRAY + "[ ]" + COLOR_RESET
675
-
676
- # Type badge
677
- type_icon = TYPE_ICONS.get(rtype, "🔧")
678
- type_badge = "[{}]".format(rtype[:6].upper())
679
-
680
- # Complexity badge
681
- cmplx_badge = COMPLEXITY_BADGES.get(complexity, "[MED]")
682
-
683
- # Detail
684
- detail = ""
685
- if rstatus == "in_progress":
686
- parts = []
687
- if retry_count > 0:
688
- parts.append("retry {}/{}".format(retry_count, max_retries_val))
689
- if resume_phase is not None:
690
- parts.append("CP-RF-{}".format(resume_phase))
691
- if parts:
692
- detail = " ({})".format(", ".join(parts))
693
- elif rstatus == "failed":
694
- detail = " (failed after {} retries)".format(retry_count)
695
-
696
- # Colorize title based on status
697
- if rstatus == "completed":
698
- colored_title = COLOR_GREEN + title + COLOR_RESET
699
- elif rstatus == "in_progress":
700
- colored_title = COLOR_YELLOW + title + COLOR_RESET
701
- elif rstatus == "failed":
702
- colored_title = COLOR_RED + title + COLOR_RESET
703
- else:
704
- colored_title = COLOR_GRAY + title + COLOR_RESET
705
-
706
- line_content = "{} {} {} {} {} {} {}{}".format(
707
- rid, icon, type_badge, cmplx_badge, type_icon, colored_title, "", detail
708
- )
709
-
710
- refactor_lines.append(line_content)
711
-
712
- total = len(refactors)
713
- completed = counts["completed"]
714
- percent = round(completed / total * 100, 1) if total > 0 else 0.0
715
- progress_bar = _build_progress_bar(percent, width=24)
716
-
717
- summary_line = "Total: {} refactors | Completed: {} | In Progress: {}".format(
718
- total, completed, counts["in_progress"]
719
- )
720
- summary_line2 = "Failed: {} | Pending: {} | Skipped: {} | Auto-skipped: {}".format(
721
- counts["failed"], counts["pending"], counts["skipped"], counts["auto_skipped"]
722
- )
723
-
724
- inner = BOX_WIDTH - 2
725
- print("╔" + "═" * BOX_WIDTH + "╗")
726
- print("║" + pad_right(COLOR_BOLD + " Refactor Pipeline Status" + COLOR_RESET, inner) + " ║")
727
- print("╠" + "═" * BOX_WIDTH + "╣")
728
- print("║" + pad_right(" Project: {}".format(project_name), inner) + " ║")
729
- print("║" + pad_right(" {}".format(summary_line), inner) + " ║")
730
- print("║" + pad_right(" {}".format(summary_line2), inner) + " ║")
731
- print("╠" + "─" * BOX_WIDTH + "╣")
732
- print("║" + pad_right(" Progress: {}".format(progress_bar), inner) + " ║")
733
- print("╠" + "═" * BOX_WIDTH + "╣")
734
- for line in refactor_lines:
735
- print("║" + pad_right(" {}".format(line), inner) + " ║")
736
- print("╚" + "═" * BOX_WIDTH + "╝")
737
-
738
-
739
- # ---------------------------------------------------------------------------
740
- # Action: reset
741
- # ---------------------------------------------------------------------------
742
-
743
- def action_reset(args, refactor_list_path, state_dir):
744
- refactor_id = args.refactor_id
745
- if not refactor_id:
746
- error_out("--refactor-id is required for 'reset' action")
747
- return
748
-
749
- rs = load_refactor_status(state_dir, refactor_id)
750
- old_status = get_refactor_status_from_list(refactor_list_path, refactor_id)
751
- old_retry = rs.get("retry_count", 0)
752
-
753
- rs["retry_count"] = 0
754
- rs["infra_error_count"] = 0
755
- rs["last_infra_error_session_id"] = None
756
- rs["sessions"] = []
757
- rs["last_session_id"] = None
758
- rs["resume_from_phase"] = None
759
- rs["updated_at"] = now_iso()
760
-
761
- err = save_refactor_status(state_dir, refactor_id, rs)
762
- if err:
763
- error_out("Failed to save refactor status: {}".format(err))
764
- return
765
-
766
- err = update_refactor_in_list(refactor_list_path, refactor_id, "pending")
767
- if err:
768
- error_out("Failed to update .prizmkit/plans/refactor-list.json: {}".format(err))
769
- return
770
-
771
- result = {
772
- "action": "reset",
773
- "refactor_id": refactor_id,
774
- "old_status": old_status,
775
- "old_retry_count": old_retry,
776
- "new_status": "pending",
777
- }
778
- print(json.dumps(result, indent=2, ensure_ascii=False))
779
-
780
-
781
- # ---------------------------------------------------------------------------
782
- # Action: clean
783
- # ---------------------------------------------------------------------------
784
-
785
- def action_clean(args, refactor_list_path, state_dir):
786
- refactor_id = args.refactor_id
787
- project_root = args.project_root
788
-
789
- if not refactor_id:
790
- error_out("--refactor-id is required for 'clean' action")
791
- return
792
- if not project_root:
793
- error_out("--project-root is required for 'clean' action")
794
- return
795
-
796
- cleaned = []
797
-
798
- # 1. Delete session history
799
- sessions_dir = os.path.join(state_dir, refactor_id, "sessions")
800
- sessions_deleted = 0
801
- if os.path.isdir(sessions_dir):
802
- for entry in os.listdir(sessions_dir):
803
- entry_path = os.path.join(sessions_dir, entry)
804
- if os.path.isdir(entry_path):
805
- shutil.rmtree(entry_path)
806
- sessions_deleted += 1
807
- cleaned.append("Deleted {} session(s) from {}".format(sessions_deleted, sessions_dir))
808
-
809
- # 2. Delete refactor artifacts for this refactor
810
- refactor_artifact_dir = os.path.join(project_root, REFACTOR_ARTIFACTS_REL, refactor_id)
811
- if os.path.isdir(refactor_artifact_dir):
812
- shutil.rmtree(refactor_artifact_dir)
813
- cleaned.append("Deleted {}".format(refactor_artifact_dir))
814
-
815
- # 3. Delete shared dev-team workspace
816
- dev_team_dir = os.path.join(project_root, DEV_TEAM_DIR_NAME)
817
- if os.path.isdir(dev_team_dir):
818
- shutil.rmtree(dev_team_dir)
819
- cleaned.append("Deleted {}".format(dev_team_dir))
820
-
821
- # 4. Reset status
822
- rs = load_refactor_status(state_dir, refactor_id)
823
- old_status = get_refactor_status_from_list(refactor_list_path, refactor_id)
824
- old_retry = rs.get("retry_count", 0)
825
-
826
- rs["retry_count"] = 0
827
- rs["infra_error_count"] = 0
828
- rs["last_infra_error_session_id"] = None
829
- rs["sessions"] = []
830
- rs["last_session_id"] = None
831
- rs["resume_from_phase"] = None
832
- rs["updated_at"] = now_iso()
833
-
834
- err = save_refactor_status(state_dir, refactor_id, rs)
835
- if err:
836
- error_out("Failed to save refactor status: {}".format(err))
837
- return
838
-
839
- err = update_refactor_in_list(refactor_list_path, refactor_id, "pending")
840
- if err:
841
- error_out("Failed to update .prizmkit/plans/refactor-list.json: {}".format(err))
842
- return
843
-
844
- result = {
845
- "action": "clean",
846
- "refactor_id": refactor_id,
847
- "old_status": old_status,
848
- "old_retry_count": old_retry,
849
- "new_status": "pending",
850
- "sessions_deleted": sessions_deleted,
851
- "cleaned": cleaned,
852
- }
853
- print(json.dumps(result, indent=2, ensure_ascii=False))
854
-
855
-
856
- # ---------------------------------------------------------------------------
857
- # Action: pause
858
- # ---------------------------------------------------------------------------
859
-
860
- def action_pause(state_dir):
861
- pipeline_path = os.path.join(state_dir, "pipeline.json")
862
- data, err = load_json_file(pipeline_path)
863
- if err:
864
- data = {"status": "paused", "paused_at": now_iso()}
865
- else:
866
- data["status"] = "paused"
867
- data["paused_at"] = now_iso()
868
-
869
- err = write_json_file(pipeline_path, data)
870
- if err:
871
- error_out("Failed to write pipeline.json: {}".format(err))
872
- return
873
-
874
- result = {
875
- "action": "pause",
876
- "status": "paused",
877
- "paused_at": data["paused_at"],
878
- }
879
- print(json.dumps(result, indent=2, ensure_ascii=False))
880
-
881
-
882
- # ---------------------------------------------------------------------------
883
- # Action: start
884
- # ---------------------------------------------------------------------------
885
-
886
- def action_start(args, refactor_list_path, state_dir):
887
- """Mark a refactor as in_progress when a session starts.
888
-
889
- This keeps refactor-list.json/state status in sync during execution,
890
- instead of only updating after session end.
891
- """
892
- refactor_id = args.refactor_id
893
- if not refactor_id:
894
- error_out("--refactor-id is required for 'start' action")
895
- return
896
-
897
- rs = load_refactor_status(state_dir, refactor_id)
898
- old_status = get_refactor_status_from_list(refactor_list_path, refactor_id)
899
-
900
- rs["updated_at"] = now_iso()
901
-
902
- err = save_refactor_status(state_dir, refactor_id, rs)
903
- if err:
904
- error_out("Failed to save refactor status: {}".format(err))
905
- return
906
-
907
- err = update_refactor_in_list(refactor_list_path, refactor_id, "in_progress")
908
- if err:
909
- error_out("Failed to update .prizmkit/plans/refactor-list.json: {}".format(err))
910
- return
911
-
912
- result = {
913
- "action": "start",
914
- "refactor_id": refactor_id,
915
- "old_status": old_status,
916
- "new_status": "in_progress",
917
- "retry_count": rs.get("retry_count", 0),
918
- "infra_error_count": rs.get("infra_error_count", 0),
919
- "updated_at": rs["updated_at"],
920
- }
921
- print(json.dumps(result, indent=2, ensure_ascii=False))
922
-
923
-
924
- # ---------------------------------------------------------------------------
925
- # Action: unskip
926
- # ---------------------------------------------------------------------------
927
-
928
- def action_unskip(args, refactor_list_path, state_dir):
929
- """Recover skipped/auto_skipped/failed refactors by resetting them and their failed upstream.
930
-
931
- Two modes:
932
- - --refactor-id R-001: Reset the specified failed/skipped/auto_skipped refactor + all
933
- downstream auto_skipped refactors whose dependency chain includes it.
934
- If the target is auto_skipped, also walk upstream to find and reset the
935
- failed/skipped ancestor that caused the cascade.
936
- - No --refactor-id: Reset ALL failed, skipped, and auto_skipped refactors to pending.
937
- """
938
- refactor_id = args.refactor_id
939
-
940
- data, err = load_json_file(refactor_list_path)
941
- if err:
942
- error_out("Cannot load refactor list: {}".format(err))
943
- return
944
- refactors = data.get("refactors", [])
945
-
946
- to_reset = set()
947
-
948
- if refactor_id:
949
- # Find the target refactor
950
- target = None
951
- for r in refactors:
952
- if isinstance(r, dict) and r.get("id") == refactor_id:
953
- target = r
954
- break
955
- if not target:
956
- error_out("Refactor '{}' not found in .prizmkit/plans/refactor-list.json".format(refactor_id))
957
- return
958
- if target.get("status") not in ("failed", "skipped", "auto_skipped"):
959
- error_out(
960
- "Refactor '{}' has status '{}', expected 'failed', 'skipped', or 'auto_skipped'".format(
961
- refactor_id, target.get("status", "unknown")
962
- )
963
- )
964
- return
965
-
966
- # If target is failed or skipped, reset it and find all auto_skipped descendants
967
- if target.get("status") in ("failed", "skipped"):
968
- to_reset.add(refactor_id)
969
- # Find all auto_skipped refactors that depend (transitively) on this one
970
- changed = True
971
- while changed:
972
- changed = False
973
- for r in refactors:
974
- if not isinstance(r, dict):
975
- continue
976
- rid = r.get("id")
977
- if not rid or rid in to_reset:
978
- continue
979
- if r.get("status") != "auto_skipped":
980
- continue
981
- deps = r.get("dependencies", [])
982
- if any(d in to_reset for d in deps):
983
- to_reset.add(rid)
984
- changed = True
985
-
986
- # If target is auto_skipped, reset it and its failed upstream + siblings
987
- elif target.get("status") == "auto_skipped":
988
- to_reset.add(refactor_id)
989
- # Transitively walk upstream to find ALL failed/auto_skipped ancestors
990
- # (e.g., R-001 failed → R-002 auto_skipped → R-003 auto_skipped;
991
- # unskip R-003 must also find and reset R-001)
992
- upstream_changed = True
993
- while upstream_changed:
994
- upstream_changed = False
995
- for r in refactors:
996
- if not isinstance(r, dict):
997
- continue
998
- rid = r.get("id")
999
- if not rid or rid not in to_reset:
1000
- continue
1001
- for dep_id in r.get("dependencies", []):
1002
- if dep_id in to_reset:
1003
- continue
1004
- for dep_r in refactors:
1005
- if isinstance(dep_r, dict) and dep_r.get("id") == dep_id:
1006
- if dep_r.get("status") in ("failed", "skipped", "auto_skipped"):
1007
- to_reset.add(dep_id)
1008
- upstream_changed = True
1009
- # Also reset downstream auto_skipped refactors blocked by the same upstreams
1010
- changed = True
1011
- while changed:
1012
- changed = False
1013
- for r in refactors:
1014
- if not isinstance(r, dict):
1015
- continue
1016
- rid = r.get("id")
1017
- if not rid or rid in to_reset:
1018
- continue
1019
- if r.get("status") != "auto_skipped":
1020
- continue
1021
- rdeps = r.get("dependencies", [])
1022
- if any(d in to_reset for d in rdeps):
1023
- to_reset.add(rid)
1024
- changed = True
1025
- else:
1026
- # No refactor-id: reset ALL failed + skipped + auto_skipped
1027
- for r in refactors:
1028
- if isinstance(r, dict) and r.get("id"):
1029
- if r.get("status") in ("failed", "skipped", "auto_skipped"):
1030
- to_reset.add(r["id"])
1031
-
1032
- if not to_reset:
1033
- error_out("No refactors to unskip")
1034
- return
1035
-
1036
- # Reset all collected refactors in refactor-list.json
1037
- reset_details = []
1038
- for r in refactors:
1039
- if isinstance(r, dict) and r.get("id") in to_reset:
1040
- old_status = r.get("status", "unknown")
1041
- r["status"] = "pending"
1042
- reset_details.append({
1043
- "refactor_id": r["id"],
1044
- "title": r.get("title", ""),
1045
- "old_status": old_status,
1046
- })
1047
-
1048
- err = write_json_file(refactor_list_path, data)
1049
- if err:
1050
- error_out("Failed to write .prizmkit/plans/refactor-list.json: {}".format(err))
1051
- return
1052
-
1053
- # Reset runtime fields in status.json for each refactor
1054
- for rid in to_reset:
1055
- rs = load_refactor_status(state_dir, rid)
1056
- rs["retry_count"] = 0
1057
- rs["infra_error_count"] = 0
1058
- rs["last_infra_error_session_id"] = None
1059
- rs["sessions"] = []
1060
- rs["last_session_id"] = None
1061
- rs["resume_from_phase"] = None
1062
- rs["updated_at"] = now_iso()
1063
- save_refactor_status(state_dir, rid, rs)
1064
-
1065
- result = {
1066
- "action": "unskip",
1067
- "reset_count": len(to_reset),
1068
- "refactors": reset_details,
1069
- }
1070
- print(json.dumps(result, indent=2, ensure_ascii=False))
1071
-
1072
-
1073
- # ---------------------------------------------------------------------------
1074
- # Main
1075
- # ---------------------------------------------------------------------------
1076
-
1077
- def main():
1078
- args = parse_args()
1079
-
1080
- if args.action == "update":
1081
- if not args.refactor_id:
1082
- error_out("--refactor-id is required for 'update' action")
1083
- if not args.session_status:
1084
- error_out("--session-status is required for 'update' action")
1085
- if args.action in ("start", "reset", "clean", "complete"):
1086
- if not args.refactor_id:
1087
- error_out("--refactor-id is required for '{}' action".format(args.action))
1088
- if args.action == "clean":
1089
- if not args.project_root:
1090
- error_out("--project-root is required for 'clean' action")
1091
-
1092
- refactor_list_data, err = load_json_file(args.refactor_list)
1093
- if err:
1094
- error_out("Cannot load refactor list: {}".format(err))
1095
-
1096
- if args.action == "get_next":
1097
- action_get_next(refactor_list_data, args.state_dir)
1098
- elif args.action == "update":
1099
- action_update(args, args.refactor_list, args.state_dir)
1100
- elif args.action == "status":
1101
- action_status(refactor_list_data, args.state_dir)
1102
- elif args.action == "reset":
1103
- action_reset(args, args.refactor_list, args.state_dir)
1104
- elif args.action == "clean":
1105
- action_clean(args, args.refactor_list, args.state_dir)
1106
- elif args.action == "start":
1107
- action_start(args, args.refactor_list, args.state_dir)
1108
- elif args.action == "pause":
1109
- action_pause(args.state_dir)
1110
- elif args.action == "unskip":
1111
- action_unskip(args, args.refactor_list, args.state_dir)
1112
- elif args.action == "complete":
1113
- # Shortcut: 'complete' is equivalent to 'update --session-status success'
1114
- args.session_status = "success"
1115
- action_update(args, args.refactor_list, args.state_dir)
1116
-
1117
-
1118
- if __name__ == "__main__":
1119
- main()