karajan-code 4.70.4 → 5.0.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 (380) hide show
  1. package/README.md +2 -2
  2. package/package.json +6 -14
  3. package/packages/hu-board/package.json +1 -1
  4. package/packages/hu-board/public/app.js +4 -18
  5. package/packages/hu-board/public/index.html +5 -2
  6. package/packages/hu-board/public/styles.css +26 -0
  7. package/packages/hu-board/public/utils/api.js +0 -74
  8. package/packages/hu-board/public/utils/board-tour.js +62 -0
  9. package/packages/hu-board/public/utils/board-view.js +49 -144
  10. package/packages/hu-board/public/utils/command-launcher.js +8 -70
  11. package/packages/hu-board/public/utils/formatters.js +10 -0
  12. package/packages/hu-board/public/utils/governance-view.js +13 -1
  13. package/packages/hu-board/public/utils/hu-actions.js +17 -68
  14. package/packages/hu-board/public/utils/init-listeners.js +7 -8
  15. package/packages/hu-board/public/utils/log-panel.js +3 -16
  16. package/packages/hu-board/public/utils/maggle-mode.js +2 -12
  17. package/packages/hu-board/public/utils/modals.js +7 -0
  18. package/packages/hu-board/public/utils/project-picker-view.js +1 -1
  19. package/packages/hu-board/public/utils/server-push.js +3 -22
  20. package/packages/hu-board/public/utils/shared-board-notice.js +33 -0
  21. package/packages/hu-board/public/utils/story-detail-view.js +5 -19
  22. package/packages/hu-board/src/cleanup-zombies.js +0 -1
  23. package/packages/hu-board/src/command-runner.js +36 -25
  24. package/packages/hu-board/src/db-connection.js +282 -0
  25. package/packages/hu-board/src/db-paths.js +113 -0
  26. package/packages/hu-board/src/db-queries.js +188 -0
  27. package/packages/hu-board/src/db-tombstones.js +51 -0
  28. package/packages/hu-board/src/db.js +28 -619
  29. package/packages/hu-board/src/ephemeral-cleaner.js +2 -3
  30. package/packages/hu-board/src/hu-zombie-reaper.js +5 -1
  31. package/packages/hu-board/src/plan-mutations.js +3 -153
  32. package/packages/hu-board/src/plans-service.js +55 -0
  33. package/packages/hu-board/src/routes/api/commands.js +122 -0
  34. package/packages/hu-board/src/routes/api/plans.js +55 -0
  35. package/packages/hu-board/src/routes/api/projects.js +267 -0
  36. package/packages/hu-board/src/routes/api/prompts.js +135 -0
  37. package/packages/hu-board/src/routes/api/sessions.js +95 -0
  38. package/packages/hu-board/src/routes/api/stories.js +183 -0
  39. package/packages/hu-board/src/routes/api/system.js +241 -0
  40. package/packages/hu-board/src/routes/api/tombstones.js +38 -0
  41. package/packages/hu-board/src/routes/api.js +24 -1371
  42. package/packages/hu-board/src/routes/governance.js +23 -1
  43. package/packages/hu-board/src/routes/lanes.js +40 -0
  44. package/packages/hu-board/src/routes/rag.js +4 -3
  45. package/packages/hu-board/src/server.js +20 -34
  46. package/packages/hu-board/src/sync-files.js +318 -0
  47. package/packages/hu-board/src/sync-project.js +99 -0
  48. package/packages/hu-board/src/sync.js +22 -566
  49. package/packages/hu-board/src/zombie-reaper.js +1 -1
  50. package/scripts/dual-publish.mjs +19 -3
  51. package/scripts/postinstall.js +15 -2
  52. package/scripts/verify-pack-mcp.mjs +11 -7
  53. package/scripts/verify-pack.mjs +4 -4
  54. package/src/audit/audit-history.js +3 -2
  55. package/src/audit/dead-exports.js +68 -59
  56. package/src/audit/deterministic-summary.js +33 -13
  57. package/src/audit/npm-signatures.js +41 -0
  58. package/src/audit/sbom.js +35 -0
  59. package/src/checks/agent-token.js +112 -0
  60. package/src/checks/dir-setup.js +34 -1
  61. package/src/checks/native-build.js +21 -39
  62. package/src/checks/runner.js +128 -142
  63. package/src/cli/advanced-commands.js +6 -6
  64. package/src/cli/register-meta.js +42 -82
  65. package/src/cli/register-pipeline.js +8 -143
  66. package/src/cli/register-plan.js +9 -100
  67. package/src/cli/retired-commands.js +49 -0
  68. package/src/cli.js +18 -5
  69. package/src/commands/agent-run.js +40 -26
  70. package/src/commands/audit.js +127 -124
  71. package/src/commands/board.js +5 -9
  72. package/src/commands/check.js +29 -16
  73. package/src/commands/doctor.js +2 -0
  74. package/src/commands/env.js +176 -150
  75. package/src/commands/go.js +71 -53
  76. package/src/commands/harden.js +90 -81
  77. package/src/commands/hu-start.js +52 -0
  78. package/src/commands/hu.js +288 -221
  79. package/src/commands/identity.js +111 -78
  80. package/src/commands/init-atril.js +47 -0
  81. package/src/commands/init.js +11 -40
  82. package/src/commands/install-tools.js +70 -85
  83. package/src/commands/main-guard.js +78 -0
  84. package/src/commands/policy.js +226 -184
  85. package/src/commands/qmd.js +27 -21
  86. package/src/commands/rag.js +75 -48
  87. package/src/commands/review-gate.js +421 -341
  88. package/src/commands/start.js +4 -5
  89. package/src/commands/steward.js +96 -47
  90. package/src/commands/tournament.js +46 -37
  91. package/src/commands/worktree.js +94 -25
  92. package/src/config/loader.js +34 -17
  93. package/src/config/secrets.js +36 -0
  94. package/src/config.js +1 -0
  95. package/src/environment/adr.js +16 -2
  96. package/src/git/karajan-label.js +20 -8
  97. package/src/guards/main-guard.js +54 -0
  98. package/src/harden/hook-templates.js +16 -1
  99. package/src/harden/sentinel/posttooluse.mjs +18 -6
  100. package/src/harden/sentinel/pretooluse-sentinel.mjs +64 -36
  101. package/src/harden/sentinel/sentinel-lib.mjs +129 -26
  102. package/src/harden/sentinel/sentinel-shell.mjs +5 -16
  103. package/src/harden/sentinel/sessionstart.mjs +3 -2
  104. package/src/harden/sentinel/stop.mjs +5 -4
  105. package/src/harden/workflow-templates.js +1 -1
  106. package/src/hu/board-lookup.js +29 -0
  107. package/src/hu/gh-identity.js +23 -0
  108. package/src/hu/github-board.js +4 -2
  109. package/src/hu/lane-prune.js +15 -7
  110. package/src/hu/lane-setup.js +65 -0
  111. package/src/hu/lanes.js +66 -0
  112. package/src/hu/team-board-mirror.js +3 -2
  113. package/src/infrastructure/command-runner.js +1 -1
  114. package/src/infrastructure/file-system-service.js +1 -1
  115. package/src/mcp/handlers/direct-handlers.js +2 -292
  116. package/src/mcp/handlers/hu-handlers.js +1 -35
  117. package/src/mcp/handlers/management-handlers.js +2 -42
  118. package/src/mcp/server-handlers.js +16 -22
  119. package/src/mcp/tools.js +1 -196
  120. package/src/plan/lane-plans.js +54 -0
  121. package/src/plan/plan-store.js +7 -4
  122. package/src/policy/add.js +26 -12
  123. package/src/policy/adr-number-check.js +31 -0
  124. package/src/prompts/audit.js +299 -339
  125. package/src/prompts/card-context.js +10 -5
  126. package/src/prompts/reviewer.js +5 -2
  127. package/src/rag/auto-update.js +56 -43
  128. package/src/rag/bootstrap-index.js +28 -54
  129. package/src/rag/migrate.js +1 -1
  130. package/src/rag/onnx-fallback.js +2 -2
  131. package/src/rag/pid-lease.js +70 -0
  132. package/src/rag/project-store.js +2 -12
  133. package/src/review/card-first.js +57 -46
  134. package/src/review/gate-gitignore.js +23 -4
  135. package/src/review/gate-hook.js +12 -4
  136. package/src/review/one-shot-review.js +45 -35
  137. package/src/review/publish-pr.js +14 -2
  138. package/src/review/repo-docs.js +73 -0
  139. package/src/review/repo-stack.js +59 -0
  140. package/src/review/reviewer-fallback.js +19 -4
  141. package/src/review/seal-commit.js +29 -0
  142. package/src/review/sonar-pregate.js +59 -44
  143. package/src/review/third-party-review.js +90 -16
  144. package/src/review/third-party-size.js +43 -0
  145. package/src/review/third-party-skills.js +54 -0
  146. package/src/review/verify-pr.js +1 -24
  147. package/src/roles/audit-role.js +106 -125
  148. package/src/skills/atril-skills.js +5 -4
  149. package/src/sonar/scanner.js +116 -101
  150. package/src/steward/invariants.js +5 -4
  151. package/src/steward/phantom-sweep.js +66 -0
  152. package/src/tournament/judge.js +60 -53
  153. package/src/utils/gh-account.js +37 -0
  154. package/src/utils/git.js +0 -13
  155. package/src/utils/home-migration.js +7 -1
  156. package/src/utils/main-checkout.js +53 -0
  157. package/src/utils/qmd-collection.js +3 -1
  158. package/src/utils/welcome.js +3 -3
  159. package/templates/{skills → atril/commands}/kj-architect.md +5 -0
  160. package/templates/{skills → atril/commands}/kj-audit.md +5 -0
  161. package/templates/{skills → atril/commands}/kj-board.md +5 -0
  162. package/templates/{skills → atril/commands}/kj-code.md +5 -0
  163. package/templates/{skills → atril/commands}/kj-csv-transform.md +5 -0
  164. package/templates/{skills → atril/commands}/kj-data-report.md +5 -0
  165. package/templates/{skills → atril/commands}/kj-discover.md +5 -0
  166. package/templates/{skills → atril/commands}/kj-rag-query.md +5 -0
  167. package/templates/{skills → atril/commands}/kj-review.md +5 -0
  168. package/templates/{skills → atril/commands}/kj-security.md +5 -0
  169. package/templates/{skills → atril/commands}/kj-sonar.md +5 -0
  170. package/templates/{skills → atril/commands}/kj-sql-analysis.md +5 -0
  171. package/templates/{skills → atril/commands}/kj-test.md +5 -0
  172. package/packages/hu-board/public/utils/run-launcher.js +0 -169
  173. package/packages/hu-board/src/run-tracker.js +0 -121
  174. package/src/activity-log.js +0 -59
  175. package/src/agents/host-agent.js +0 -38
  176. package/src/agents/model-registry.js +0 -142
  177. package/src/audit/plan-adherence.js +0 -224
  178. package/src/autonomy/arbiter-role.js +0 -71
  179. package/src/autonomy/arbiter.js +0 -22
  180. package/src/autonomy/decider.js +0 -18
  181. package/src/autonomy/decision-resolver.js +0 -58
  182. package/src/autonomy/outcome-report.js +0 -55
  183. package/src/autonomy/stage-ask.js +0 -30
  184. package/src/brain/decision-tracker.js +0 -125
  185. package/src/brain/decisor.js +0 -243
  186. package/src/brain/solomon-consult.js +0 -171
  187. package/src/brain/standby-scheduler.js +0 -8
  188. package/src/budget/comparison.js +0 -96
  189. package/src/canvas/parse-md.js +0 -238
  190. package/src/canvas/schema.js +0 -101
  191. package/src/canvas/to-flat.js +0 -85
  192. package/src/canvas/validate.js +0 -163
  193. package/src/ci/dispatch.js +0 -99
  194. package/src/ci/index.js +0 -3
  195. package/src/ci/pr-diff.js +0 -26
  196. package/src/cli/register-standby.js +0 -26
  197. package/src/commands/architect.js +0 -111
  198. package/src/commands/autorun.js +0 -49
  199. package/src/commands/researcher.js +0 -54
  200. package/src/commands/resume.js +0 -72
  201. package/src/commands/review.js +0 -89
  202. package/src/commands/run.js +0 -185
  203. package/src/commands/standby.js +0 -117
  204. package/src/commands/status.js +0 -36
  205. package/src/commands/triage.js +0 -78
  206. package/src/commands/undo.js +0 -62
  207. package/src/domains/domain-loader.js +0 -245
  208. package/src/domains/domain-registry.js +0 -140
  209. package/src/domains/domain-synthesizer.js +0 -129
  210. package/src/git/automation.js +0 -433
  211. package/src/git/coder-commit-guard.js +0 -40
  212. package/src/git/hu-automation.js +0 -243
  213. package/src/git/hu-snapshot.js +0 -10
  214. package/src/git/symlink-targets.js +0 -57
  215. package/src/golden/asserter.js +0 -92
  216. package/src/golden/loader.js +0 -52
  217. package/src/golden/runner.js +0 -92
  218. package/src/golden/schema.js +0 -41
  219. package/src/guards/duplicate-members.js +0 -86
  220. package/src/guards/intent-guard.js +0 -161
  221. package/src/guards/perf-guard.js +0 -126
  222. package/src/guards/policy-guard.js +0 -90
  223. package/src/guards/policy-resolver.js +0 -85
  224. package/src/guards/secret-redactor.js +0 -71
  225. package/src/hu/acceptance-runner.js +0 -138
  226. package/src/hu/lazy-planner.js +0 -109
  227. package/src/hu/parallel-executor.js +0 -94
  228. package/src/hu/routing-metrics.js +0 -17
  229. package/src/hu/split-validator.js +0 -143
  230. package/src/hu/splitting-detector.js +0 -158
  231. package/src/hu/splitting-generator.js +0 -175
  232. package/src/hu/store.js +0 -394
  233. package/src/infrastructure/mocks.js +0 -182
  234. package/src/mcp/handlers/run-handler.js +0 -318
  235. package/src/mcp/sovereignty-guard.js +0 -113
  236. package/src/mcp/tool-arg-normalizers.js +0 -16
  237. package/src/mutate/reviewer-signal.js +0 -76
  238. package/src/orchestrator/agent-fallback.js +0 -81
  239. package/src/orchestrator/brain-coordinator.js +0 -186
  240. package/src/orchestrator/ci-integration.js +0 -139
  241. package/src/orchestrator/config-init.js +0 -426
  242. package/src/orchestrator/direct-actions.js +0 -217
  243. package/src/orchestrator/drivers/error-recovery.js +0 -287
  244. package/src/orchestrator/drivers/init-context.js +0 -238
  245. package/src/orchestrator/drivers/iteration-loop.js +0 -382
  246. package/src/orchestrator/drivers/iteration-phases/coder-and-refactorer.js +0 -69
  247. package/src/orchestrator/drivers/iteration-phases/guards.js +0 -91
  248. package/src/orchestrator/drivers/iteration-phases/handle-approved.js +0 -29
  249. package/src/orchestrator/drivers/iteration-phases/quality-gates.js +0 -125
  250. package/src/orchestrator/drivers/iteration-phases/reviewer-gate.js +0 -62
  251. package/src/orchestrator/drivers/post-loop.js +0 -404
  252. package/src/orchestrator/drivers/pre-loop-phases/auto-hu-batch.js +0 -137
  253. package/src/orchestrator/drivers/pre-loop-phases/config-deprecations.js +0 -47
  254. package/src/orchestrator/drivers/pre-loop-phases/ensure-addyosmani-skills.js +0 -84
  255. package/src/orchestrator/drivers/pre-loop-phases/inject-loaded-plan.js +0 -393
  256. package/src/orchestrator/drivers/pre-loop.js +0 -524
  257. package/src/orchestrator/drivers/run-hu-batch.js +0 -468
  258. package/src/orchestrator/feedback-enrichment.js +0 -140
  259. package/src/orchestrator/feedback-queue.js +0 -151
  260. package/src/orchestrator/flow-control.js +0 -170
  261. package/src/orchestrator/flow-runner.js +0 -365
  262. package/src/orchestrator/fs-leak-detector.js +0 -228
  263. package/src/orchestrator/hu-scheduler.js +0 -114
  264. package/src/orchestrator/hu-sub-pipeline.js +0 -642
  265. package/src/orchestrator/iteration-gate.js +0 -73
  266. package/src/orchestrator/iteration-stages.js +0 -9
  267. package/src/orchestrator/parallel-limiter.js +0 -74
  268. package/src/orchestrator/pipeline-context.js +0 -72
  269. package/src/orchestrator/post-loop-stages.js +0 -468
  270. package/src/orchestrator/pre-loop-stages.js +0 -11
  271. package/src/orchestrator/preflight-checks.js +0 -487
  272. package/src/orchestrator/repair/repair-detector.js +0 -117
  273. package/src/orchestrator/repair/repair-runner.js +0 -142
  274. package/src/orchestrator/reviewer-fallback.js +0 -45
  275. package/src/orchestrator/role-output-compressor.js +0 -189
  276. package/src/orchestrator/session-journal.js +0 -308
  277. package/src/orchestrator/solomon-escalation.js +0 -331
  278. package/src/orchestrator/solomon-rules.js +0 -212
  279. package/src/orchestrator/stages/acceptance-coverage-stage.js +0 -47
  280. package/src/orchestrator/stages/architect-stage.js +0 -172
  281. package/src/orchestrator/stages/coder-stage.js +0 -506
  282. package/src/orchestrator/stages/domain-curator-stage.js +0 -82
  283. package/src/orchestrator/stages/format-stage.js +0 -61
  284. package/src/orchestrator/stages/hu-reviewer-phases/detect-and-apply-splits.js +0 -127
  285. package/src/orchestrator/stages/hu-reviewer-stage.js +0 -419
  286. package/src/orchestrator/stages/perf-stage.js +0 -140
  287. package/src/orchestrator/stages/planner-stage.js +0 -85
  288. package/src/orchestrator/stages/rag-context-stage.js +0 -80
  289. package/src/orchestrator/stages/rag-preload-decisor.js +0 -58
  290. package/src/orchestrator/stages/research-stage.js +0 -69
  291. package/src/orchestrator/stages/reviewer-stage.js +0 -431
  292. package/src/orchestrator/stages/sonar-stage.js +0 -439
  293. package/src/orchestrator/stages/stage-classes.js +0 -84
  294. package/src/orchestrator/stages/stage-executor.js +0 -155
  295. package/src/orchestrator/stages/suite-green-stage.js +0 -62
  296. package/src/orchestrator/stages/tdd-discipline-stage.js +0 -56
  297. package/src/orchestrator/stages/tool-judge-stage.js +0 -53
  298. package/src/orchestrator/stages/triage-stage.js +0 -172
  299. package/src/orchestrator/standby.js +0 -71
  300. package/src/orchestrator/verification-gate.js +0 -183
  301. package/src/orchestrator.js +0 -22
  302. package/src/plan/adr-generator.js +0 -170
  303. package/src/plan/adr-loader.js +0 -60
  304. package/src/plan/plan-executor.js +0 -100
  305. package/src/plan/plan-validation.js +0 -4
  306. package/src/prompts/acceptance-coverage.js +0 -32
  307. package/src/prompts/arbiter.js +0 -38
  308. package/src/prompts/architect.js +0 -103
  309. package/src/prompts/hu-reviewer.js +0 -244
  310. package/src/prompts/tool-correctness-judge.js +0 -31
  311. package/src/prompts/triage.js +0 -57
  312. package/src/rag/embedder.js +0 -2
  313. package/src/rag/embedders/_cloud-base.js +0 -2
  314. package/src/rag/embedders/cohere.js +0 -2
  315. package/src/rag/embedders/mistral.js +0 -2
  316. package/src/rag/embedders/onnx.js +0 -2
  317. package/src/rag/embedders/openai.js +0 -2
  318. package/src/rag/embedders/voyage.js +0 -2
  319. package/src/rag/rerank.js +0 -4
  320. package/src/rag/where-parser.js +0 -4
  321. package/src/repeat-detector.js +0 -88
  322. package/src/review/diff-generator.js +0 -112
  323. package/src/review/git-stash-helper.js +0 -104
  324. package/src/review/schema.js +0 -31
  325. package/src/review/scope-filter.js +0 -152
  326. package/src/review/snapshot-diff.js +0 -122
  327. package/src/review/tdd-discipline.js +0 -90
  328. package/src/review/tdd-policy.js +0 -69
  329. package/src/roles/acceptance-coverage-role.js +0 -78
  330. package/src/roles/architect-role.js +0 -77
  331. package/src/roles/coder-role.js +0 -113
  332. package/src/roles/commiter-role.js +0 -113
  333. package/src/roles/domain-curator-role.js +0 -134
  334. package/src/roles/hu-reviewer-role.js +0 -64
  335. package/src/roles/impeccable-role.js +0 -85
  336. package/src/roles/index.js +0 -18
  337. package/src/roles/karajan-brain-role.js +0 -134
  338. package/src/roles/perf-role.js +0 -122
  339. package/src/roles/planner-role.js +0 -151
  340. package/src/roles/refactorer-role.js +0 -30
  341. package/src/roles/repairer-role.js +0 -181
  342. package/src/roles/researcher-role.js +0 -70
  343. package/src/roles/reviewer-role.js +0 -115
  344. package/src/roles/security-role.js +0 -73
  345. package/src/roles/solomon-role.js +0 -271
  346. package/src/roles/sonar-role.js +0 -72
  347. package/src/roles/tester-role.js +0 -235
  348. package/src/roles/tool-correctness-judge-role.js +0 -78
  349. package/src/roles/triage-role.js +0 -99
  350. package/src/session/journal/decisions-writer.js +0 -200
  351. package/src/session/journal/iteration-logger.js +0 -194
  352. package/src/session/journal/summary-writer.js +0 -320
  353. package/src/session/journal/tree-writer.js +0 -164
  354. package/src/session/journal/write-all.js +0 -89
  355. package/src/session-cleanup.js +0 -116
  356. package/src/skills/semantic-detector.js +0 -167
  357. package/src/skills/skill-detector.js +0 -385
  358. package/src/sonar/cloud-scanner.js +0 -78
  359. package/src/tracker-bootstrap.js +0 -44
  360. package/src/types/index.js +0 -38
  361. package/src/types/policy.js +0 -43
  362. package/src/types/solomon.js +0 -87
  363. package/src/utils/async-lock.js +0 -31
  364. package/src/utils/budget.js +0 -229
  365. package/src/utils/cwd-confirm.js +0 -39
  366. package/src/utils/display/event-handlers.js +0 -403
  367. package/src/utils/display/formatters.js +0 -132
  368. package/src/utils/display/header.js +0 -47
  369. package/src/utils/display/session-summary.js +0 -118
  370. package/src/utils/display/solomon.js +0 -42
  371. package/src/utils/pricing.js +0 -29
  372. package/src/utils/quota-simulator.js +0 -56
  373. package/src/utils/role-assigner.js +0 -137
  374. package/src/utils/rtk-wrapper.js +0 -87
  375. package/src/utils/run-registry.js +0 -9
  376. package/src/utils/status-dashboard.js +0 -254
  377. package/src/utils/tool-call-extractor.js +0 -56
  378. package/src/webperf/devtools-detect.js +0 -112
  379. package/src/webperf/webperf-role-integration.js +0 -66
  380. package/templates/skills/kj-run.md +0 -73
@@ -1,140 +0,0 @@
1
- /**
2
- * PerfStage — webperf quality gate inside the iteration loop.
3
- *
4
- * KJC-TSK-0151. Wraps PerfRole and slots into the existing
5
- * runQualityGateStages flow alongside Sonar and Impeccable. Designed
6
- * to be the simplest possible quality gate:
7
- *
8
- * - PASS verdict (cwv.pass === true) → return ok, iteration continues.
9
- * - FAIL verdict → set reviewer feedback with the blocking metrics
10
- * so the coder receives concrete guidance next iteration. Returns
11
- * `continue` to retry the iteration loop. No repeat-detector +
12
- * retry-limit machinery: rerunning Lighthouse on the same URL
13
- * gives the same result unless the coder changes something, and
14
- * the iteration limit (max_iterations) is the natural ceiling.
15
- * - Scanner unavailable (lighthouse missing, URL unreachable, timeout)
16
- * → log a warn and return ok-skipped. Best-effort, never blocks
17
- * the pipeline by itself.
18
- *
19
- * The role surface (PerfRole) is responsible for persisting the result
20
- * to ~/.karajan/webperf/<slug>/last.json so subsequent `kj audit` runs
21
- * pick it up via the auto-discovery added in #602.
22
- */
23
-
24
- import { PerfRole } from "../../roles/perf-role.js";
25
- import { setReviewerFeedback } from "../../session/mutators.js";
26
- import { saveSession } from "../../session/store.js";
27
- import { emitProgress, makeEvent } from "../../utils/events.js";
28
-
29
- /**
30
- * Build the human-readable feedback line that goes back to the coder
31
- * on FAIL. Concrete enough that the LLM can act on it without re-reading
32
- * the whole report.
33
- */
34
- function buildFeedback(roleResult) {
35
- const { result } = roleResult;
36
- const score = typeof result.performanceScore === "number" ? result.performanceScore : null;
37
- const blocking = (result.cwv?.blocking || []).map(b => `${b.metric.toUpperCase()}=${Math.round(b.value)} (poor>${b.threshold})`);
38
- const top = (result.issues || []).slice(0, 3).map(i => `${i.id}${i.savingsMs ? ` (~${Math.round(i.savingsMs)}ms)` : ""}`);
39
-
40
- const lines = [`Webperf gate FAILED${score !== null ? ` (score ${score}/100)` : ""}.`];
41
- if (blocking.length > 0) lines.push(`Blocking metrics: ${blocking.join(", ")}.`);
42
- if (top.length > 0) lines.push(`Top opportunities: ${top.join(", ")}.`);
43
- lines.push("Address the blocking metric(s) before the next iteration; rerunning without code changes will produce the same verdict.");
44
- return lines.join(" ");
45
- }
46
-
47
- /**
48
- * Run the perf gate against config.webperf.url.
49
- *
50
- * @returns {Promise<{action: "ok"|"continue", stageResult?: object, summary?: string}>}
51
- */
52
- export async function runPerfStage({ config, logger, emitter, eventBase, session, trackBudget, iteration, task: _task, brainCtx }) {
53
- if (!session) {
54
- throw new Error("runPerfStage: `session` is required.");
55
- }
56
- logger.setContext({ iteration, stage: "perf" });
57
- emitProgress(
58
- emitter,
59
- makeEvent("perf:start", { ...eventBase, stage: "perf" }, {
60
- message: "WebPerf gate scanning",
61
- detail: { url: config?.webperf?.url || null, preset: config?.webperf?.preset || "desktop" },
62
- })
63
- );
64
-
65
- const role = new PerfRole({ config, logger, emitter });
66
- const roleResult = await role.execute();
67
-
68
- // Track budget — the role doesn't spawn an LLM but it does consume wall
69
- // time; surface that in the budget summary alongside the agent calls.
70
- if (trackBudget) {
71
- try { trackBudget("perf", { tokens_in: 0, tokens_out: 0, cost_usd: 0 }); } catch { /* best-effort */ }
72
- }
73
-
74
- // Scanner unavailable → skip with warn. PerfRole returns ok=false for
75
- // both "verdict FAIL" and "scanner failed", so we differentiate on the
76
- // result.error field (set only by the second case).
77
- if (!roleResult.ok && roleResult.result?.error) {
78
- logger.warn(`Perf gate skipped: ${roleResult.result.error}`);
79
- emitProgress(emitter, makeEvent("perf:end", { ...eventBase, stage: "perf" }, {
80
- status: "warn",
81
- message: `Perf gate skipped — ${roleResult.result.error}`,
82
- }));
83
- return { action: "ok", stageResult: { skipped: true, reason: roleResult.result.error } };
84
- }
85
-
86
- // PASS verdict
87
- if (roleResult.ok === true) {
88
- emitProgress(emitter, makeEvent("perf:end", { ...eventBase, stage: "perf" }, {
89
- status: "ok",
90
- message: roleResult.summary,
91
- }));
92
- return {
93
- action: "ok",
94
- stageResult: {
95
- verdict: "PASS",
96
- url: roleResult.result?.url,
97
- performanceScore: roleResult.result?.performanceScore,
98
- cwv: roleResult.result?.cwv,
99
- savedPath: roleResult.result?.savedPath,
100
- summary: roleResult.summary,
101
- },
102
- };
103
- }
104
-
105
- // FAIL verdict → push concrete feedback to the coder for next iteration.
106
- const feedback = buildFeedback(roleResult);
107
- setReviewerFeedback(session, feedback);
108
- await saveSession(session);
109
-
110
- // Brain: when enabled, surface perf feedback on the queue too.
111
- if (brainCtx?.enabled) {
112
- try {
113
- const { processRoleOutput } = await import("../brain-coordinator.js");
114
- processRoleOutput(brainCtx, {
115
- roleName: "perf",
116
- output: { verdict: "fail", summary: feedback },
117
- iteration,
118
- });
119
- } catch (err) {
120
- logger.warn(`Perf gate: brain queue push failed (non-blocking): ${err.message}`);
121
- }
122
- }
123
-
124
- emitProgress(emitter, makeEvent("perf:end", { ...eventBase, stage: "perf" }, {
125
- status: "fail",
126
- message: roleResult.summary,
127
- }));
128
-
129
- return {
130
- action: "continue",
131
- stageResult: {
132
- verdict: "FAIL",
133
- url: roleResult.result?.url,
134
- performanceScore: roleResult.result?.performanceScore,
135
- cwv: roleResult.result?.cwv,
136
- issues: roleResult.result?.issues,
137
- summary: feedback,
138
- },
139
- };
140
- }
@@ -1,85 +0,0 @@
1
- /**
2
- * Planner stage logic.
3
- * Extracted from pre-loop-stages.js for maintainability.
4
- */
5
-
6
- import { PlannerRole } from "../../roles/planner-role.js";
7
- import { createAgent } from "../../agents/index.js";
8
- import { addCheckpoint, markSessionStatus } from "../../session/store.js";
9
- import { emitProgress, makeEvent, emitAgentOutput } from "../../utils/events.js";
10
- import { parsePlannerOutput } from "../../prompts/planner.js";
11
- import { createStallDetector } from "../../utils/stall-detector.js";
12
-
13
- export async function runPlannerStage({ config, logger, emitter, eventBase, session, plannerRole, researchContext, architectContext = null, triageDecomposition = null, trackBudget }) {
14
- const task = session.task;
15
- logger.setContext({ iteration: 0, stage: "planner" });
16
- emitProgress(
17
- emitter,
18
- makeEvent("planner:start", { ...eventBase, stage: "planner" }, {
19
- message: `Planner (${plannerRole.provider}) running`,
20
- detail: { planner: plannerRole.provider, provider: plannerRole.provider, executorType: "agent" }
21
- })
22
- );
23
-
24
- const plannerOnOutput = (payload) => emitAgentOutput(emitter, eventBase, "planner", plannerRole.provider, payload);
25
- const plannerStall = createStallDetector({
26
- onOutput: plannerOnOutput, emitter, eventBase, stage: "planner", provider: plannerRole.provider
27
- });
28
-
29
- const planRole = new PlannerRole({ config, logger, emitter, createAgentFn: createAgent });
30
- planRole.context = { task, research: researchContext, architecture: architectContext, triageDecomposition };
31
- await planRole.init();
32
- const plannerStart = Date.now();
33
- let planResult;
34
- try {
35
- planResult = await planRole.execute({ task, onOutput: plannerStall.onOutput });
36
- } catch (err) {
37
- logger.warn(`Planner threw: ${err.message}`);
38
- planResult = { ok: false, result: { error: err.message }, summary: `Planner error: ${err.message}` };
39
- } finally {
40
- plannerStall.stop();
41
- }
42
- trackBudget({ role: "planner", provider: plannerRole.provider, model: plannerRole.model, result: planResult.result, duration_ms: Date.now() - plannerStart });
43
- await addCheckpoint(session, {
44
- stage: "planner",
45
- iteration: 0,
46
- ok: planResult.ok,
47
- provider: plannerRole.provider,
48
- model: plannerRole.model || null
49
- });
50
-
51
- if (!planResult.ok) {
52
- await markSessionStatus(session, "failed");
53
- const details = planResult.result?.error || planResult.summary || "unknown error";
54
- emitProgress(
55
- emitter,
56
- makeEvent("planner:end", { ...eventBase, stage: "planner" }, {
57
- status: "fail",
58
- message: `Planner failed: ${details}`,
59
- detail: { provider: plannerRole.provider, executorType: "agent" }
60
- })
61
- );
62
- throw new Error(`Planner failed: ${details}`);
63
- }
64
-
65
- const planOutput = planResult.result?.plan || "";
66
- const plannedTask = planOutput ? `${task}\n\nExecution plan:\n${planOutput}` : task;
67
- const parsedPlan = parsePlannerOutput(planOutput);
68
- const stageResult = {
69
- ok: true,
70
- title: parsedPlan?.title || null,
71
- approach: parsedPlan?.approach || null,
72
- steps: parsedPlan?.steps || [],
73
- completedSteps: []
74
- };
75
-
76
- emitProgress(
77
- emitter,
78
- makeEvent("planner:end", { ...eventBase, stage: "planner" }, {
79
- message: "Planner completed",
80
- detail: { provider: plannerRole.provider, executorType: "agent" }
81
- })
82
- );
83
-
84
- return { plannedTask, stageResult };
85
- }
@@ -1,80 +0,0 @@
1
- // KJC-PCS-0049 Camino C — pre-loop RAG retrieval stage.
2
- // Runs between triage and domainCurator. When `config.rag.preload.enabled`
3
- // is true and the corpus has chunks, queries the retriever with the
4
- // task text and returns a markdown block ready to prepend to the task.
5
- // Failures degrade gracefully (warn + continue); the rest of the pipeline
6
- // never sees an exception from this stage.
7
- import { emitProgress, makeEvent } from "../../utils/events.js";
8
- import { countChunks } from "../../rag/vec-store.js";
9
- import { makeGovernedEmbedder } from "../../rag/governed-embedder.js";
10
- import { query } from "../../rag/retriever.js";
11
- import { openProjectStore } from "../../rag/project-store.js";
12
-
13
- const DEFAULT_TOP_K = 5;
14
- const DEFAULT_SCOPE = "all";
15
- const DEFAULT_SEARCH_MODE = "hybrid";
16
- const DEFAULT_SEARCH_ALPHA = 0.6;
17
- const MAX_CHUNK_CHARS = 600;
18
-
19
- // KJC-TSK-0463 — pull search-time knobs from config so the HU Board
20
- // modal (rag.search.{mode,alpha,rerank}) actually steers retrieval at
21
- // pipeline time. Returns the args object query() expects; unset fields
22
- // fall back to the retriever's own defaults.
23
- export function resolveSearchOpts(config) {
24
- const s = config?.rag?.search ?? {};
25
- const out = {
26
- mode: typeof s.mode === "string" ? s.mode : DEFAULT_SEARCH_MODE,
27
- alpha: Number.isFinite(s.alpha) ? s.alpha : DEFAULT_SEARCH_ALPHA,
28
- };
29
- if (s.rerank && typeof s.rerank === "object") out.rerankOpts = s.rerank;
30
- else if (s.rerank === true) out.rerankOpts = {};
31
- return out;
32
- }
33
-
34
- /**
35
- * Runs the RAG preload stage. Returns:
36
- * { skipped: true, reason } — when disabled / empty / error
37
- * { skipped: false, contextBlock, hits } — markdown block + raw hits
38
- *
39
- * The caller decides whether to mutate `task` with the contextBlock. We
40
- * keep that responsibility at the call site so this module stays pure.
41
- */
42
- export async function runRagContextStage({ config, logger, emitter, eventBase, task }) {
43
- const preload = config?.rag?.preload;
44
- if (!preload?.enabled) return { skipped: true, reason: "disabled" };
45
- if (typeof task !== "string" || task.length === 0) return { skipped: true, reason: "no-task" };
46
- try {
47
- const dim = config?.rag?.embedder?.dim || 768;
48
- // KJC-TSK-0882: el preload que entra en el prompt del coder solo puede traer
49
- // codigo de ESTE proyecto: antes abria el indice de la maquina sin filtrar.
50
- const db = openProjectStore({ projectDir: config?.projectDir || process.cwd(), dim });
51
- try {
52
- if (countChunks(db) === 0) {
53
- logger?.info?.("[rag-preload] corpus is empty, skipping (run `kj rag index` to seed)");
54
- return { skipped: true, reason: "empty" };
55
- }
56
- const topK = preload.topK || DEFAULT_TOP_K;
57
- const scope = preload.scope || DEFAULT_SCOPE;
58
- const embedder = makeGovernedEmbedder(config);
59
- const searchOpts = resolveSearchOpts(config);
60
- const hits = await query(db, embedder, task, { topK, scope, ...searchOpts });
61
- if (hits.length === 0) return { skipped: true, reason: "no-hits" };
62
- const lines = hits.map((h) => {
63
- const label = h.metadata?.hu_id || h.metadata?.symbol || h.metadata?.headingPath?.join(" > ") || "block";
64
- const text = h.text.length > MAX_CHUNK_CHARS ? `${h.text.slice(0, MAX_CHUNK_CHARS)}…` : h.text;
65
- return `### [${h.kind} · ${label}] ${h.source}\n\n${text}`;
66
- });
67
- const contextBlock = `## Prior context from RAG (auto-retrieved, top ${hits.length})\n\n${lines.join("\n\n")}`;
68
- emitProgress(emitter, makeEvent("rag-preload:hits", { ...eventBase, stage: "rag-preload" }, {
69
- message: `RAG preload: injected ${hits.length} chunk(s) into the task context`,
70
- detail: { topK, scope, hits: hits.length, mode: searchOpts.mode, alpha: searchOpts.alpha, rerank: Boolean(searchOpts.rerankOpts) },
71
- }));
72
- return { skipped: false, contextBlock, hits };
73
- } finally {
74
- db.close();
75
- }
76
- } catch (err) {
77
- logger?.warn?.(`[rag-preload] failed (non-blocking): ${err.message}`);
78
- return { skipped: true, reason: "error", error: err.message };
79
- }
80
- }
@@ -1,58 +0,0 @@
1
- // KJC-TSK-0434 — RAG Camino D: Brain decisor heuristic for retrieval.
2
- // Decides WHETHER to pay the cost of running the RAG preload stage based
3
- // on signals from triage + task shape, instead of pre-fetching every run.
4
- //
5
- // Returns `{ pull: boolean, reason: string }`. The pre-loop driver
6
- // skips `runRagContextStage` when `pull === false`.
7
- //
8
- // Policies (config.rag.preload.policy):
9
- // - "always" : pull regardless (back-compat with v2.24.0 behaviour)
10
- // - "never" : never pull (useful for benchmarking, debugging)
11
- // - "auto" : heuristic — pull only when triage signals complexity,
12
- // decomposition, or when the task body is long enough
13
- // to suggest non-trivial scope. Default.
14
-
15
- const DEFAULT_POLICY = "auto";
16
- const COMPLEX_LEVELS = new Set(["complex", "high", "epic"]);
17
- const LONG_TASK_CHARS = 200;
18
-
19
- /**
20
- * @param {object} params
21
- * @param {object} [params.triage] - triage stage result (may be null)
22
- * @param {string} [params.task] - the user task text
23
- * @param {object} [params.config] - full karajan config
24
- * @returns {{ pull: boolean, reason: string }}
25
- */
26
- export function shouldPreloadRag({ triage, task, config } = {}) {
27
- const policy = config?.rag?.preload?.policy || DEFAULT_POLICY;
28
-
29
- if (policy === "always") return { pull: true, reason: "policy:always" };
30
- if (policy === "never") return { pull: false, reason: "policy:never" };
31
-
32
- // policy === "auto" — apply heuristic.
33
- // Brownfield is an explicit user signal — if onboarding produced a
34
- // brief and config marks the project as brownfield, prior context is
35
- // almost always worth pulling.
36
- if (config?.rag?.preload?.brownfield === true) {
37
- return { pull: true, reason: "auto:brownfield" };
38
- }
39
-
40
- // Triage said this is big enough to decompose → multi-HU run benefits
41
- // from prior context fed to researcher/architect/planner.
42
- if (triage?.shouldDecompose === true) {
43
- return { pull: true, reason: "auto:decompose" };
44
- }
45
-
46
- // Triage classified the task as complex / high-effort.
47
- if (triage?.level && COMPLEX_LEVELS.has(String(triage.level).toLowerCase())) {
48
- return { pull: true, reason: "auto:complex" };
49
- }
50
-
51
- // Long task body usually means a brief with context, motivation and
52
- // non-trivial scope — worth checking the RAG.
53
- if (typeof task === "string" && task.length >= LONG_TASK_CHARS) {
54
- return { pull: true, reason: "auto:long-task" };
55
- }
56
-
57
- return { pull: false, reason: "auto:low-value" };
58
- }
@@ -1,69 +0,0 @@
1
- /**
2
- * Researcher stage logic.
3
- * Extracted from pre-loop-stages.js for maintainability.
4
- */
5
-
6
- import { ResearcherRole } from "../../roles/researcher-role.js";
7
- import { addCheckpoint } from "../../session/store.js";
8
- import { emitProgress, makeEvent, emitAgentOutput } from "../../utils/events.js";
9
- import { createStallDetector } from "../../utils/stall-detector.js";
10
-
11
- export async function runResearcherStage({ config, logger, emitter, eventBase, session, coderRole, trackBudget }) {
12
- logger.setContext({ iteration: 0, stage: "researcher" });
13
-
14
- const researcherProvider = config?.roles?.researcher?.provider || coderRole.provider;
15
- emitProgress(
16
- emitter,
17
- makeEvent("researcher:start", { ...eventBase, stage: "researcher" }, {
18
- message: "Researcher investigating codebase",
19
- detail: { researcher: researcherProvider, provider: researcherProvider, executorType: "agent" }
20
- })
21
- );
22
-
23
- const researcherOnOutput = (payload) => emitAgentOutput(emitter, eventBase, "researcher", researcherProvider, payload);
24
- const researcherStall = createStallDetector({
25
- onOutput: researcherOnOutput, emitter, eventBase, stage: "researcher", provider: researcherProvider
26
- });
27
-
28
- const researcher = new ResearcherRole({ config, logger, emitter });
29
- await researcher.init({ task: session.task });
30
- const researchStart = Date.now();
31
- let researchOutput;
32
- try {
33
- researchOutput = await researcher.run({ task: session.task, onOutput: researcherStall.onOutput });
34
- } catch (err) {
35
- logger.warn(`Researcher threw: ${err.message}`);
36
- researchOutput = { ok: false, summary: `Researcher error: ${err.message}`, result: { error: err.message } };
37
- } finally {
38
- researcherStall.stop();
39
- }
40
- trackBudget({
41
- role: "researcher",
42
- provider: config?.roles?.researcher?.provider || coderRole.provider,
43
- model: config?.roles?.researcher?.model || coderRole.model,
44
- result: researchOutput,
45
- duration_ms: Date.now() - researchStart
46
- });
47
-
48
- await addCheckpoint(session, {
49
- stage: "researcher",
50
- iteration: 0,
51
- ok: researchOutput.ok,
52
- provider: config?.roles?.researcher?.provider || coderRole.provider,
53
- model: config?.roles?.researcher?.model || coderRole.model || null
54
- });
55
-
56
- emitProgress(
57
- emitter,
58
- makeEvent("researcher:end", { ...eventBase, stage: "researcher" }, {
59
- status: researchOutput.ok ? "ok" : "fail",
60
- message: researchOutput.ok ? "Research completed" : `Research failed: ${researchOutput.summary}`,
61
- detail: { provider: researcherProvider, executorType: "agent" }
62
- })
63
- );
64
-
65
- const stageResult = { ok: researchOutput.ok, summary: researchOutput.summary || null };
66
- const researchContext = researchOutput.ok ? researchOutput.result : null;
67
-
68
- return { researchContext, stageResult };
69
- }