kenaz 0.3.18 → 0.3.20

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 (329) hide show
  1. package/core/.claude/commands/agent-worker.md +1 -1
  2. package/core/.claude/commands/architect.md +1 -2
  3. package/core/.claude/commands/spec.md +1 -1
  4. package/core/.claude/commands//347/224/242/345/223/201.md +1 -1
  5. package/core/.claude/hooks/__tests__/task-1977-dedupe-guard.test.js +8 -8
  6. package/core/.claude/skills/architect_agent/SKILL.md +11 -92
  7. package/core/.claude/skills/assessment_agent/SKILL.md +0 -1
  8. package/core/.claude/skills/backend_engineer/SKILL.md +3 -6
  9. package/core/.claude/skills/code_reviewer/SKILL.md +1 -1
  10. package/core/.claude/skills/code_reviewer/patterns.yaml +1 -1
  11. package/core/.claude/skills/designer/SKILL.md +3 -6
  12. package/core/.claude/skills/dev_agent/SKILL.md +30 -491
  13. package/core/.claude/skills/developer/SKILL.md +3 -6
  14. package/core/.claude/skills/feature_agent/SKILL.md +3 -17
  15. package/core/.claude/skills/product_manager/SKILL.md +29 -1064
  16. package/core/.claude/skills/qa_engineer/SKILL.md +12 -17
  17. package/core/.claude/skills/spec_optimizer/SKILL.md +25 -275
  18. package/core/.claude/skills/sre_agent/SKILL.md +3 -6
  19. package/core/.collaboration/README.md +2 -3
  20. package/core/.collaboration/core/task-api.js +5 -138
  21. package/core/.collaboration/docs/CLI.md +0 -2
  22. package/core/.failure/INDEX.yaml +6 -40
  23. package/core/.failure/agent-execution/FAIL-013-search-cwd-drift-and-case-mismatch.yaml +1 -1
  24. package/core/.failure/tools/README.md +9 -227
  25. package/core/.formation/bifrost/launch.js +1 -6
  26. package/core/.formation/bifrost/launch.test.js +1 -1
  27. package/core/.formation/bifrost/shared/ansuz-boot-policy.js +3 -3
  28. package/core/.formation/bifrost/shared/ansuz-boot-policy.test.js +1 -2
  29. package/core/.formation/tools/__tests__/arms.test.js +41 -0
  30. package/core/.formation/tools/__tests__/diagnose-bug.test.js +10 -0
  31. package/core/.formation/tools/__tests__/m1-hmap-convid.test.js +1 -124
  32. package/core/.formation/tools/arms.js +48 -0
  33. package/core/.formation/tools/dispatch.js +24 -15
  34. package/core/.formation/tools/kenaz-stats.js +32 -8
  35. package/core/.formation/tools/kenaz-stats.test.js +15 -2
  36. package/core/.formation/tools/loader.js +17 -140
  37. package/core/.formation/tools/post-complete.js +0 -31
  38. package/core/.formation/tools/prompt.js +16 -1
  39. package/core/.formation/tools/prompt.test.js +20 -0
  40. package/core/.rule/INDEX.yaml +0 -18
  41. package/core/.rule/general/agent-workflow.yaml +14 -164
  42. package/core/.rule/general/project-self-containment.yaml +8 -19
  43. package/core/.rule/general/rust-verify-target.yaml +6 -5
  44. package/core/.rule/general/synapse-code-intelligence.yaml +3 -3
  45. package/core/.specialist/Amelia/capability.yaml +12 -12
  46. package/core/.specialist/Amelia/workflow.yaml +2 -2
  47. package/core/.specialist/Ansuz/SYSTEM_DOC.md +20 -578
  48. package/core/.specialist/Ansuz/cognitive_principles.yaml +2 -3
  49. package/core/.specialist/Ansuz/concepts/boot_rules_summary.yaml +0 -1
  50. package/core/.specialist/Ansuz/concepts/deep_knowledge_pointers.yaml +1 -2
  51. package/core/.specialist/Ansuz/core.yaml +6 -108
  52. package/core/.specialist/Ansuz/guards/lesson_guards.yaml +0 -3
  53. package/core/.specialist/Ansuz/identity_contract.yaml +0 -1
  54. package/core/.specialist/Ansuz/knowledge.yaml +0 -4
  55. package/core/.specialist/Ansuz/rule.yaml +0 -1
  56. package/core/.specialist/Ansuz/tools/handoff-session-identity.test.js +6 -150
  57. package/core/.specialist/tests/runtime-discovery/README.md +1 -1
  58. package/core/.specialist/tools/__tests__/task-2374-usage-counter.test.js +1 -12
  59. package/core/.specialist/tools/ansuz-boot-fast.js +7 -4
  60. package/core/.specialist/tools/ansuz-boot-fast.test.js +10 -3
  61. package/core/.specialist/tools/prompt-files.test.js +1 -0
  62. package/core/.specialist/tools/task-bridge.js +1 -66
  63. package/core/.system/README.md +11 -552
  64. package/core/.system/collaboration/README.md +10 -174
  65. package/core/CLAUDE.md +1 -6
  66. package/core/KENAZ_CORE_VERSION +1 -1
  67. package/core/dev/scripts/js-yaml-resolution.test.js +1 -1
  68. package/core/dev/scripts/peer-identity-e2e.js +402 -0
  69. package/core/dev/scripts/peer-identity-e2e.md +47 -0
  70. package/core/dev/scripts/relay-admin.js +94 -0
  71. package/core/dev/scripts/relay-admin.test.js +131 -0
  72. package/core/dev/scripts/run-rust-tests.js +9 -45
  73. package/core/dev/scripts/rust-verify-worktree.js +4 -4
  74. package/core/dev/scripts/verify-target-dir.js +6 -6
  75. package/core/plugins/kenaz/INVENTORY.md +8 -8
  76. package/core/plugins/kenaz/README.md +10 -0
  77. package/core/plugins/kenaz/commands/architect.md +1 -2
  78. package/core/plugins/kenaz/commands/spec.md +1 -1
  79. package/core/plugins/kenaz/commands//347/224/242/345/223/201.md +1 -1
  80. package/core/plugins/kenaz/guidance.md +1 -1
  81. package/core/plugins/kenaz/hooks/kenaz-hook.js +2 -1
  82. package/core/plugins/kenaz/hooks/sdk-gate.js +9 -0
  83. package/core/plugins/kenaz/scripts/kenaz.test.js +15 -3
  84. package/core/plugins/kenaz/scripts/sync.js +1 -1
  85. package/core/plugins/kenaz/scripts/ygg.js +8 -0
  86. package/core/plugins/kenaz/scripts/ygg.test.js +72 -0
  87. package/core/plugins/kenaz/skills/architect_agent/SKILL.md +11 -92
  88. package/core/plugins/kenaz/skills/assessment_agent/SKILL.md +0 -1
  89. package/core/plugins/kenaz/skills/backend_engineer/SKILL.md +3 -6
  90. package/core/plugins/kenaz/skills/code_reviewer/SKILL.md +1 -1
  91. package/core/plugins/kenaz/skills/code_reviewer/patterns.yaml +1 -1
  92. package/core/plugins/kenaz/skills/designer/SKILL.md +3 -6
  93. package/core/plugins/kenaz/skills/dev_agent/SKILL.md +30 -491
  94. package/core/plugins/kenaz/skills/developer/SKILL.md +3 -6
  95. package/core/plugins/kenaz/skills/feature_agent/SKILL.md +3 -17
  96. package/core/plugins/kenaz/skills/product_manager/SKILL.md +29 -1064
  97. package/core/plugins/kenaz/skills/qa_engineer/SKILL.md +12 -17
  98. package/core/plugins/kenaz/skills/spec_optimizer/SKILL.md +25 -275
  99. package/core/plugins/kenaz/skills/sre_agent/SKILL.md +3 -6
  100. package/core/plugins/kenaz-peer/hooks/register.test.ts +32 -0
  101. package/core/plugins/kenaz-peer/hooks/register.ts +9 -0
  102. package/package.json +6 -6
  103. package/core/.claude/commands/archive.md +0 -24
  104. package/core/.claude/commands/init.md +0 -112
  105. package/core/.claude/commands/legacy_dev.md +0 -18
  106. package/core/.claude/commands/product-review.md +0 -131
  107. package/core/.claude/commands/strategy.md +0 -141
  108. package/core/.claude/commands/sunny.md +0 -1
  109. package/core/.claude/commands//347/224/242/345/223/201/346/252/242/350/246/226.md +0 -129
  110. package/core/.claude/commands//351/200/262/345/272/246.md +0 -15
  111. package/core/.claude/hooks/__tests__/substrate.test.js +0 -122
  112. package/core/.claude/hooks/_substrate-paths.js +0 -95
  113. package/core/.claude/hooks/context-check.js +0 -51
  114. package/core/.claude/hooks/fatigue-check.js +0 -52
  115. package/core/.claude/hooks/handoff-snapshot-on-commit.js +0 -154
  116. package/core/.claude/hooks/handoff-snapshot-on-question.js +0 -158
  117. package/core/.claude/hooks/handoff-staleness.js +0 -197
  118. package/core/.claude/hooks/jev-thalamus-context.js +0 -17
  119. package/core/.claude/hooks/jev-thalamus-context.test.js +0 -41
  120. package/core/.claude/hooks/lease-release.js +0 -119
  121. package/core/.claude/hooks/lease-touch.js +0 -96
  122. package/core/.claude/hooks/reflex-feedback.js +0 -5
  123. package/core/.claude/hooks/session-init.ps1 +0 -49
  124. package/core/.claude/hooks/sound-event.js +0 -70
  125. package/core/.claude/hooks/sound-event.sh +0 -37
  126. package/core/.claude/hooks/stream-delta.js +0 -169
  127. package/core/.claude/no-hooks.settings.json +0 -3
  128. package/core/.claude/skills/legacy_dev/SKILL.md +0 -202
  129. package/core/.claude/skills/sunny/SKILL.md +0 -74
  130. package/core/.collaboration/cli/commands/assign.js +0 -39
  131. package/core/.collaboration/cli/commands/claim.js +0 -33
  132. package/core/.collaboration/cli/commands/complete.js +0 -44
  133. package/core/.collaboration/cli/commands/create.js +0 -110
  134. package/core/.collaboration/cli/commands/get.js +0 -83
  135. package/core/.collaboration/cli/commands/index.js +0 -52
  136. package/core/.collaboration/cli/commands/list.js +0 -51
  137. package/core/.collaboration/cli/commands/lock.js +0 -45
  138. package/core/.collaboration/cli/commands/rebuild.js +0 -39
  139. package/core/.collaboration/cli/commands/search.js +0 -61
  140. package/core/.collaboration/cli/commands/stats.js +0 -61
  141. package/core/.collaboration/cli/commands/transfer.js +0 -41
  142. package/core/.collaboration/cli/commands/unlock.js +0 -48
  143. package/core/.collaboration/cli/formatters/help-formatter.js +0 -70
  144. package/core/.collaboration/cli/formatters/index.js +0 -7
  145. package/core/.collaboration/cli/task-cli.js +0 -46
  146. package/core/.collaboration/cli/utils/arg-parser.js +0 -74
  147. package/core/.collaboration/cli/utils/git-user.js +0 -25
  148. package/core/.collaboration/cli/utils/index.js +0 -9
  149. package/core/.collaboration/cli/utils/output.js +0 -10
  150. package/core/.collaboration/config/default.yaml +0 -189
  151. package/core/.collaboration/core/conflict-resolver.js +0 -461
  152. package/core/.collaboration/core/conflict-resolver.test.js +0 -389
  153. package/core/.collaboration/core/migrate-legacy.js +0 -260
  154. package/core/.collaboration/docs/API.md +0 -787
  155. package/core/.collaboration/docs/ARCHITECTURE.md +0 -596
  156. package/core/.collaboration/docs/FAQ.md +0 -695
  157. package/core/.collaboration/docs/MIGRATION.md +0 -804
  158. package/core/.collaboration/docs/examples/README.md +0 -320
  159. package/core/.collaboration/docs/examples/advanced-queries.js +0 -261
  160. package/core/.collaboration/docs/examples/basic-usage.js +0 -184
  161. package/core/.collaboration/docs/examples/team-workflow.js +0 -352
  162. package/core/.failure/agent-execution/FAIL-001-agent-no-output.yaml +0 -391
  163. package/core/.failure/agent-execution/FAIL-007-pm-lead-wrong-team-invocation.yaml +0 -0
  164. package/core/.failure/agent-execution/FAIL-010-phase0-poem-format-skipped.yaml +0 -28
  165. package/core/.failure/agent-execution/FAIL-010-skipping-cognitive-checkpoint-after-verification.yaml +0 -59
  166. package/core/.failure/agent-execution/FAIL-012-grep-shortcut-during-investigation.yaml +0 -85
  167. package/core/.failure/architecture/FAIL-006-python-version-compatibility.yaml +0 -445
  168. package/core/.failure/pipeline/FAIL-003-queue-pollution.yaml +0 -335
  169. package/core/.failure/pipeline/README.md +0 -95
  170. package/core/.failure/retired/FAIL-009-skipping-synapse-pulse-before-code-change.yaml +0 -49
  171. package/core/.failure/tools/USAGE_GUIDE.md +0 -323
  172. package/core/.failure/tools/check_failures.ps1 +0 -387
  173. package/core/.failure/tools/log_failure.ps1 +0 -474
  174. package/core/.formation/.episode-input.json +0 -10
  175. package/core/.formation/.merge-lock +0 -1
  176. package/core/.formation/lead.yaml +0 -118
  177. package/core/.formation/legacy.bak/designer.yaml +0 -57
  178. package/core/.formation/legacy.bak/pm.yaml +0 -57
  179. package/core/.formation/legacy.bak/qa.yaml +0 -57
  180. package/core/.formation/legacy.bak/review.yaml +0 -62
  181. package/core/.formation/legacy.bak/scheduler.yaml +0 -129
  182. package/core/.formation/legacy.bak/sre.yaml +0 -57
  183. package/core/.formation/role-map.yaml +0 -274
  184. package/core/.formation/roles/_shared/modules/code_review.yaml +0 -98
  185. package/core/.formation/roles/_shared/modules/security.yaml +0 -103
  186. package/core/.formation/roles/_shared/modules/testing.yaml +0 -14
  187. package/core/.formation/roles/backend/role.yaml +0 -93
  188. package/core/.formation/roles/code_reviewer/role.yaml +0 -102
  189. package/core/.formation/roles/database_optimizer/role.yaml +0 -107
  190. package/core/.formation/roles/designer/role.yaml +0 -66
  191. package/core/.formation/roles/developer/role.yaml +0 -75
  192. package/core/.formation/roles/frontend/role.yaml +0 -134
  193. package/core/.formation/roles/incident_response/role.yaml +0 -89
  194. package/core/.formation/roles/qa/role.yaml +0 -89
  195. package/core/.formation/roles/security/role.yaml +0 -87
  196. package/core/.formation/roles/sre/role.yaml +0 -66
  197. package/core/.formation/skills/coordinator.yaml +0 -52
  198. package/core/.formation/solo/diagnosis.yaml +0 -78
  199. package/core/.formation/solo/strategy.yaml +0 -121
  200. package/core/.formation/tests/hello.txt +0 -2
  201. package/core/.formation/tools/coordinator.js +0 -350
  202. package/core/.formation/tools/jev-correction.js +0 -214
  203. package/core/.formation/tools/jev-correction.test.js +0 -178
  204. package/core/.formation/tools/log-reader.js +0 -232
  205. package/core/.formation/tools/revert-daemon-state.js +0 -162
  206. package/core/.formation/tools/test-drift.js +0 -148
  207. package/core/.formation/unit/heimdall.yaml +0 -96
  208. package/core/.formation/unit/plan.yaml +0 -67
  209. package/core/.formation/unit/think.yaml +0 -58
  210. package/core/.kenaz/MUNINN_SNAPSHOT9_EPISODE.json +0 -32
  211. package/core/.kenaz/MUNINN_SNAPSHOT9_RUNE.json +0 -23
  212. package/core/.kenaz/MUNINN_SNAPSHOT9_SUMMARY.md +0 -89
  213. package/core/.kenaz/ash_TASK_1428-20260507.json +0 -14
  214. package/core/.kenaz/muninn_episode_write.ps1 +0 -17
  215. package/core/.kenaz/muninn_snapshot11_rune_candidates.md +0 -63
  216. package/core/.kenaz/muninn_snapshot1_rune_candidates.md +0 -49
  217. package/core/.kenaz/runes_TASK_1428.json +0 -57
  218. package/core/.kenaz/tmp_heimdall_proposal_8d3e392.json +0 -13
  219. package/core/.kenaz/tmp_props.json +0 -1
  220. package/core/.kenaz/tmp_sounddrop_t1_prompt.txt +0 -371
  221. package/core/.rule/MECHANIZED.md +0 -61
  222. package/core/.rule/general/cortex-memory-recall.yaml +0 -446
  223. package/core/.rule/general/pipeline.yaml +0 -246
  224. package/core/.rule/general/sunny-access-control.yaml +0 -60
  225. package/core/.rule/general/system-invariants.yaml +0 -231
  226. package/core/.rule/pipeline/PPL-002-completed-task-archival.yaml +0 -528
  227. package/core/.rule/pipeline/auto-update.yaml +0 -282
  228. package/core/.rule/pipeline/task-execution.yaml +0 -365
  229. package/core/.specialist/Ansuz/concepts/phase_protocol.yaml +0 -65
  230. package/core/.specialist/Ansuz/experiments/boot_ablation_replay.js +0 -197
  231. package/core/.specialist/Ansuz/tools/bootstrap-anchors.js +0 -289
  232. package/core/.specialist/Ansuz/workflow.yaml +0 -1225
  233. package/core/.specialist/experiments/rg_benchmark.js +0 -523
  234. package/core/.specialist/experiments/rg_benchmark_results.json +0 -27
  235. package/core/.specialist/tools/jev-optional-context.js +0 -107
  236. package/core/.specialist/tools/jev-optional-context.test.js +0 -152
  237. package/core/.specialist/tools/memory-action-log.js +0 -839
  238. package/core/.specialist/tools/phase-gate.js +0 -3534
  239. package/core/.specialist/tools/phase-gate.test.js +0 -85
  240. package/core/.specialist/tools/precompute-runner.js +0 -444
  241. package/core/.specialist/tools/rule-engine.js +0 -621
  242. package/core/.specialist/tools/task-bridge-jev.test.js +0 -170
  243. package/core/.synapse/memory-shared.json.sync +0 -1
  244. package/core/.system/agent-skills/README.md +0 -724
  245. package/core/.system/cli-tools/README.md +0 -724
  246. package/core/.system/cortex/MODULES.md +0 -1046
  247. package/core/.system/dashboard/FRONTEND.md +0 -812
  248. package/core/.system/dashboard/README.md +0 -737
  249. package/core/.system/failure/README.md +0 -723
  250. package/core/.system/formation/LEGACY_SKILLS.md +0 -974
  251. package/core/.system/formation/POST_COMPLETE.md +0 -602
  252. package/core/.system/formation/README.md +0 -1094
  253. package/core/.system/formation/TOOLS_REFERENCE.md +0 -1145
  254. package/core/.system/kenaz/README.md +0 -787
  255. package/core/.system/memory/README.md +0 -719
  256. package/core/.system/pipeline/README.md +0 -712
  257. package/core/.system/rule/README.md +0 -794
  258. package/core/.system/sunny/README.md +0 -476
  259. package/core/.system/sunny/RULES.json +0 -89
  260. package/core/.system/sunny/knowledge/INDEX.md +0 -37
  261. package/core/.system/sunny/knowledge/agent-teams-api.md +0 -0
  262. package/core/.system/sunny/knowledge/ansuz-specialist.md +0 -500
  263. package/core/.system/sunny/knowledge/claude-cli-spawn.md +0 -177
  264. package/core/.system/sunny/knowledge/collaboration-api.md +0 -925
  265. package/core/.system/sunny/teammates/README.md +0 -107
  266. package/core/.system/sunny/teammates/how_to_use.yaml +0 -101
  267. package/core/.system/sunny/teammates/tools/headless/launcher.js +0 -318
  268. package/core/.system/sunny/teammates/tools/powershell/launcher.js +0 -241
  269. package/core/.system/sunny/teammates/tools/powershell/start.bat +0 -50
  270. package/core/.system/sunny/teammates/tools/utils/env.js +0 -96
  271. package/core/.system/sunny/teammates/tools/utils/format-output.js +0 -329
  272. package/core/.system/sunny/tools.json +0 -101
  273. package/core/dev/scripts/cleanup-queue.js +0 -184
  274. package/core/dev/scripts/cleanup_queue.js +0 -86
  275. package/core/dev/scripts/legacy/README.md +0 -39
  276. package/core/dev/scripts/legacy/dev_agent_scheduler.ps1.bak +0 -536
  277. package/core/dev/scripts/legacy/multi_agent_scheduler.ps1.bak +0 -1978
  278. package/core/dev/scripts/matrix/CLI_README.md +0 -214
  279. package/core/dev/scripts/matrix/README.md +0 -310
  280. package/core/dev/scripts/matrix/package-lock.json +0 -4266
  281. package/core/dev/scripts/matrix/package.json +0 -55
  282. package/core/dev/scripts/matrix/src/abbreviations.ts +0 -295
  283. package/core/dev/scripts/matrix/src/cli/commands/convert.ts +0 -211
  284. package/core/dev/scripts/matrix/src/cli/commands/create.ts +0 -95
  285. package/core/dev/scripts/matrix/src/cli/commands/delete.ts +0 -102
  286. package/core/dev/scripts/matrix/src/cli/commands/list-tags.ts.wip +0 -140
  287. package/core/dev/scripts/matrix/src/cli/commands/manage-tags.ts.wip +0 -173
  288. package/core/dev/scripts/matrix/src/cli/commands/query.ts +0 -261
  289. package/core/dev/scripts/matrix/src/cli/commands/read.ts +0 -77
  290. package/core/dev/scripts/matrix/src/cli/commands/stats.ts.wip +0 -168
  291. package/core/dev/scripts/matrix/src/cli/commands/tokens.ts.wip +0 -126
  292. package/core/dev/scripts/matrix/src/cli/commands/update.ts +0 -147
  293. package/core/dev/scripts/matrix/src/cli/commands/validate.ts +0 -275
  294. package/core/dev/scripts/matrix/src/cli/index.ts +0 -350
  295. package/core/dev/scripts/matrix/src/cli/utils/file-handler.ts +0 -72
  296. package/core/dev/scripts/matrix/src/cli/utils/logger.ts +0 -65
  297. package/core/dev/scripts/matrix/src/index.ts +0 -62
  298. package/core/dev/scripts/matrix/src/indexer/tag-indexer.ts +0 -165
  299. package/core/dev/scripts/matrix/src/parser.ts +0 -281
  300. package/core/dev/scripts/matrix/src/serializer.ts +0 -151
  301. package/core/dev/scripts/matrix/src/validator.ts +0 -301
  302. package/core/dev/scripts/matrix/tests/abbreviations.test.ts +0 -122
  303. package/core/dev/scripts/matrix/tests/cli.test.ts +0 -177
  304. package/core/dev/scripts/matrix/tests/convert.test.ts +0 -143
  305. package/core/dev/scripts/matrix/tests/parser.test.ts +0 -203
  306. package/core/dev/scripts/matrix/tests/query.test.ts +0 -85
  307. package/core/dev/scripts/matrix/tests/serializer.test.ts +0 -197
  308. package/core/dev/scripts/matrix/tests/validate.test.ts +0 -141
  309. package/core/dev/scripts/matrix/tests/validator.test.ts +0 -167
  310. package/core/dev/scripts/matrix/tsconfig.json +0 -20
  311. package/core/dev/scripts/matrix/types/index.d.ts +0 -111
  312. package/core/dev/scripts/matrix/types/index.d.ts.map +0 -1
  313. package/core/dev/scripts/matrix/types/index.js +0 -8
  314. package/core/dev/scripts/matrix/types/index.js.map +0 -1
  315. package/core/dev/scripts/matrix/types/index.ts +0 -124
  316. package/core/dev/scripts/memory-usage-report.js +0 -152
  317. package/core/dev/scripts/probe/ansuz-scaffold-ablation.js +0 -579
  318. package/core/dev/scripts/probe/ansuz-scaffold-ablation.test.js +0 -244
  319. package/core/dev/scripts/probe/hook-latency-probe.js +0 -315
  320. package/core/dev/scripts/probe/hook-latency-probe.test.js +0 -105
  321. package/core/dev/scripts/probe/prediction-signal-auc.js +0 -483
  322. package/core/dev/scripts/probe/prediction-signal-auc.test.js +0 -200
  323. package/core/dev/scripts/test-pty-ws-tunnel.js +0 -229
  324. package/core/dev/scripts/validate_pipeline.js +0 -197
  325. package/core/dev/spikes/task2145-evidence-20261004/backend-log-excerpt.txt +0 -56
  326. package/core/dev/spikes/task2145-evidence-20261004/graph.shadow +0 -0
  327. package/core/dev/spikes/task2145-evidence-20261004/graph.wal +0 -0
  328. package/core/dev/spikes/task2145-evidence-20261004/graph_corrupt_suspect.marker +0 -1
  329. package/core/plugins/kenaz/commands/strategy.md +0 -141
@@ -1,1145 +0,0 @@
1
- # Formation 工具鏈完整參考
2
-
3
- **版本**: v2.0
4
- **最後更新**: 2026-02-20
5
-
6
- 本文檔詳細說明 `.formation/tools/` 下所有模組的函數簽名、參數、呼叫關係與設計意圖。
7
-
8
- ---
9
-
10
- ## 目錄
11
-
12
- 1. [系統架構總覽](#系統架構總覽)
13
- 2. [headless.js — Dispatch 入口](#headlessjs--dispatch-入口)
14
- 3. [prompt.js — Prompt 組裝 + Principles 注入](#promptjs--prompt-組裝--principles-注入)
15
- 4. [runner.js — Subagent 執行](#runnerjs--subagent-執行)
16
- 5. [logger.js — Log 管理](#loggerjs--log-管理)
17
- 6. [utils.js — 工具函數](#utilsjs--工具函數)
18
- 7. [loader.js — 任務載入三層 Fallback](#loaderjs--任務載入三層-fallback)
19
- 8. [呼叫關係圖](#呼叫關係圖)
20
- 9. [關鍵流程範例](#關鍵流程範例)
21
-
22
- ---
23
-
24
- ## 系統架構總覽
25
-
26
- Formation 工具鏈採用**分層架構**,各模組職責清晰:
27
-
28
- ```
29
- ┌──────────────────────────────────────────────────────────┐
30
- │ L5: headless.js — 陣型編排層(5 種陣型的執行邏輯) │
31
- │ launch() → launchUnit/Solo/Squad/Legion/Legacy │
32
- └────────────────────┬─────────────────────────────────────┘
33
- ↓
34
- ┌──────────────────────────────────────────────────────────┐
35
- │ L4: runner.js — 進程啟動層(統一的 claude 進程管理) │
36
- │ runSingle / runHeadless / runLegionLead / runParallel │
37
- └────────────────────┬─────────────────────────────────────┘
38
- ↓
39
- ┌──────────────────────────────────────────────────────────┐
40
- │ L3: prompt.js — Prompt 組裝層(針對不同陣型組裝 prompt) │
41
- │ buildPrompt → Unit/Solo/Squad/Legion/Legacy builders │
42
- └────────────────────┬─────────────────────────────────────┘
43
- ↓
44
- ┌──────────────────────────────────────────────────────────┐
45
- │ L2: loader.js — 資料載入層(skill YAML + 任務三層查詢) │
46
- │ loadSkill / loadTask │
47
- └────────────────────┬─────────────────────────────────────┘
48
- ↓
49
- ┌──────────────────────────────────────────────────────────┐
50
- │ L1: logger.js + utils.js — 基礎設施層 │
51
- │ createLogWriter / formatEntry / generateSessionId │
52
- └──────────────────────────────────────────────────────────┘
53
- ```
54
-
55
- **設計原則**:
56
- - **單一職責**:每個模組只負責一件事(編排 / 進程 / prompt / 載入 / 日誌)
57
- - **依賴單向**:L5 依賴 L4,L4 依賴 L3,依此類推,無循環依賴
58
- - **可測試性**:每層可獨立測試,dry-run 可在 prompt 層停下
59
-
60
- ---
61
-
62
- ## headless.js — Dispatch 入口
63
-
64
- **職責**:根據 `--formation` 參數分發到 5 種陣型的執行邏輯
65
-
66
- ### 主入口
67
-
68
- #### `launch(options)`
69
-
70
- 陣型編排的總調度器。
71
-
72
- **參數**:
73
- ```js
74
- {
75
- formation: 'unit' | 'solo' | 'squad' | 'legion' | 'legacy',
76
- skill: string, // 技能名稱(YAML 檔名,不含 .yaml)
77
- task: string | null, // TASK_ID 或任務描述(null 則自動尋找)
78
- dryRun: boolean, // true=只印 prompt,不啟動進程
79
- mode: string | null // 分析模式(squad 用),如 'optimization', 'innovation'
80
- }
81
- ```
82
-
83
- **回傳**:
84
- - `unit/solo`: `ChildProcess`(單一進程)
85
- - `squad`: `ChildProcess[]`(並行進程陣列)
86
- - `legion`: `ChildProcess`(lead 進程)
87
- - `legacy`: `null`(scheduler loop 在 legacy-scheduler.js)
88
-
89
- **流程**:
90
- 1. 若 `task` 為空且非 legacy → 呼叫 `findNextTask()` 自動選擇任務
91
- 2. 載入 skill YAML (`loadSkill`) 和任務資料 (`loadTask`)
92
- 3. 組裝 prompt (`buildPrompt`)
93
- 4. 若 `dryRun=true` → 印出 prompt,結束
94
- 5. 分發到對應陣型的 launcher 函數
95
-
96
- ---
97
-
98
- ### 陣型 Launchers
99
-
100
- #### `launchUnit(opts)`
101
-
102
- **單一 agent 直接執行**(最簡單的模式)
103
-
104
- **參數**:
105
- ```js
106
- {
107
- rawPrompt: string, // 組裝好的 prompt
108
- skill: string,
109
- sessionId: string
110
- }
111
- ```
112
-
113
- **行為**:
114
- - 呼叫 `runHeadless({ prompt: HEADLESS_PREFIX + rawPrompt, ... })`
115
- - 輸出壓縮、原始 stdout 直通
116
-
117
- ---
118
-
119
- #### `launchSolo(opts)`
120
-
121
- **單一 agent 多視角分析**(agent 自主切換視角)
122
-
123
- **參數** / **行為**:與 `launchUnit` 相同,差異在 prompt 結構(含 perspectives)
124
-
125
- ---
126
-
127
- #### `launchSquad(opts)`
128
-
129
- **多 agent 並行 + 辯論 + 整合**(複雜度最高的陣型)
130
-
131
- **參數**:
132
- ```js
133
- {
134
- rawPrompt: Array<{ memberId, prompt, skill }>, // 成員 prompt 陣列
135
- skill: string,
136
- sessionId: string,
137
- skillDef: object // 完整的 skill YAML(含 debate/merge 設定)
138
- }
139
- ```
140
-
141
- **執行流程**:
142
- 1. **Round 1**:並行啟動所有成員 (`runHeadless` × N),各自獨立分析
143
- 2. 等待所有成員完成 (`waitAll`)
144
- 3. 若啟用 debate → **Round 2**:每個成員讀取其他人的報告,寫反駁
145
- 4. **Synthesis**:整合者讀取所有報告,產出最終報告
146
-
147
- **關鍵函數**:
148
- - `waitAll(children)`: 等待所有進程完成,回傳 `Promise<{ memberId, exitCode, logPath }[]>`
149
- - `printResults(label, results, total)`: 格式化輸出進程執行結果
150
- - `hasSuccess(results)`: 檢查是否有至少一個成功
151
- - `squadSynthesis(opts)`: 啟動整合 agent
152
-
153
- ---
154
-
155
- #### `launchLegion(opts)`
156
-
157
- **Agent Teams 啟動**(使用 Claude Code 官方 teammate 功能)
158
-
159
- **參數**:
160
- ```js
161
- {
162
- rawPrompt: { // buildLegionPrompts 的輸出
163
- teamName: string,
164
- teamDesc: string,
165
- lead: { prompt },
166
- members: [{ name, agentType, prompt }]
167
- },
168
- skill: string,
169
- sessionId: string
170
- }
171
- ```
172
-
173
- **行為**:
174
- - 用 `buildLegionLeadPrompt(legionConfig)` 組裝 lead prompt
175
- - 呼叫 `runLegionLead({ prompt, ... })` 啟動 lead agent
176
- - Lead agent 用 `Task` 工具 spawn teammates(進程內並行)
177
-
178
- ---
179
-
180
- #### `launchLegacy(opts)`
181
-
182
- **連續排程器**(Rust SingleAgentScheduler 對等實作)
183
-
184
- **參數**:
185
- ```js
186
- {
187
- skillDef: object // legacy skill YAML(含 config 設定)
188
- }
189
- ```
190
-
191
- **行為**:
192
- - 從 `skillDef.config` 提取參數(initial_delay_secs, interval_minutes 等)
193
- - 呼叫 `legacy-scheduler.js` 的 `start(overrides)`
194
- - 回傳 `null`(scheduler loop 不是 child process)
195
-
196
- ---
197
-
198
- ### 自動任務選擇
199
-
200
- #### `findNextTask()`
201
-
202
- 從 `.collaboration/tasks/backlog/` 中找出最高優先級的任務。
203
-
204
- **回傳**:
205
- ```js
206
- {
207
- id: 'TASK_XXX',
208
- title: string,
209
- priority: number // 0=P0, 1=P1, 2=P2, 3=P3
210
- } | null
211
- ```
212
-
213
- **排序規則**:
214
- 1. 優先級排序(P0 > P1 > P2 > P3)
215
- 2. 同優先級按 ID 數字排序(TASK_150 > TASK_151)
216
- 3. 跳過有未完成依賴的任務(檢查 dependencies 是否都在 done/)
217
-
218
- ---
219
-
220
- ### Dry Run
221
-
222
- #### `printDryRun(formation, rawPrompt, skillDef, skill)`
223
-
224
- 列印 prompt 但不執行,用於偵錯。
225
-
226
- **行為**:
227
- - `legion`: 印 lead prompt
228
- - `squad`: 印 R1 所有成員 prompt + R2 debate prompts + synthesis prompt
229
- - 其他: 直接印 `HEADLESS_PREFIX + rawPrompt`
230
-
231
- ---
232
-
233
- ## prompt.js — Prompt 組裝 + Principles 注入
234
-
235
- **職責**:根據 skill YAML 和陣型,組裝出符合格式的 prompt
236
-
237
- ### 主入口
238
-
239
- #### `buildPrompt(skillDef, taskInput, taskData, options)`
240
-
241
- 根據陣型分發到對應的 prompt builder。
242
-
243
- **參數**:
244
- ```js
245
- skillDef: object, // loadSkill 回傳的 YAML 解析結果
246
- taskInput: string, // TASK_ID 或任務描述
247
- taskData: string | null, // loadTask 回傳的 YAML 文本(或 null)
248
- options: {
249
- analysisMode?: string // 'optimization' | 'innovation'(squad 用)
250
- }
251
- ```
252
-
253
- **回傳**:
254
- - `unit/solo/legacy`: `string`(單一 prompt)
255
- - `squad`: `Array<{ memberId, prompt, skill }>`
256
- - `legion`: `{ teamName, teamDesc, lead, members }`
257
-
258
- ---
259
-
260
- ### 陣型 Builders
261
-
262
- #### `buildUnitPrompt(skillDef, taskInput, taskData)`
263
-
264
- 組裝單一 agent 的 prompt(最簡單結構)
265
-
266
- **Prompt 結構**:
267
- ```
268
- ## Role
269
- {role.identity}
270
- Priority: {role.priority}
271
-
272
- ## Behavior
273
- - {behavior[0]}
274
- - {behavior[1]}
275
- ...
276
-
277
- ## Task
278
- {taskInput 或 taskData}
279
-
280
- ## Workflow
281
- ### {workflow[0].step}
282
- ...
283
-
284
- ## Expected Output
285
- Primary: {output.primary}
286
- Secondary: {output.secondary}
287
- ```
288
-
289
- ---
290
-
291
- #### `buildSoloPrompt(skillDef, taskInput, taskData)`
292
-
293
- 在 unit 基礎上加入**可用視角 (perspectives)** 和**分析原則 (analysis_principles)**
294
-
295
- **額外區塊**:
296
- ```
297
- ## Analysis Principles
298
- ### {principle.name}
299
- {principle.description}
300
-
301
- ## Available Perspectives
302
- ### {perspective.name}
303
- - 關注:{perspective.lens}
304
- - 何時切換:{perspective.trigger}
305
- ```
306
-
307
- ---
308
-
309
- #### `buildSquadPrompts(skillDef, taskInput, taskData, options)`
310
-
311
- 為每個成員分別組裝 prompt(**最複雜的 builder**)
312
-
313
- **成員 Prompt 結構**:
314
- ```
315
- ## Role
316
- {member.role}
317
-
318
- ## Analysis Mode: {analysisMode}
319
- {modeConfig.description}
320
- **你在此模式下的立場調整**:
321
- {member.mode_behavior[analysisMode]}
322
-
323
- ## Principles (絕對遵守)
324
- {skillDef.principles.focus}
325
- **禁止 (違反即失敗)**:
326
- - ❌ {forbidden[0]}
327
- ...
328
- **必須遵守**:
329
- - ✅ {required[0]}
330
- ...
331
-
332
- ## Identity
333
- 你是 Squad 的成員 **{member.name}** (id: {member.id})。
334
- 你與其他成員並行工作,各自獨立,不能互相通訊。
335
- 完成你負責的部分後回報結果,Lead 會負責整合。
336
-
337
- ## Scope (你只能碰這些檔案)
338
- Include:
339
- - {scope.include[0]}
340
- - ...
341
- Exclude:
342
- - {scope.exclude[0]}
343
- - ...
344
-
345
- ## Shared Context (所有成員共享的約定)
346
- {skillDef.shared_context.description}
347
- ### {key}
348
- {value}
349
-
350
- ## Behavior
351
- - {skillDef.behavior[0]}
352
- - {member.behavior[0]}
353
- ...
354
-
355
- ## Task
356
- {taskInput 或 taskData}
357
-
358
- ## Workflow
359
- {member.workflow 或 skillDef.collaboration.workflow}
360
-
361
- ## Expected Output
362
- {member.output 或 skillDef.output}
363
- ```
364
-
365
- **關鍵函數**:
366
- - `buildSharedContextBlock(skillDef)`: 組裝 shared_context 區塊(成員共用的約定)
367
-
368
- ---
369
-
370
- #### `buildLegionPrompts(skillDef, taskInput, taskData)`
371
-
372
- 組裝 team lead 和每個成員的 prompt。
373
-
374
- **回傳結構**:
375
- ```js
376
- {
377
- teamName: string, // 團隊名稱(自動轉 kebab-case)
378
- teamDesc: string, // 團隊描述
379
- lead: {
380
- prompt: string // Lead agent 的 prompt
381
- },
382
- members: [
383
- {
384
- name: string, // 成員名稱
385
- agentType: string, // 'general-purpose' 等
386
- prompt: string // 成員的 prompt
387
- }
388
- ]
389
- }
390
- ```
391
-
392
- **Lead Prompt 結構**:
393
- ```
394
- ## Role
395
- 你是 {teamName} 的 Team Lead。
396
- {role.identity}
397
-
398
- ## Team Members
399
- - **{member.name}**: {member.role}
400
-
401
- ## Communication Rules
402
- ### Principles
403
- - {comm.principles[0]}
404
- ...
405
- ### Patterns
406
- - **{pattern.name}**: {pattern.who} — {pattern.content}
407
- ...
408
- ### Broadcast Policy
409
- {comm.broadcast_policy}
410
-
411
- ## Task
412
- {taskInput}
413
-
414
- ## Lifecycle
415
- ### {phase}
416
- {description}
417
- Lead actions:
418
- - {lead_actions[0]}
419
- Exit criteria:
420
- - {exit_criteria[0]}
421
-
422
- ## Expected Output
423
- ...
424
- ```
425
-
426
- **Member Prompt**:
427
- - 優先使用 `skillDef.member_prompts[member.id]`(如 forge 的 designer/implementer)
428
- - 否則自動生成(Role + Responsibilities + Skills + Scope + Team Context)
429
-
430
- ---
431
-
432
- #### `buildLegacyPrompt(skillDef)`
433
-
434
- 回傳 scheduler 配置摘要(供 dry-run 顯示)
435
-
436
- ---
437
-
438
- ### Squad 專用:Synthesis 與 Debate
439
-
440
- #### `buildSquadSynthesisPrompt(skillDef, reportDir)`
441
-
442
- 組裝整合 agent 的 prompt,讀取所有成員報告並整合。
443
-
444
- **Prompt 結構**:
445
- ```
446
- ## Role
447
- 你是 Squad Synthesis Agent(整合者)。
448
- 你不偏袒任何一方。
449
-
450
- ## Principles (整合時也必須遵守)
451
- {skillDef.principles.focus}
452
- **禁止**: {forbidden}
453
- **必須遵守**: {required}
454
-
455
- ## Merge Strategy: {merge.strategy}
456
- {merge.description}
457
-
458
- ## Merge Steps (按順序執行)
459
- ### Step: {step.step}
460
- {step.action}
461
- **Partial Failure Handling**: {step.on_partial_failure}
462
-
463
- ## Reports Location
464
- 所有成員報告位於 `.formation/reports/{reportDir}/` 目錄。
465
- **執行步驟**:
466
- 1. 用 Glob 工具掃描 `.formation/reports/{reportDir}/*.md`
467
- 2. 排除 synthesis.md
468
- 3. 用 Read 工具逐一讀取每份報告
469
- 4. 按照上述 Merge Steps 逐步整合
470
-
471
- ## Squad Members(供參考)
472
- - **{member.name}** ({member.id}): {roleFirstLine}
473
-
474
- ## Output
475
- 將整合報告寫入 `.formation/reports/{reportDir}/synthesis.md`
476
- ```
477
-
478
- ---
479
-
480
- #### `buildSquadDebatePrompts(skillDef, reportDir)`
481
-
482
- 組裝 Round 2 交叉辯論的 prompts(每個成員讀其他人的報告)
483
-
484
- **回傳**:`Array<{ memberId, prompt, skill }>`(格式與 buildSquadPrompts 相同)
485
-
486
- **Prompt 結構**:
487
- ```
488
- ## Role
489
- 你是 **{member.name}**,這是你的第二輪分析(辯論回合)。
490
-
491
- ## 你的立場(簡要提醒)
492
- {roleFirstLine}
493
-
494
- ## Debate Instructions
495
- {member.debate_instructions}
496
-
497
- ## Debate Rules
498
- - {debate.rules[0]}
499
- ...
500
-
501
- ## Reports to Read
502
- - **{other.name}**: `.formation/reports/{reportDir}/{other.id}.md`
503
-
504
- 用 Read 工具讀取上述報告,然後寫出你的回應。
505
-
506
- ## Output
507
- 將反駁報告寫入 `.formation/reports/{reportDir}/{member.id}-r2.md`
508
- ```
509
-
510
- ---
511
-
512
- ### Legion 專用
513
-
514
- #### `buildLegionLeadPrompt(config)`
515
-
516
- 組裝 Legion lead 的完整 headless prompt(複製 Sunny teammate 成功模式)
517
-
518
- **結構**:
519
- ```
520
- {LEGION_SYSTEM_PREFIX}
521
- Create an agent team with {members.length} teammates:
522
- 1. "{name}" - {desc}
523
- 2. ...
524
-
525
- Task: {taskMatch}
526
-
527
- {LEGION_AUTO_EXECUTE}
528
- ```
529
-
530
- **常數定義**:
531
- - `LEGION_SYSTEM_PREFIX`: 定義 Team Lead 的角色與責任
532
- - `LEGION_AUTO_EXECUTE`: 強制執行規則(立即建 teammates,進入 polling loop,等所有人完成)
533
-
534
- ---
535
-
536
- ### 共用片段
537
-
538
- #### `appendBehavior(lines, skillDef)`
539
-
540
- 將 `skillDef.behavior` 陣列附加到 lines。
541
-
542
- #### `appendTask(lines, taskInput, taskData)`
543
-
544
- 組裝 Task 區塊:
545
- - 若有 taskData → 用 ` ``` ` 包起來顯示
546
- - 否則直接顯示 taskInput
547
-
548
- #### `appendWorkflow(lines, skillDef)`
549
-
550
- 組裝 Workflow 區塊(從 `skillDef.collaboration.workflow`)
551
-
552
- #### `appendOutput(lines, skillDef)`
553
-
554
- 組裝 Output 區塊(`primary` + `secondary`)
555
-
556
- ---
557
-
558
- ### Headless 常數
559
-
560
- #### `HEADLESS_PREFIX`
561
-
562
- 強制規則:
563
- 1. 直接執行,不要提問
564
- 2. 不要讀取 CLAUDE.md
565
- 3. 完成後輸出結構化結果
566
- 4. 遇到無法執行的問題,輸出錯誤描述後結束
567
- 5. **禁止執行任何 git 操作**(Git 由 Formation Lead 統一管理)
568
-
569
- ---
570
-
571
- ## runner.js — Subagent 執行
572
-
573
- **職責**:統一的 `claude` 進程啟動與輸出收集
574
-
575
- ### 內部:進程管理
576
-
577
- #### `spawnClaude(opts)`
578
-
579
- 所有 `run*` 函數的底層實作。
580
-
581
- **參數**:
582
- ```js
583
- {
584
- prompt: string, // 完整 prompt(已包含 HEADLESS_PREFIX)
585
- formation: string, // 陣型名稱(用於 log 目錄)
586
- skill: string, // 技能名稱
587
- sessionId: string, // session ID
588
- memberId?: string, // 成員 ID(squad/legion 用)
589
- silent?: boolean, // 不輸出到 console
590
- outputPath?: string, // 自訂 log 路徑
591
- cleanPrompt?: boolean, // true=壓縮 prompt(移除換行、多餘空格)
592
- allowedTools?: string, // 允許的工具清單(逗號分隔)
593
- extraArgs?: string[], // 額外的 claude CLI 參數
594
- pipeRaw?: boolean, // true=原始 stdout 直通,false=格式化輸出
595
- onLog?: (formatted: string) => void // 自訂 log handler
596
- }
597
- ```
598
-
599
- **回傳**:`ChildProcess`(附加 `_formation` 屬性)
600
-
601
- **流程**:
602
- 1. 建立 log writer (`createLogWriter`)
603
- 2. 啟動 `claude.cmd -p - --dangerously-skip-permissions --output-format stream-json ...`
604
- 3. 將 prompt 透過 stdin 傳入
605
- 4. 呼叫 `collectOutput(child, log, opts)` 收集輸出
606
- 5. 附加 `_formation` 屬性到 child process
607
-
608
- **`_formation` 屬性**:
609
- ```js
610
- {
611
- logPath: string, // log 檔案路徑
612
- memberId: string, // 成員 ID
613
- log: object // log writer 實例
614
- }
615
- ```
616
-
617
- ---
618
-
619
- #### `collectOutput(child, log, opts)`
620
-
621
- 收集 `claude` 進程的 stdout/stderr,寫入 log。
622
-
623
- **參數**:
624
- ```js
625
- child: ChildProcess,
626
- log: LogWriter,
627
- opts: {
628
- silent?: boolean, // 不輸出到 console
629
- memberId?: string, // 成員 ID(顯示用)
630
- pipeRaw?: boolean, // true=直通,false=格式化
631
- onLog?: (line) => void // 自訂 handler
632
- }
633
- ```
634
-
635
- **行為**:
636
- 1. 監聽 `stdout.data` 事件,解析 stream-json 格式
637
- 2. 用 `formatEntry(entry)` 格式化每條 entry
638
- 3. 寫入 log 檔案
639
- 4. 若 `!silent && !pipeRaw` → 輸出到 console
640
- 5. 偵測到 `type: 'result'` → emit `formation:done` 並延遲 kill(Windows fix)
641
- 6. 監聽 `close/exit/formation:done` → 呼叫 `log.writeFooter(code)`
642
-
643
- **Windows 特殊處理**:
644
- - `claude.cmd` 有時進程不 exit,偵測到 `result` 就 emit 完成信號並延遲 kill
645
-
646
- ---
647
-
648
- ### 公開 API
649
-
650
- #### `runSingle(opts)`
651
-
652
- 啟動單一 claude subagent(**格式化輸出**)
653
-
654
- **用途**:dispatch.js 用(一般模式)
655
-
656
- ---
657
-
658
- #### `runHeadless(opts)`
659
-
660
- 無頭模式:**壓縮 prompt + 原始 stdout 直通**
661
-
662
- **用途**:Unit / Solo / Squad 成員
663
-
664
- ---
665
-
666
- #### `runLegionLead(opts)`
667
-
668
- Agent Teams 模式:啟用 `--teammate-mode in-process` + `Task` 工具
669
-
670
- **預設參數覆蓋**:
671
- ```js
672
- {
673
- cleanPrompt: true,
674
- pipeRaw: true,
675
- allowedTools: 'Bash,Read,Edit,Write,Glob,Grep,Task',
676
- extraArgs: ['--teammate-mode', 'in-process']
677
- }
678
- ```
679
-
680
- ---
681
-
682
- #### `runParallel(opts)`
683
-
684
- 並行啟動多個 claude subagent(**dispatch 用**)
685
-
686
- **參數**:
687
- ```js
688
- {
689
- members: Array<{ memberId, prompt, skill }>,
690
- formation: string,
691
- sessionId: string
692
- }
693
- ```
694
-
695
- **回傳**:`Promise<Array<{ memberId, exitCode, logPath }>>`
696
-
697
- **行為**:
698
- 1. 用 `runSingle` 並行啟動所有成員
699
- 2. 用 `Promise.all` 等待所有進程完成
700
- 3. 輸出執行結果摘要
701
-
702
- ---
703
-
704
- ## logger.js — Log 管理
705
-
706
- **職責**:Claude subagent 的 stream-json 格式化與 log 寫入
707
-
708
- ### Log Writer
709
-
710
- #### `createLogWriter(opts)`
711
-
712
- 建立 log writer 實例。
713
-
714
- **參數**:
715
- ```js
716
- {
717
- formation: string, // 陣型(決定 log 目錄)
718
- skill: string, // 技能名稱
719
- sessionId: string, // session ID
720
- outputPath?: string, // 自訂輸出路徑
721
- memberId?: string // Squad 成員 ID
722
- }
723
- ```
724
-
725
- **回傳**:
726
- ```js
727
- {
728
- stream: WriteStream, // fs.createWriteStream 實例
729
- path: string, // log 檔案絕對路徑
730
- writeHeader: () => void, // 寫入 header(formation, skill, session, 時間)
731
- writeFooter: (code) => void // 寫入 footer(finished, exit code)
732
- }
733
- ```
734
-
735
- **Log 目錄結構**:
736
- ```
737
- .formation/logs/{formation}/{skill}_{memberId?}_{sessionId}.log
738
- ```
739
-
740
- ---
741
-
742
- ### Entry 格式化
743
-
744
- #### `formatEntry(entry)`
745
-
746
- 格式化 stream-json 的一條 entry。
747
-
748
- **參數**:
749
- ```js
750
- entry: {
751
- type: 'system' | 'assistant' | 'user' | 'result',
752
- subtype?: string,
753
- message?: { content: [...] },
754
- ...
755
- }
756
- ```
757
-
758
- **回傳**:`string | null`(格式化後的文本,或 null 表示跳過)
759
-
760
- **支援的 entry types**:
761
-
762
- 1. **system**:
763
- - `init`: `[SYSTEM][INIT] model=... cwd=...`
764
- - `hook_started`: `[SYSTEM][HOOK] {hook_name} started`
765
- - `hook_response`: `[SYSTEM][HOOK] {hook_name} OK/FAILED`
766
-
767
- 2. **assistant**(agent 輸出 + 工具呼叫):
768
- - `text` block → 移除 markdown 格式,分行輸出 `[Agent] ...`
769
- - `tool_use` block → `[Agent][{tool}] {detail}`
770
-
771
- 3. **user**(tool results、teammate 訊息):
772
- - `tool_use_result.status === 'teammate_spawned'` → `[SYSTEM][Spawned] ...`
773
- - `message.content` 包含 "Message from" → `[Teammate:{name}] | ...`
774
-
775
- 4. **result**(session 結束摘要):
776
- - `[RESULT] {subtype}`
777
- - `Duration: {duration_ms/1000}s`
778
- - `Cost: ${total_cost_usd}`
779
- - `Turns: {num_turns}`
780
- - 摘要前 10 行
781
-
782
- ---
783
-
784
- #### `formatToolUse(ts, block)`
785
-
786
- 格式化 tool_use block。
787
-
788
- **工具清單**:
789
- - `Bash`: 顯示 `description` 或 `command` 前 60 字元
790
- - `Read/Write/Edit`: 顯示 `file_path`
791
- - `Glob/Grep`: 顯示 `pattern`
792
- - `TeamCreate`: 顯示 `team_name`
793
- - `Task`: 顯示 `name` 和 `subagent_type`
794
- - `SendMessage`: 顯示 `recipient` 和 `type`,並附加完整訊息內容
795
-
796
- **格式**:
797
- ```
798
- [HH:MM:SS][Agent][{tool}] {detail}
799
- | {message line 1}
800
- | {message line 2}
801
- | ...
802
- ```
803
-
804
- ---
805
-
806
- #### `formatUser(ts, entry)`
807
-
808
- 格式化 user events(tool results、teammate 訊息)
809
-
810
- **格式**:
811
- ```
812
- [HH:MM:SS][SYSTEM][Spawned] Teammate "{name}" model=...
813
- [HH:MM:SS][Teammate:{name}]
814
- | {message line 1}
815
- | {message line 2}
816
- | ...
817
- ```
818
-
819
- ---
820
-
821
- #### `formatResult(ts, entry)`
822
-
823
- 格式化 session 結束摘要。
824
-
825
- **格式**:
826
- ```
827
- [HH:MM:SS][RESULT] {subtype}
828
- Duration: {seconds}s
829
- Cost: ${usd}
830
- Turns: {num_turns}
831
- {result line 1}
832
- {result line 2}
833
- ...
834
- ```
835
-
836
- ---
837
-
838
- ## utils.js — 工具函數
839
-
840
- **職責**:路徑常數、Session ID 生成、Git Bash 偵測、環境變數設定
841
-
842
- ### 路徑常數
843
-
844
- ```js
845
- ROOT // D:\repo\side\ava\KenazAI
846
- FORMATION_DIR // {ROOT}/.formation
847
- COLLABORATION_API // {ROOT}/.collaboration/core/task-api.js
848
- LOG_DIR // {ROOT}/.formation/logs
849
- ```
850
-
851
- ---
852
-
853
- ### Session ID
854
-
855
- #### `generateSessionId()`
856
-
857
- 生成唯一的 session ID。
858
-
859
- **格式**:`YYYYMMDD-HHMMSS-{4 位隨機 hex}`
860
-
861
- **範例**:`20260220-123045-a3f9`
862
-
863
- ---
864
-
865
- ### Git Bash 偵測
866
-
867
- #### `detectGitBash()`
868
-
869
- Windows 專用:自動偵測 Git Bash 路徑。
870
-
871
- **回傳**:`string | null`(bash.exe 的絕對路徑)
872
-
873
- **偵測順序**:
874
- 1. 從 `where git` 找到 git.exe 路徑
875
- 2. 往上找包含 `bin/bash.exe` 的 Git 根目錄
876
- 3. Fallback 到固定路徑清單:
877
- - `C:\Program Files\Git\bin\bash.exe`
878
- - `C:\Program Files (x86)\Git\bin\bash.exe`
879
- - `D:\Program Files\Git\bin\bash.exe`
880
-
881
- ---
882
-
883
- ### 環境變數
884
-
885
- #### `getClaudeEnv()`
886
-
887
- 建立 claude 進程的環境變數。
888
-
889
- **回傳**:`object`(繼承 `process.env` 並修改)
890
-
891
- **變更**:
892
- 1. 設定 `CLAUDE_CODE_EXPERIMENTAL_AGENT_TEAMS=1`(啟用 agent teams)
893
- 2. 刪除 `CLAUDECODE`(避免 nested session 錯誤)
894
- 3. Windows: 設定 `CLAUDE_CODE_GIT_BASH_PATH`(若未設定)
895
-
896
- ---
897
-
898
- ## loader.js — 任務載入三層 Fallback
899
-
900
- **職責**:載入 skill YAML + 任務資料(支援新舊兩套任務系統)
901
-
902
- ### Skill 載入
903
-
904
- #### `loadSkill(formation, skill)`
905
-
906
- 載入 skill YAML 定義。
907
-
908
- **參數**:
909
- ```js
910
- formation: string, // 陣型名稱(決定子目錄)
911
- skill: string // 技能名稱(YAML 檔名,不含 .yaml)
912
- ```
913
-
914
- **回傳**:`object`(YAML 解析結果)
915
-
916
- **路徑**:`.formation/{formation}/{skill}.yaml`
917
-
918
- **錯誤處理**:檔案不存在 → `console.error` + `process.exit(1)`
919
-
920
- ---
921
-
922
- #### `listSkills(formation)`
923
-
924
- 列出某個陣型下所有可用的 skill。
925
-
926
- **回傳**:`string[]`(skill 名稱列表,不含 .yaml)
927
-
928
- ---
929
-
930
- ### 任務載入(三層 Fallback)
931
-
932
- #### `loadTask(taskId)`
933
-
934
- 載入任務資料,支援新舊兩套任務系統。
935
-
936
- **參數**:
937
- ```js
938
- taskId: string // TASK_XXX 格式(若不符合或為 null 則回傳 null)
939
- ```
940
-
941
- **回傳**:`string | null`(YAML 或 JSON 文本)
942
-
943
- **查詢順序**:
944
-
945
- 1. **新系統** (`.collaboration/tasks/`)
946
- - 呼叫 `node .collaboration/core/task-api.js get {taskId}`
947
- - 目錄結構:`{status}/{taskId}_{git_user}.yaml`(status = backlog/active/done/blocked)
948
-
949
- 2. **舊系統 YAML** (`dev/pipeline/completed/` + `tasks/`)
950
- - 掃描兩個目錄,找到以 `{taskId}` 開頭且 `.yaml` 結尾的檔案
951
- - 讀取並回傳檔案內容
952
-
953
- 3. **舊系統 JSON** (`dev/pipeline/TASK_QUEUE.json`)
954
- - 解析 JSON 檔案
955
- - 從 `tasks` 陣列找到 `id === taskId` 的任務
956
- - 用 `yaml.dump` 轉為 YAML 格式回傳
957
-
958
- **錯誤處理**:
959
- - 所有層都失敗 → `console.warn` + 回傳 `null`(不中斷執行)
960
-
961
- ---
962
-
963
- ### 實作細節
964
-
965
- #### `loadTaskFromCollaboration(taskId)`
966
-
967
- 新系統載入邏輯。
968
-
969
- **實作**:
970
- ```js
971
- const result = execSync(
972
- `node "${COLLABORATION_API}" get ${taskId}`,
973
- { encoding: 'utf8', cwd: ROOT, timeout: 10000 }
974
- );
975
- ```
976
-
977
- **錯誤處理**:捕捉 exception 並回傳 `null`
978
-
979
- ---
980
-
981
- #### `loadTaskFromLegacyYaml(taskId)`
982
-
983
- 舊系統 YAML 檔載入。
984
-
985
- **實作**:
986
- ```js
987
- const dirs = ['completed', 'tasks'];
988
- for (const dir of dirs) {
989
- const files = fs.readdirSync(dirPath);
990
- const match = files.find(f => f.startsWith(taskId) && f.endsWith('.yaml'));
991
- if (match) return fs.readFileSync(...);
992
- }
993
- ```
994
-
995
- ---
996
-
997
- #### `loadTaskFromLegacyQueue(taskId)`
998
-
999
- 舊系統 JSON 索引載入。
1000
-
1001
- **實作**:
1002
- ```js
1003
- const queue = JSON.parse(fs.readFileSync(LEGACY_TASK_QUEUE, 'utf8'));
1004
- const task = queue.tasks.find(t => t.id === taskId);
1005
- if (task) return yaml.dump(task, { lineWidth: -1 });
1006
- ```
1007
-
1008
- ---
1009
-
1010
- ## 呼叫關係圖
1011
-
1012
- ```
1013
- CLI (node .formation/tools/headless.js --formation=squad --skill=blitz)
1014
- ↓
1015
- headless.js:launch()
1016
- ↓
1017
- ├─→ loader.js:loadSkill(formation, skill) → 載入 YAML
1018
- ├─→ loader.js:loadTask(taskId) → 三層 fallback 載入任務
1019
- ├─→ prompt.js:buildPrompt(skillDef, taskInput) → 組裝 prompt
1020
- ↓
1021
- ├── formation='squad' → headless.js:launchSquad()
1022
- │ ↓
1023
- │ ├─→ runner.js:runHeadless() × N (Round 1)
1024
- │ │ ↓
1025
- │ │ ├─→ runner.js:spawnClaude()
1026
- │ │ │ ↓
1027
- │ │ │ ├─→ logger.js:createLogWriter()
1028
- │ │ │ ├─→ utils.js:getClaudeEnv()
1029
- │ │ │ └─→ runner.js:collectOutput()
1030
- │ │ │ ↓
1031
- │ │ │ └─→ logger.js:formatEntry() → log 寫入
1032
- │ │ └─→ waitAll() → 等待所有進程完成
1033
- │ ↓
1034
- │ ├─→ prompt.js:buildSquadDebatePrompts() (Round 2)
1035
- │ ├─→ runner.js:runHeadless() × N (Round 2)
1036
- │ └─→ headless.js:squadSynthesis()
1037
- │ ↓
1038
- │ └─→ prompt.js:buildSquadSynthesisPrompt()
1039
- │ ↓
1040
- │ └─→ runner.js:runHeadless()
1041
- │
1042
- ├── formation='legion' → headless.js:launchLegion()
1043
- │ ↓
1044
- │ ├─→ prompt.js:buildLegionLeadPrompt()
1045
- │ └─→ runner.js:runLegionLead()
1046
- │ ↓
1047
- │ └─→ runner.js:spawnClaude(extraArgs: ['--teammate-mode', ...])
1048
- │
1049
- ├── formation='unit' → headless.js:launchUnit()
1050
- │ ↓
1051
- │ └─→ runner.js:runHeadless()
1052
- │
1053
- ├── formation='solo' → headless.js:launchSolo()
1054
- │ ↓
1055
- │ └─→ runner.js:runHeadless()
1056
- │
1057
- └── formation='legacy' → headless.js:launchLegacy()
1058
- ↓
1059
- └─→ legacy-scheduler.js:start()
1060
- ```
1061
-
1062
- ---
1063
-
1064
- ## 關鍵流程範例
1065
-
1066
- ### 範例 1:Unit 執行流程
1067
-
1068
- **命令**:
1069
- ```bash
1070
- node .formation/tools/headless.js --skill=do --task="修正按鈕顏色"
1071
- ```
1072
-
1073
- **流程**:
1074
- 1. `headless.launch()` 解析參數:`formation='unit', skill='do', task='修正按鈕顏色'`
1075
- 2. `loader.loadSkill('unit', 'do')` → 讀取 `.formation/unit/do.yaml`
1076
- 3. `prompt.buildPrompt()` → 呼叫 `buildUnitPrompt()` 組裝 prompt
1077
- 4. `headless.launchUnit()` → 呼叫 `runner.runHeadless()`
1078
- 5. `runner.spawnClaude()` 啟動 `claude.cmd -p - ...`
1079
- 6. `collectOutput()` 收集輸出,`formatEntry()` 格式化每條 entry
1080
- 7. 寫入 `.formation/logs/unit/do_{sessionId}.log`
1081
-
1082
- ---
1083
-
1084
- ### 範例 2:Squad 執行流程(含 Debate)
1085
-
1086
- **命令**:
1087
- ```bash
1088
- node .formation/tools/headless.js --formation=squad --skill=blitz --task=TASK_201
1089
- ```
1090
-
1091
- **流程**:
1092
- 1. `headless.launch()` 解析參數:`formation='squad', skill='blitz', task='TASK_201'`
1093
- 2. `loader.loadTask('TASK_201')` → 三層 fallback 載入任務 YAML
1094
- 3. `prompt.buildSquadPrompts()` → 回傳 `[{ memberId, prompt, skill }, ...]`
1095
- 4. `headless.launchSquad()`:
1096
- - **Round 1**:`runHeadless()` × N,並行啟動所有成員
1097
- - `waitAll()` 等待所有進程完成
1098
- - 若 `skillDef.debate.enabled=true`:
1099
- - **Round 2**:`buildSquadDebatePrompts()` 組裝辯論 prompts
1100
- - `runHeadless()` × N,成員互相讀取報告
1101
- - **Synthesis**:`buildSquadSynthesisPrompt()` + `runHeadless()`
1102
- 5. 每個成員的輸出分別寫入:
1103
- - R1: `.formation/logs/squad/{member.id}_{sessionId}.log`
1104
- - R2: `.formation/logs/squad/{member.id}-r2_{sessionId}.log`
1105
- - Synthesis: `.formation/logs/squad/{skill}-synthesis_{sessionId}.log`
1106
-
1107
- ---
1108
-
1109
- ### 範例 3:Legion 執行流程
1110
-
1111
- **命令**:
1112
- ```bash
1113
- node .formation/tools/headless.js --formation=legion --skill=forge --task=TASK_202
1114
- ```
1115
-
1116
- **流程**:
1117
- 1. `prompt.buildLegionPrompts()` → 回傳 `{ teamName, lead, members }`
1118
- 2. `prompt.buildLegionLeadPrompt()` → 組裝 lead prompt(含 `LEGION_AUTO_EXECUTE`)
1119
- 3. `runner.runLegionLead()` → 啟動 lead agent(`--teammate-mode in-process`)
1120
- 4. Lead agent 用 `Task` 工具 spawn teammates(進程內並行)
1121
- 5. Lead agent 進入 polling loop(`sleep 5` + check messages)
1122
- 6. 等待所有 teammates 回報 → 整合結果 → 結束
1123
-
1124
- ---
1125
-
1126
- ## 總結
1127
-
1128
- Formation 工具鏈設計遵循以下核心原則:
1129
-
1130
- 1. **分層架構**:L1 基礎設施 → L2 載入 → L3 prompt → L4 進程 → L5 編排
1131
- 2. **單一職責**:每個模組只做一件事,介面清晰
1132
- 3. **可測試性**:dry-run 可在 prompt 層停下,不啟動進程
1133
- 4. **統一進程管理**:所有陣型的 subagent 啟動都經過 `runner.js`
1134
- 5. **統一日誌格式**:所有 log 都經過 `logger.js` 格式化
1135
- 6. **雙系統相容**:任務載入支援新舊兩套系統(三層 fallback)
1136
-
1137
- **擴展建議**:
1138
- - 新增陣型:在 `.formation/{formation}/` 建立 YAML,在 `headless.js` 新增 launcher
1139
- - 新增工具支援:在 `logger.js:formatToolUse()` 新增格式化規則
1140
- - 調整 prompt 結構:修改 `prompt.js` 對應的 builder 函數
1141
-
1142
- **維護要點**:
1143
- - 修改 prompt 結構時,同步更新 `.formation/{formation}/` 下的 YAML 範例
1144
- - 新增環境變數時,在 `utils.js:getClaudeEnv()` 統一設定
1145
- - 修改 log 格式時,確保與 Sunny 的 `format-output.js` 保持一致