@goondocks/myco 0.10.0 → 0.12.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 (197) hide show
  1. package/CONTRIBUTING.md +3 -20
  2. package/README.md +21 -10
  3. package/dist/{agent-run-CGXF5PPC.js → agent-run-5KYQJQTY.js} +6 -6
  4. package/dist/{agent-tasks-T7NVI3R7.js → agent-tasks-N7BDYKGB.js} +6 -6
  5. package/dist/{chunk-XLY3REL3.js → chunk-4VSNNMEU.js} +2 -2
  6. package/dist/{chunk-5LPERML5.js → chunk-7NBDELZB.js} +9 -9
  7. package/dist/{chunk-ZMW6KQX2.js → chunk-D4ESHOOJ.js} +6 -6
  8. package/dist/{chunk-W6HI4CCS.js → chunk-D4M2AV65.js} +5 -4
  9. package/dist/chunk-D4M2AV65.js.map +1 -0
  10. package/dist/{chunk-YZMNEIFI.js → chunk-DPJVKNNP.js} +3 -3
  11. package/dist/{chunk-FMIWFRAM.js → chunk-HAG2YDH6.js} +9 -8
  12. package/dist/chunk-HAG2YDH6.js.map +1 -0
  13. package/dist/{chunk-AEJS57ZK.js → chunk-J3L2RTYK.js} +2 -2
  14. package/dist/{chunk-MKKXCCQ5.js → chunk-JHLALJPB.js} +5 -5
  15. package/dist/{chunk-CUDM5YJY.js → chunk-JROOQQH6.js} +3 -3
  16. package/dist/{chunk-D6DXYAFK.js → chunk-LGPBVBFY.js} +3 -3
  17. package/dist/{chunk-5SDH75YC.js → chunk-LUQBT2Y4.js} +2 -2
  18. package/dist/{chunk-76ZO5RGT.js → chunk-PIRWYDOH.js} +30 -2
  19. package/dist/chunk-PIRWYDOH.js.map +1 -0
  20. package/dist/{chunk-WZZH3YXJ.js → chunk-PW5QVY44.js} +2 -2
  21. package/dist/{chunk-U7UUJ4FD.js → chunk-Q2AYS2QE.js} +3 -3
  22. package/dist/{chunk-5PEUFJ6U.js → chunk-QFMBZ72S.js} +24 -8
  23. package/dist/chunk-QFMBZ72S.js.map +1 -0
  24. package/dist/{chunk-FPMEIN2W.js → chunk-QL2RBFIC.js} +2 -2
  25. package/dist/{chunk-MSXYUXZR.js → chunk-RGRPAKEY.js} +3 -3
  26. package/dist/chunk-RR75ZKEV.js +83 -0
  27. package/dist/chunk-RR75ZKEV.js.map +1 -0
  28. package/dist/{chunk-5QERXFH7.js → chunk-SW62AX75.js} +2 -2
  29. package/dist/{chunk-FFQES5MC.js → chunk-TCGOSLW6.js} +3 -3
  30. package/dist/{chunk-G2LQBFE3.js → chunk-TY7A5OZ5.js} +2 -2
  31. package/dist/chunk-YRHSTVCZ.js +792 -0
  32. package/dist/chunk-YRHSTVCZ.js.map +1 -0
  33. package/dist/{chunk-C3AEZ3BZ.js → chunk-YRUJ5KGV.js} +3 -3
  34. package/dist/{cli-6CPFJGRZ.js → cli-Y5QZJAHX.js} +39 -37
  35. package/dist/cli-Y5QZJAHX.js.map +1 -0
  36. package/dist/{client-B27SN5QG.js → client-UGM6MG55.js} +4 -4
  37. package/dist/{detect-H5OPI7GD.js → detect-27DN6UTL.js} +3 -3
  38. package/dist/{detect-providers-AZ6DEQU7.js → detect-providers-JFE3QLJI.js} +4 -4
  39. package/dist/{doctor-RHHWJTMB.js → doctor-NFWPX75B.js} +22 -28
  40. package/dist/doctor-NFWPX75B.js.map +1 -0
  41. package/dist/{executor-A5C5KDLP.js → executor-ESRLUCGU.js} +19 -19
  42. package/dist/executor-ESRLUCGU.js.map +1 -0
  43. package/dist/{init-ARJROOWV.js → init-NMSG24BY.js} +42 -61
  44. package/dist/init-NMSG24BY.js.map +1 -0
  45. package/dist/{init-wizard-XNFOZCEB.js → init-wizard-WIUCR4JE.js} +7 -7
  46. package/dist/{llm-XJFHRFHB.js → llm-O46QYWEM.js} +7 -7
  47. package/dist/{loader-GKXR5ONU.js → loader-BQ4X4K3F.js} +5 -5
  48. package/dist/{main-PVX6R3I6.js → main-3NTAT7ZD.js} +996 -104
  49. package/dist/main-3NTAT7ZD.js.map +1 -0
  50. package/dist/{openai-embeddings-ST3B6GW7.js → openai-embeddings-HWAKOGUM.js} +4 -4
  51. package/dist/{openrouter-HJHOO3EO.js → openrouter-GXZK7JXR.js} +4 -4
  52. package/dist/{post-compact-LR3DSGT3.js → post-compact-3DDK3OVZ.js} +12 -8
  53. package/dist/post-compact-3DDK3OVZ.js.map +1 -0
  54. package/dist/{post-tool-use-SOFVNFU3.js → post-tool-use-LSG6N3W5.js} +21 -14
  55. package/dist/post-tool-use-LSG6N3W5.js.map +1 -0
  56. package/dist/post-tool-use-failure-5V3OCLI6.js +32 -0
  57. package/dist/post-tool-use-failure-5V3OCLI6.js.map +1 -0
  58. package/dist/{pre-compact-3E3D6565.js → pre-compact-F7Y7SDSZ.js} +11 -7
  59. package/dist/pre-compact-F7Y7SDSZ.js.map +1 -0
  60. package/dist/{provider-check-SOTDYLJE.js → provider-check-CKZW3GQX.js} +4 -4
  61. package/dist/{registry-WVZG6R2R.js → registry-ZHUVXGPO.js} +6 -6
  62. package/dist/remove-VCWRNG54.js +92 -0
  63. package/dist/remove-VCWRNG54.js.map +1 -0
  64. package/dist/{resolution-events-UPHJJLDQ.js → resolution-events-WZHPQQMN.js} +4 -4
  65. package/dist/{restart-XIUFVS33.js → restart-YYJ7SH4K.js} +7 -7
  66. package/dist/{search-VB6Z2ZXV.js → search-L7KTBURJ.js} +7 -7
  67. package/dist/{server-AKPBRP6Z.js → server-GMRVF2PB.js} +14 -14
  68. package/dist/{session-UVZS6CY5.js → session-V3SNFG7J.js} +8 -8
  69. package/dist/{session-end-YMQ44U6Z.js → session-end-V3V3GMP2.js} +12 -7
  70. package/dist/session-end-V3V3GMP2.js.map +1 -0
  71. package/dist/{session-start-3754HF3N.js → session-start-OH7SBUIA.js} +17 -14
  72. package/dist/{session-start-3754HF3N.js.map → session-start-OH7SBUIA.js.map} +1 -1
  73. package/dist/{setup-llm-NWHOPJUV.js → setup-llm-5AMWEAJ5.js} +9 -9
  74. package/dist/src/agent/definitions/tasks/full-intelligence.yaml +0 -1
  75. package/dist/src/agent/prompts/agent.md +1 -1
  76. package/dist/src/cli.js +1 -1
  77. package/dist/src/daemon/main.js +1 -1
  78. package/dist/src/hooks/post-tool-use.js +1 -1
  79. package/dist/src/hooks/session-end.js +1 -1
  80. package/dist/src/hooks/session-start.js +1 -1
  81. package/dist/src/hooks/stop.js +1 -1
  82. package/dist/src/hooks/user-prompt-submit.js +1 -1
  83. package/dist/src/mcp/server.js +1 -1
  84. package/dist/src/symbionts/manifests/claude-code.yaml +8 -4
  85. package/dist/src/symbionts/manifests/codex.yaml +19 -0
  86. package/dist/src/symbionts/manifests/cursor.yaml +6 -3
  87. package/dist/src/symbionts/manifests/gemini.yaml +20 -0
  88. package/dist/src/symbionts/manifests/vscode-copilot.yaml +17 -0
  89. package/dist/src/symbionts/manifests/windsurf.yaml +16 -0
  90. package/dist/src/symbionts/templates/claude-code/hooks.json +134 -0
  91. package/dist/src/symbionts/templates/claude-code/mcp.json +7 -0
  92. package/dist/src/symbionts/templates/claude-code/settings.json +10 -0
  93. package/dist/src/symbionts/templates/codex/hooks.json +46 -0
  94. package/dist/src/symbionts/templates/codex/mcp.json +6 -0
  95. package/dist/src/symbionts/templates/cursor/mcp.json +7 -0
  96. package/dist/src/symbionts/templates/cursor/settings.json +6 -0
  97. package/dist/src/symbionts/templates/gemini/hooks.json +74 -0
  98. package/dist/src/symbionts/templates/gemini/mcp.json +6 -0
  99. package/dist/src/symbionts/templates/gemini/settings.json +6 -0
  100. package/dist/src/symbionts/templates/instructions-stub.md +9 -0
  101. package/dist/src/symbionts/templates/vscode-copilot/hooks.json +79 -0
  102. package/dist/src/symbionts/templates/vscode-copilot/mcp.json +7 -0
  103. package/dist/src/symbionts/templates/vscode-copilot/settings.json +6 -0
  104. package/dist/src/symbionts/templates/windsurf/hooks.json +22 -0
  105. package/dist/src/symbionts/templates/windsurf/settings.json +6 -0
  106. package/dist/{stats-CDQXOTEC.js → stats-B2V7P45Y.js} +10 -10
  107. package/dist/{stop-WSFGRPXZ.js → stop-D6L2KRHZ.js} +17 -11
  108. package/dist/stop-D6L2KRHZ.js.map +1 -0
  109. package/dist/{stop-failure-4FR7574F.js → stop-failure-7OM2AYRX.js} +12 -8
  110. package/dist/stop-failure-7OM2AYRX.js.map +1 -0
  111. package/dist/{subagent-start-7SGBXJYP.js → subagent-start-MKL5I54S.js} +12 -8
  112. package/dist/{subagent-start-7SGBXJYP.js.map → subagent-start-MKL5I54S.js.map} +1 -1
  113. package/dist/subagent-stop-2E7VKZW2.js +32 -0
  114. package/dist/subagent-stop-2E7VKZW2.js.map +1 -0
  115. package/dist/task-completed-5QHIT773.js +31 -0
  116. package/dist/task-completed-5QHIT773.js.map +1 -0
  117. package/dist/{team-XMHYCKFF.js → team-TBS5OILG.js} +5 -5
  118. package/dist/ui/assets/index-aMc07Ym5.js +804 -0
  119. package/dist/ui/index.html +1 -1
  120. package/dist/{update-W3UFZU4G.js → update-4NVFET56.js} +30 -34
  121. package/dist/update-4NVFET56.js.map +1 -0
  122. package/dist/{user-prompt-submit-LSWCYUW3.js → user-prompt-submit-X4BCPMZ4.js} +15 -8
  123. package/dist/user-prompt-submit-X4BCPMZ4.js.map +1 -0
  124. package/dist/{verify-O7TQ5DDY.js → verify-D7EDVXO5.js} +8 -8
  125. package/dist/{version-VWWY7SPQ.js → version-GTFCEIJ2.js} +2 -2
  126. package/package.json +5 -4
  127. package/skills/rules/SKILL.md +32 -9
  128. package/.claude-plugin/marketplace.json +0 -26
  129. package/.claude-plugin/plugin.json +0 -27
  130. package/dist/chunk-5PEUFJ6U.js.map +0 -1
  131. package/dist/chunk-76ZO5RGT.js.map +0 -1
  132. package/dist/chunk-FMIWFRAM.js.map +0 -1
  133. package/dist/chunk-J4RVYUH4.js +0 -21
  134. package/dist/chunk-J4RVYUH4.js.map +0 -1
  135. package/dist/chunk-W6HI4CCS.js.map +0 -1
  136. package/dist/chunk-WXSJKESH.js +0 -441
  137. package/dist/chunk-WXSJKESH.js.map +0 -1
  138. package/dist/cli-6CPFJGRZ.js.map +0 -1
  139. package/dist/doctor-RHHWJTMB.js.map +0 -1
  140. package/dist/executor-A5C5KDLP.js.map +0 -1
  141. package/dist/init-ARJROOWV.js.map +0 -1
  142. package/dist/main-PVX6R3I6.js.map +0 -1
  143. package/dist/post-compact-LR3DSGT3.js.map +0 -1
  144. package/dist/post-tool-use-SOFVNFU3.js.map +0 -1
  145. package/dist/post-tool-use-failure-2CZZZASB.js +0 -28
  146. package/dist/post-tool-use-failure-2CZZZASB.js.map +0 -1
  147. package/dist/pre-compact-3E3D6565.js.map +0 -1
  148. package/dist/session-end-YMQ44U6Z.js.map +0 -1
  149. package/dist/stop-WSFGRPXZ.js.map +0 -1
  150. package/dist/stop-failure-4FR7574F.js.map +0 -1
  151. package/dist/subagent-stop-MRVTNX3V.js +0 -28
  152. package/dist/subagent-stop-MRVTNX3V.js.map +0 -1
  153. package/dist/task-completed-XXPYPSRV.js +0 -27
  154. package/dist/task-completed-XXPYPSRV.js.map +0 -1
  155. package/dist/ui/assets/index-CPA_uq_j.js +0 -794
  156. package/dist/update-W3UFZU4G.js.map +0 -1
  157. package/dist/user-prompt-submit-LSWCYUW3.js.map +0 -1
  158. package/hooks/hooks.json +0 -137
  159. /package/dist/{agent-run-CGXF5PPC.js.map → agent-run-5KYQJQTY.js.map} +0 -0
  160. /package/dist/{agent-tasks-T7NVI3R7.js.map → agent-tasks-N7BDYKGB.js.map} +0 -0
  161. /package/dist/{chunk-XLY3REL3.js.map → chunk-4VSNNMEU.js.map} +0 -0
  162. /package/dist/{chunk-5LPERML5.js.map → chunk-7NBDELZB.js.map} +0 -0
  163. /package/dist/{chunk-ZMW6KQX2.js.map → chunk-D4ESHOOJ.js.map} +0 -0
  164. /package/dist/{chunk-YZMNEIFI.js.map → chunk-DPJVKNNP.js.map} +0 -0
  165. /package/dist/{chunk-AEJS57ZK.js.map → chunk-J3L2RTYK.js.map} +0 -0
  166. /package/dist/{chunk-MKKXCCQ5.js.map → chunk-JHLALJPB.js.map} +0 -0
  167. /package/dist/{chunk-CUDM5YJY.js.map → chunk-JROOQQH6.js.map} +0 -0
  168. /package/dist/{chunk-D6DXYAFK.js.map → chunk-LGPBVBFY.js.map} +0 -0
  169. /package/dist/{chunk-5SDH75YC.js.map → chunk-LUQBT2Y4.js.map} +0 -0
  170. /package/dist/{chunk-WZZH3YXJ.js.map → chunk-PW5QVY44.js.map} +0 -0
  171. /package/dist/{chunk-U7UUJ4FD.js.map → chunk-Q2AYS2QE.js.map} +0 -0
  172. /package/dist/{chunk-FPMEIN2W.js.map → chunk-QL2RBFIC.js.map} +0 -0
  173. /package/dist/{chunk-MSXYUXZR.js.map → chunk-RGRPAKEY.js.map} +0 -0
  174. /package/dist/{chunk-5QERXFH7.js.map → chunk-SW62AX75.js.map} +0 -0
  175. /package/dist/{chunk-FFQES5MC.js.map → chunk-TCGOSLW6.js.map} +0 -0
  176. /package/dist/{chunk-G2LQBFE3.js.map → chunk-TY7A5OZ5.js.map} +0 -0
  177. /package/dist/{chunk-C3AEZ3BZ.js.map → chunk-YRUJ5KGV.js.map} +0 -0
  178. /package/dist/{client-B27SN5QG.js.map → client-UGM6MG55.js.map} +0 -0
  179. /package/dist/{detect-H5OPI7GD.js.map → detect-27DN6UTL.js.map} +0 -0
  180. /package/dist/{detect-providers-AZ6DEQU7.js.map → detect-providers-JFE3QLJI.js.map} +0 -0
  181. /package/dist/{init-wizard-XNFOZCEB.js.map → init-wizard-WIUCR4JE.js.map} +0 -0
  182. /package/dist/{llm-XJFHRFHB.js.map → llm-O46QYWEM.js.map} +0 -0
  183. /package/dist/{loader-GKXR5ONU.js.map → loader-BQ4X4K3F.js.map} +0 -0
  184. /package/dist/{openai-embeddings-ST3B6GW7.js.map → openai-embeddings-HWAKOGUM.js.map} +0 -0
  185. /package/dist/{openrouter-HJHOO3EO.js.map → openrouter-GXZK7JXR.js.map} +0 -0
  186. /package/dist/{provider-check-SOTDYLJE.js.map → provider-check-CKZW3GQX.js.map} +0 -0
  187. /package/dist/{registry-WVZG6R2R.js.map → registry-ZHUVXGPO.js.map} +0 -0
  188. /package/dist/{resolution-events-UPHJJLDQ.js.map → resolution-events-WZHPQQMN.js.map} +0 -0
  189. /package/dist/{restart-XIUFVS33.js.map → restart-YYJ7SH4K.js.map} +0 -0
  190. /package/dist/{search-VB6Z2ZXV.js.map → search-L7KTBURJ.js.map} +0 -0
  191. /package/dist/{server-AKPBRP6Z.js.map → server-GMRVF2PB.js.map} +0 -0
  192. /package/dist/{session-UVZS6CY5.js.map → session-V3SNFG7J.js.map} +0 -0
  193. /package/dist/{setup-llm-NWHOPJUV.js.map → setup-llm-5AMWEAJ5.js.map} +0 -0
  194. /package/dist/{stats-CDQXOTEC.js.map → stats-B2V7P45Y.js.map} +0 -0
  195. /package/dist/{team-XMHYCKFF.js.map → team-TBS5OILG.js.map} +0 -0
  196. /package/dist/{verify-O7TQ5DDY.js.map → verify-D7EDVXO5.js.map} +0 -0
  197. /package/dist/{version-VWWY7SPQ.js.map → version-GTFCEIJ2.js.map} +0 -0
@@ -5,7 +5,7 @@
5
5
  <link rel="icon" type="image/svg+xml" href="/favicon.svg" />
6
6
  <meta name="viewport" content="width=device-width, initial-scale=1.0" />
7
7
  <title>Myco</title>
8
- <script type="module" crossorigin src="/assets/index-CPA_uq_j.js"></script>
8
+ <script type="module" crossorigin src="/assets/index-aMc07Ym5.js"></script>
9
9
  <link rel="stylesheet" crossorigin href="/assets/index-BGbil7f1.css">
10
10
  </head>
11
11
  <body>
@@ -1,32 +1,38 @@
1
1
  import { createRequire as __cr } from 'node:module'; const require = __cr(import.meta.url);
2
2
  import {
3
- VAULT_GITIGNORE
4
- } from "./chunk-WXSJKESH.js";
3
+ VAULT_GITIGNORE,
4
+ registerSymbionts
5
+ } from "./chunk-YRHSTVCZ.js";
5
6
  import "./chunk-SAKJMNSR.js";
7
+ import "./chunk-LUQBT2Y4.js";
8
+ import "./chunk-MYX5NCRH.js";
9
+ import "./chunk-DPJVKNNP.js";
10
+ import "./chunk-PIRWYDOH.js";
11
+ import "./chunk-S6I62FAH.js";
12
+ import "./chunk-TY7A5OZ5.js";
6
13
  import {
7
- detectSymbionts
8
- } from "./chunk-5PEUFJ6U.js";
9
- import "./chunk-5SDH75YC.js";
14
+ loadManifests,
15
+ resolvePackageRoot
16
+ } from "./chunk-QFMBZ72S.js";
17
+ import "./chunk-LPUQPDC2.js";
10
18
  import "./chunk-D7TYRPRM.js";
11
19
  import "./chunk-E4VLWIJC.js";
12
20
  import "./chunk-KH64DHOY.js";
13
- import "./chunk-MYX5NCRH.js";
14
- import "./chunk-YZMNEIFI.js";
15
- import "./chunk-76ZO5RGT.js";
16
- import "./chunk-S6I62FAH.js";
17
- import "./chunk-G2LQBFE3.js";
18
- import "./chunk-LPUQPDC2.js";
19
21
  import {
20
22
  resolveVaultDir
21
23
  } from "./chunk-JTYZRPX5.js";
22
24
  import "./chunk-PZUWP5VK.js";
23
25
 
24
26
  // src/cli/update.ts
25
- import { execFileSync } from "child_process";
26
27
  import fs from "fs";
27
28
  import path from "path";
28
29
  async function run(args) {
29
- const vaultDir = resolveVaultDir();
30
+ let projectRoot;
31
+ const projectIdx = args.indexOf("--project");
32
+ if (projectIdx !== -1 && args[projectIdx + 1]) {
33
+ projectRoot = args[projectIdx + 1];
34
+ }
35
+ const vaultDir = projectRoot ? path.join(projectRoot, ".myco") : resolveVaultDir();
30
36
  if (!fs.existsSync(path.join(vaultDir, "myco.yaml"))) {
31
37
  console.error(`No myco.yaml found in ${vaultDir}. Run 'myco init' first.`);
32
38
  process.exit(1);
@@ -43,27 +49,17 @@ async function run(args) {
43
49
  } else {
44
50
  console.log(" \u2013 .gitignore is current");
45
51
  }
46
- const projectRoot = path.dirname(vaultDir);
47
- const detected = detectSymbionts(projectRoot);
48
- if (detected.length > 0) {
49
- for (const d of detected) {
50
- try {
51
- if (d.manifest.pluginInstallCommands.length > 0) {
52
- for (const cmd of d.manifest.pluginInstallCommands) {
53
- const [bin, ...cmdArgs] = cmd.split(" ");
54
- execFileSync(bin, cmdArgs, { stdio: "inherit" });
55
- }
56
- console.log(` \u2713 Updated ${d.manifest.displayName} plugin`);
57
- updatedCount++;
58
- } else {
59
- console.log(` \u2013 ${d.manifest.displayName}: no automated update available`);
60
- }
61
- } catch (err) {
62
- console.error(` \u2717 Failed to update ${d.manifest.displayName}: ${err.message}`);
63
- }
64
- }
52
+ const resolvedProjectRoot = projectRoot ?? path.dirname(vaultDir);
53
+ const allManifests = loadManifests();
54
+ const pkgRoot = resolvePackageRoot();
55
+ const configured = allManifests.filter(
56
+ (m) => fs.existsSync(path.join(resolvedProjectRoot, m.configDir))
57
+ );
58
+ if (configured.length > 0) {
59
+ const registered = registerSymbionts(configured, resolvedProjectRoot, pkgRoot, "Updated");
60
+ updatedCount += registered;
65
61
  } else {
66
- console.log(" \u2013 No agents detected");
62
+ console.log(" \u2013 No configured agents found");
67
63
  }
68
64
  console.log("");
69
65
  if (updatedCount > 0) {
@@ -76,4 +72,4 @@ async function run(args) {
76
72
  export {
77
73
  run
78
74
  };
79
- //# sourceMappingURL=update-W3UFZU4G.js.map
75
+ //# sourceMappingURL=update-4NVFET56.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/cli/update.ts"],"sourcesContent":["import { resolveVaultDir } from '../vault/resolve.js';\nimport { VAULT_GITIGNORE, registerSymbionts } from './shared.js';\nimport { loadManifests, resolvePackageRoot } from '../symbionts/detect.js';\nimport fs from 'node:fs';\nimport path from 'node:path';\n\nexport async function run(args: string[]): Promise<void> {\n // Support --project <path> for detached update scripts\n let projectRoot: string | undefined;\n const projectIdx = args.indexOf('--project');\n if (projectIdx !== -1 && args[projectIdx + 1]) {\n projectRoot = args[projectIdx + 1];\n }\n\n const vaultDir = projectRoot\n ? path.join(projectRoot, '.myco')\n : resolveVaultDir();\n if (!fs.existsSync(path.join(vaultDir, 'myco.yaml'))) {\n console.error(`No myco.yaml found in ${vaultDir}. Run 'myco init' first.`);\n process.exit(1);\n }\n\n console.log(`Updating Myco vault at ${vaultDir}\\n`);\n\n let updatedCount = 0;\n\n // --- Update .gitignore to match current template ---\n\n const gitignorePath = path.join(vaultDir, '.gitignore');\n const currentGitignore = fs.existsSync(gitignorePath)\n ? fs.readFileSync(gitignorePath, 'utf-8')\n : '';\n\n if (currentGitignore !== VAULT_GITIGNORE) {\n fs.writeFileSync(gitignorePath, VAULT_GITIGNORE, 'utf-8');\n console.log(' \\u2713 Updated .gitignore');\n updatedCount++;\n } else {\n console.log(' \\u2013 .gitignore is current');\n }\n\n // --- Update symbiont registration (only agents already configured) ---\n\n const resolvedProjectRoot = projectRoot ?? path.dirname(vaultDir);\n const allManifests = loadManifests();\n const pkgRoot = resolvePackageRoot();\n // Only update agents whose config directory already exists in the project\n const configured = allManifests.filter((m) =>\n fs.existsSync(path.join(resolvedProjectRoot, m.configDir)),\n );\n\n if (configured.length > 0) {\n const registered = registerSymbionts(configured, resolvedProjectRoot, pkgRoot, 'Updated');\n updatedCount += registered;\n } else {\n console.log(' \\u2013 No configured agents found');\n }\n\n // --- Summary ---\n\n console.log('');\n if (updatedCount > 0) {\n console.log(`Updated ${updatedCount} item${updatedCount > 1 ? 's' : ''}.`);\n } else {\n console.log('Everything is up to date.');\n }\n console.log('Run `myco doctor` to verify setup health.');\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;AAGA,OAAO,QAAQ;AACf,OAAO,UAAU;AAEjB,eAAsB,IAAI,MAA+B;AAEvD,MAAI;AACJ,QAAM,aAAa,KAAK,QAAQ,WAAW;AAC3C,MAAI,eAAe,MAAM,KAAK,aAAa,CAAC,GAAG;AAC7C,kBAAc,KAAK,aAAa,CAAC;AAAA,EACnC;AAEA,QAAM,WAAW,cACb,KAAK,KAAK,aAAa,OAAO,IAC9B,gBAAgB;AACpB,MAAI,CAAC,GAAG,WAAW,KAAK,KAAK,UAAU,WAAW,CAAC,GAAG;AACpD,YAAQ,MAAM,yBAAyB,QAAQ,0BAA0B;AACzE,YAAQ,KAAK,CAAC;AAAA,EAChB;AAEA,UAAQ,IAAI,0BAA0B,QAAQ;AAAA,CAAI;AAElD,MAAI,eAAe;AAInB,QAAM,gBAAgB,KAAK,KAAK,UAAU,YAAY;AACtD,QAAM,mBAAmB,GAAG,WAAW,aAAa,IAChD,GAAG,aAAa,eAAe,OAAO,IACtC;AAEJ,MAAI,qBAAqB,iBAAiB;AACxC,OAAG,cAAc,eAAe,iBAAiB,OAAO;AACxD,YAAQ,IAAI,6BAA6B;AACzC;AAAA,EACF,OAAO;AACL,YAAQ,IAAI,gCAAgC;AAAA,EAC9C;AAIA,QAAM,sBAAsB,eAAe,KAAK,QAAQ,QAAQ;AAChE,QAAM,eAAe,cAAc;AACnC,QAAM,UAAU,mBAAmB;AAEnC,QAAM,aAAa,aAAa;AAAA,IAAO,CAAC,MACtC,GAAG,WAAW,KAAK,KAAK,qBAAqB,EAAE,SAAS,CAAC;AAAA,EAC3D;AAEA,MAAI,WAAW,SAAS,GAAG;AACzB,UAAM,aAAa,kBAAkB,YAAY,qBAAqB,SAAS,SAAS;AACxF,oBAAgB;AAAA,EAClB,OAAO;AACL,YAAQ,IAAI,qCAAqC;AAAA,EACnD;AAIA,UAAQ,IAAI,EAAE;AACd,MAAI,eAAe,GAAG;AACpB,YAAQ,IAAI,WAAW,YAAY,QAAQ,eAAe,IAAI,MAAM,EAAE,GAAG;AAAA,EAC3E,OAAO;AACL,YAAQ,IAAI,2BAA2B;AAAA,EACzC;AACA,UAAQ,IAAI,2CAA2C;AACzD;","names":[]}
@@ -3,15 +3,20 @@ import {
3
3
  EventBuffer
4
4
  } from "./chunk-V7XG6V6C.js";
5
5
  import {
6
+ normalizeHookInput,
6
7
  readStdin
7
- } from "./chunk-J4RVYUH4.js";
8
+ } from "./chunk-RR75ZKEV.js";
8
9
  import {
9
10
  DaemonClient
10
- } from "./chunk-YZMNEIFI.js";
11
- import "./chunk-76ZO5RGT.js";
11
+ } from "./chunk-DPJVKNNP.js";
12
+ import "./chunk-PIRWYDOH.js";
12
13
  import "./chunk-S6I62FAH.js";
13
- import "./chunk-G2LQBFE3.js";
14
+ import "./chunk-TY7A5OZ5.js";
15
+ import "./chunk-QFMBZ72S.js";
14
16
  import "./chunk-LPUQPDC2.js";
17
+ import "./chunk-D7TYRPRM.js";
18
+ import "./chunk-E4VLWIJC.js";
19
+ import "./chunk-KH64DHOY.js";
15
20
  import {
16
21
  resolveVaultDir
17
22
  } from "./chunk-JTYZRPX5.js";
@@ -24,9 +29,10 @@ async function main() {
24
29
  const VAULT_DIR = resolveVaultDir();
25
30
  if (!fs.existsSync(path.join(VAULT_DIR, "myco.yaml"))) return;
26
31
  try {
27
- const input = JSON.parse(await readStdin());
32
+ const rawInput = JSON.parse(await readStdin());
33
+ const input = normalizeHookInput(rawInput);
28
34
  const prompt = input.prompt ?? "";
29
- const sessionId = input.session_id ?? `s-${Date.now()}`;
35
+ const sessionId = input.sessionId;
30
36
  const client = new DaemonClient(VAULT_DIR);
31
37
  if (!await client.isHealthy()) {
32
38
  client.spawnDaemon();
@@ -34,7 +40,8 @@ async function main() {
34
40
  const eventResult = await client.post("/events", {
35
41
  type: "user_prompt",
36
42
  prompt,
37
- session_id: sessionId
43
+ session_id: sessionId,
44
+ agent: input.agent
38
45
  });
39
46
  if (!eventResult.ok) {
40
47
  const buffer = new EventBuffer(path.join(VAULT_DIR, "buffer"), sessionId);
@@ -56,4 +63,4 @@ ${sessionLine}` : sessionLine;
56
63
  export {
57
64
  main
58
65
  };
59
- //# sourceMappingURL=user-prompt-submit-LSWCYUW3.js.map
66
+ //# sourceMappingURL=user-prompt-submit-X4BCPMZ4.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/hooks/user-prompt-submit.ts"],"sourcesContent":["import { DaemonClient } from './client.js';\nimport { readStdin } from './read-stdin.js';\nimport { normalizeHookInput } from './normalize.js';\nimport { EventBuffer } from '../capture/buffer.js';\nimport { resolveVaultDir } from '../vault/resolve.js';\nimport fs from 'node:fs';\nimport path from 'node:path';\n\nexport async function main() {\n const VAULT_DIR = resolveVaultDir();\n if (!fs.existsSync(path.join(VAULT_DIR, 'myco.yaml'))) return;\n\n try {\n const rawInput = JSON.parse(await readStdin());\n const input = normalizeHookInput(rawInput);\n const prompt = input.prompt ?? '';\n const sessionId = input.sessionId;\n\n const client = new DaemonClient(VAULT_DIR);\n // Spawn daemon if needed but don't block on full health check backoff.\n // The event POST will fail fast if daemon isn't ready — buffer absorbs it.\n if (!(await client.isHealthy())) {\n client.spawnDaemon();\n }\n\n // Forward prompt as event for capture\n const eventResult = await client.post('/events', {\n type: 'user_prompt', prompt, session_id: sessionId, agent: input.agent,\n });\n\n if (!eventResult.ok) {\n // Daemon still unreachable — write directly to buffer for later processing\n const buffer = new EventBuffer(path.join(VAULT_DIR, 'buffer'), sessionId);\n buffer.append({ type: 'user_prompt', prompt });\n }\n\n // Search for relevant spores to inject as context for this prompt.\n // The daemon does a vector search against the prompt text and returns\n // any high-relevance spores. This is fast (~20ms) — no LLM call.\n const contextResult = await client.post('/context/prompt', {\n prompt,\n session_id: sessionId,\n });\n\n // Always include the session ID so the agent can pass it to myco_remember.\n // Uses Session:: format consistent with daemon context injection (Branch::, Session::).\n const sessionLine = `Session:: \\`${sessionId}\\``;\n const contextText = contextResult.ok && contextResult.data?.text\n ? `${contextResult.data.text}\\n${sessionLine}`\n : sessionLine;\n\n process.stdout.write(contextText);\n } catch (error) {\n process.stderr.write(`[myco] user-prompt-submit error: ${(error as Error).message}\\n`);\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;AAKA,OAAO,QAAQ;AACf,OAAO,UAAU;AAEjB,eAAsB,OAAO;AAC3B,QAAM,YAAY,gBAAgB;AAClC,MAAI,CAAC,GAAG,WAAW,KAAK,KAAK,WAAW,WAAW,CAAC,EAAG;AAEvD,MAAI;AACF,UAAM,WAAW,KAAK,MAAM,MAAM,UAAU,CAAC;AAC7C,UAAM,QAAQ,mBAAmB,QAAQ;AACzC,UAAM,SAAS,MAAM,UAAU;AAC/B,UAAM,YAAY,MAAM;AAExB,UAAM,SAAS,IAAI,aAAa,SAAS;AAGzC,QAAI,CAAE,MAAM,OAAO,UAAU,GAAI;AAC/B,aAAO,YAAY;AAAA,IACrB;AAGA,UAAM,cAAc,MAAM,OAAO,KAAK,WAAW;AAAA,MAC/C,MAAM;AAAA,MAAe;AAAA,MAAQ,YAAY;AAAA,MAAW,OAAO,MAAM;AAAA,IACnE,CAAC;AAED,QAAI,CAAC,YAAY,IAAI;AAEnB,YAAM,SAAS,IAAI,YAAY,KAAK,KAAK,WAAW,QAAQ,GAAG,SAAS;AACxE,aAAO,OAAO,EAAE,MAAM,eAAe,OAAO,CAAC;AAAA,IAC/C;AAKA,UAAM,gBAAgB,MAAM,OAAO,KAAK,mBAAmB;AAAA,MACzD;AAAA,MACA,YAAY;AAAA,IACd,CAAC;AAID,UAAM,cAAc,eAAe,SAAS;AAC5C,UAAM,cAAc,cAAc,MAAM,cAAc,MAAM,OACxD,GAAG,cAAc,KAAK,IAAI;AAAA,EAAK,WAAW,KAC1C;AAEJ,YAAQ,OAAO,MAAM,WAAW;AAAA,EAClC,SAAS,OAAO;AACd,YAAQ,OAAO,MAAM,oCAAqC,MAAgB,OAAO;AAAA,CAAI;AAAA,EACvF;AACF;","names":[]}
@@ -1,19 +1,19 @@
1
1
  import { createRequire as __cr } from 'node:module'; const require = __cr(import.meta.url);
2
2
  import {
3
3
  createEmbeddingProvider
4
- } from "./chunk-MKKXCCQ5.js";
5
- import "./chunk-AEJS57ZK.js";
6
- import "./chunk-5QERXFH7.js";
7
- import "./chunk-FPMEIN2W.js";
8
- import "./chunk-5SDH75YC.js";
4
+ } from "./chunk-JHLALJPB.js";
5
+ import "./chunk-J3L2RTYK.js";
6
+ import "./chunk-SW62AX75.js";
7
+ import "./chunk-QL2RBFIC.js";
8
+ import "./chunk-LUQBT2Y4.js";
9
9
  import {
10
10
  loadConfig
11
11
  } from "./chunk-MAZOVVDU.js";
12
+ import "./chunk-PIRWYDOH.js";
13
+ import "./chunk-S6I62FAH.js";
12
14
  import "./chunk-D7TYRPRM.js";
13
15
  import "./chunk-E4VLWIJC.js";
14
16
  import "./chunk-KH64DHOY.js";
15
- import "./chunk-76ZO5RGT.js";
16
- import "./chunk-S6I62FAH.js";
17
17
  import "./chunk-PZUWP5VK.js";
18
18
 
19
19
  // src/cli/verify.ts
@@ -42,4 +42,4 @@ async function run(_args, vaultDir) {
42
42
  export {
43
43
  run
44
44
  };
45
- //# sourceMappingURL=verify-O7TQ5DDY.js.map
45
+ //# sourceMappingURL=verify-D7EDVXO5.js.map
@@ -1,10 +1,10 @@
1
1
  import { createRequire as __cr } from 'node:module'; const require = __cr(import.meta.url);
2
2
  import {
3
3
  getPluginVersion
4
- } from "./chunk-G2LQBFE3.js";
4
+ } from "./chunk-TY7A5OZ5.js";
5
5
  import "./chunk-LPUQPDC2.js";
6
6
  import "./chunk-PZUWP5VK.js";
7
7
  export {
8
8
  getPluginVersion
9
9
  };
10
- //# sourceMappingURL=version-VWWY7SPQ.js.map
10
+ //# sourceMappingURL=version-GTFCEIJ2.js.map
package/package.json CHANGED
@@ -1,20 +1,19 @@
1
1
  {
2
2
  "name": "@goondocks/myco",
3
- "version": "0.10.0",
3
+ "version": "0.12.0",
4
4
  "description": "Collective agent intelligence — Claude Code plugin",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",
7
7
  "types": "dist/index.d.ts",
8
8
  "bin": {
9
- "myco": "dist/src/cli.js"
9
+ "myco": "dist/src/cli.js",
10
+ "myco-run": "bin/myco-run"
10
11
  },
11
12
  "files": [
12
13
  "bin/",
13
14
  "dist/",
14
15
  "commands/",
15
16
  "skills/",
16
- "hooks/",
17
- ".claude-plugin/",
18
17
  "CONTRIBUTING.md"
19
18
  ],
20
19
  "scripts": {
@@ -42,6 +41,7 @@
42
41
  "better-sqlite3": "^12.8.0",
43
42
  "chokidar": "^5.0.0",
44
43
  "gray-matter": "^4.0.3",
44
+ "semver": "^7.7.4",
45
45
  "sqlite-vec": "^0.1.7",
46
46
  "yaml": "^2.4.0",
47
47
  "zod": "^4.3.6"
@@ -49,6 +49,7 @@
49
49
  "devDependencies": {
50
50
  "@types/better-sqlite3": "^7.6.13",
51
51
  "@types/node": "^25.5.0",
52
+ "@types/semver": "^7.7.1",
52
53
  "tsup": "^8.0.0",
53
54
  "tsx": "^4.0.0",
54
55
  "typescript": "^5.5.0",
@@ -33,6 +33,26 @@ Rules files contain **project invariants** — things every agent must follow ev
33
33
 
34
34
  **The test:** If it's an invariant that applies to every session on every branch, it's a rule. If it depends on what you're working on, it's context — let Myco inject it.
35
35
 
36
+ ## Multi-Agent File Topology
37
+
38
+ Myco supports 6 coding agents. Each has its own instruction file format, but **`AGENTS.md` is the canonical source of truth** for all project rules.
39
+
40
+ ### File hierarchy
41
+
42
+ | File | Purpose | Who reads it |
43
+ |------|---------|-------------|
44
+ | `AGENTS.md` | **Canonical rules** — all architecture, conventions, golden paths | Codex, VS Code Copilot, Gemini CLI, Windsurf, Cursor |
45
+ | `CLAUDE.md` | Thin stub pointing to `AGENTS.md` + Claude-specific overrides | Claude Code |
46
+ | `GEMINI.md` | Thin stub pointing to `AGENTS.md` + Gemini-specific overrides | Gemini CLI |
47
+ | `.github/copilot-instructions.md` | Thin stub pointing to `AGENTS.md` | VS Code Copilot |
48
+
49
+ ### Rules for placement
50
+
51
+ - **All rules go in `AGENTS.md`** unless they are genuinely agent-specific (e.g., "Use Claude Code agent teams for X")
52
+ - Agent-specific files MUST start with a reference to `AGENTS.md` as the source of truth
53
+ - Never duplicate rules across files — if it applies to all agents, it belongs in `AGENTS.md`
54
+ - If a project has `CLAUDE.md` with substantial rules but no `AGENTS.md`, suggest migrating the rules to `AGENTS.md` and replacing `CLAUDE.md` with a thin stub
55
+
36
56
  ## Rule Writing Principles
37
57
 
38
58
  These principles apply whether you're writing new rules or auditing existing ones.
@@ -93,11 +113,13 @@ Specific commands that must pass before work is done. Example: "Before committin
93
113
 
94
114
  ### Step 1: Discover existing rules files
95
115
 
96
- Scan the project root and subdirectories for:
97
- - `CLAUDE.md` (root and subdirectories)
98
- - `AGENTS.md` (root)
116
+ Scan the project root for:
117
+ - `AGENTS.md` (canonical should exist in every Myco project)
118
+ - `CLAUDE.md` (Claude Code stub/overrides)
119
+ - `GEMINI.md` (Gemini CLI stub/overrides)
120
+ - `.github/copilot-instructions.md` (VS Code Copilot stub)
99
121
 
100
- Report what exists and what doesn't. If neither exists, offer to create CLAUDE.md.
122
+ Report what exists. If `AGENTS.md` doesn't exist, offer to create it. If `CLAUDE.md` has substantial rules but `AGENTS.md` doesn't exist, offer to migrate.
101
123
 
102
124
  ### Step 2: Run audit checks
103
125
 
@@ -144,11 +166,12 @@ Edit the rules file with approved changes. Never auto-commit — the developer r
144
166
  1. Developer describes the rule they want
145
167
  2. Craft the rule: specific, anchored, RFC 2119 language
146
168
  3. Determine placement:
147
- - **CLAUDE.md**Rules specific to Claude Code (tool patterns, commit conventions, test commands)
148
- - **AGENTS.md**Universal rules any agent should follow (architecture, golden paths, conventions)
149
- - If only one file exists, put it there
150
- - If neither exists, create CLAUDE.md
151
- - If CLAUDE.md contains agent-agnostic rules (architecture, golden paths), suggest creating AGENTS.md and moving them there
169
+ - **`AGENTS.md`**All rules that any agent should follow (architecture, golden paths, conventions, quality gates). This is the default.
170
+ - **`CLAUDE.md`**Only Claude Code-specific rules (agent team patterns, Claude-specific tool conventions)
171
+ - **`GEMINI.md`** Only Gemini CLI-specific rules
172
+ - **`.github/copilot-instructions.md`** Only VS Code Copilot-specific rules
173
+ - If only `CLAUDE.md` exists with agent-agnostic rules, suggest creating `AGENTS.md` and migrating rules there
174
+ - If `AGENTS.md` doesn't exist, create it as the canonical file
152
175
  4. Find the correct section (invariant, golden path, quality gate, etc.)
153
176
  5. Insert the rule
154
177
  6. Developer reviews the diff
@@ -1,26 +0,0 @@
1
- {
2
- "name": "myco-plugins",
3
- "owner": {
4
- "name": "goondocks-co"
5
- },
6
- "metadata": {
7
- "description": "Myco — collective agent intelligence plugins"
8
- },
9
- "plugins": [
10
- {
11
- "name": "myco",
12
- "source": ".",
13
- "description": "Collective agent intelligence — captures session knowledge and serves it back via MCP",
14
- "license": "MIT",
15
- "keywords": [
16
- "intelligence",
17
- "memory",
18
- "mcp",
19
- "sessions",
20
- "team",
21
- "knowledge"
22
- ],
23
- "category": "productivity"
24
- }
25
- ]
26
- }
@@ -1,27 +0,0 @@
1
- {
2
- "name": "myco",
3
- "version": "0.10.0",
4
- "description": "Collective agent intelligence — captures session knowledge and serves it back to your team via MCP",
5
- "author": {
6
- "name": "goondocks-co",
7
- "url": "https://github.com/goondocks-co"
8
- },
9
- "license": "MIT",
10
- "keywords": [
11
- "intelligence",
12
- "memory",
13
- "mcp",
14
- "sessions",
15
- "team",
16
- "knowledge"
17
- ],
18
- "mcpServers": {
19
- "myco": {
20
- "command": "${CLAUDE_PLUGIN_ROOT}/bin/myco-run",
21
- "args": [
22
- "mcp"
23
- ],
24
- "env": {}
25
- }
26
- }
27
- }
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/symbionts/manifest-schema.ts","../src/symbionts/detect.ts"],"sourcesContent":["import { z } from 'zod';\n\nconst CaptureManifestSchema = z.object({\n planDirs: z.array(z.string()).default([]),\n});\n\nexport const SymbiontManifestSchema = z.object({\n name: z.string(),\n displayName: z.string(),\n binary: z.string(),\n configDir: z.string(),\n pluginRootEnvVar: z.string(),\n pluginInstallCommands: z.array(z.string()).default([]),\n settingsPath: z.string().optional(),\n mcpConfigPath: z.string().optional(),\n hookFields: z.object({\n transcriptPath: z.string(),\n lastResponse: z.string(),\n sessionId: z.string(),\n }),\n capture: CaptureManifestSchema.optional(),\n});\n\nexport type SymbiontManifest = z.infer<typeof SymbiontManifestSchema>;\n","import { SymbiontManifestSchema, type SymbiontManifest } from './manifest-schema.js';\nimport { findPackageRoot } from '../utils/find-package-root.js';\nimport { execFileSync } from 'node:child_process';\nimport fs from 'node:fs';\nimport path from 'node:path';\nimport YAML from 'yaml';\n\nexport interface DetectedSymbiont {\n manifest: SymbiontManifest;\n binaryFound: boolean;\n configDirFound: boolean;\n}\n\nconst MANIFESTS_SUBDIR = 'symbionts/manifests';\n\n/** Cached manifests — static files that never change at runtime. */\nlet manifestCache: SymbiontManifest[] | null = null;\n\n/** Load all symbiont manifests from the package's dist directory. */\nexport function loadManifests(): SymbiontManifest[] {\n if (manifestCache) return manifestCache;\n const candidates = [\n // Source layout: src/symbionts/detect.ts → src/symbionts/manifests/\n path.resolve(import.meta.dirname, MANIFESTS_SUBDIR),\n // Dist layout: dist/src/symbionts/ → dist/src/symbionts/manifests/\n // (or dist/src/daemon/ → dist/src/symbionts/manifests/)\n path.resolve(import.meta.dirname, '..', MANIFESTS_SUBDIR),\n path.resolve(import.meta.dirname, '..', '..', MANIFESTS_SUBDIR),\n // Chunk layout: dist/chunk-*.js → dist/src/symbionts/manifests/\n path.resolve(import.meta.dirname, 'src', MANIFESTS_SUBDIR),\n ];\n\n for (const dir of candidates) {\n if (!fs.existsSync(dir)) continue;\n const files = fs.readdirSync(dir).filter(f => f.endsWith('.yaml'));\n if (files.length === 0) continue;\n manifestCache = files.map(f => {\n const raw = YAML.parse(fs.readFileSync(path.join(dir, f), 'utf-8'));\n return SymbiontManifestSchema.parse(raw);\n });\n return manifestCache;\n }\n return [];\n}\n\n/** Check if a binary is available on PATH. */\nfunction isBinaryOnPath(binary: string): boolean {\n try {\n execFileSync('which', [binary], { stdio: 'pipe' });\n return true;\n } catch {\n return false;\n }\n}\n\n/** Detect which symbionts are available for a project. */\nexport function detectSymbionts(projectRoot: string): DetectedSymbiont[] {\n const manifests = loadManifests();\n return manifests.map(manifest => ({\n manifest,\n binaryFound: isBinaryOnPath(manifest.binary),\n configDirFound: fs.existsSync(path.join(projectRoot, manifest.configDir)),\n })).filter(d => d.binaryFound || d.configDirFound);\n}\n\n/** Find the Myco package root (where package.json lives). */\nexport function resolvePackageRoot(): string {\n return findPackageRoot(import.meta.dirname) ?? process.cwd();\n}\n"],"mappings":";;;;;;;;;;;;;;;AAEA,IAAM,wBAAwB,iBAAE,OAAO;AAAA,EACrC,UAAU,iBAAE,MAAM,iBAAE,OAAO,CAAC,EAAE,QAAQ,CAAC,CAAC;AAC1C,CAAC;AAEM,IAAM,yBAAyB,iBAAE,OAAO;AAAA,EAC7C,MAAM,iBAAE,OAAO;AAAA,EACf,aAAa,iBAAE,OAAO;AAAA,EACtB,QAAQ,iBAAE,OAAO;AAAA,EACjB,WAAW,iBAAE,OAAO;AAAA,EACpB,kBAAkB,iBAAE,OAAO;AAAA,EAC3B,uBAAuB,iBAAE,MAAM,iBAAE,OAAO,CAAC,EAAE,QAAQ,CAAC,CAAC;AAAA,EACrD,cAAc,iBAAE,OAAO,EAAE,SAAS;AAAA,EAClC,eAAe,iBAAE,OAAO,EAAE,SAAS;AAAA,EACnC,YAAY,iBAAE,OAAO;AAAA,IACnB,gBAAgB,iBAAE,OAAO;AAAA,IACzB,cAAc,iBAAE,OAAO;AAAA,IACvB,WAAW,iBAAE,OAAO;AAAA,EACtB,CAAC;AAAA,EACD,SAAS,sBAAsB,SAAS;AAC1C,CAAC;;;AChBD,kBAAiB;AAHjB,SAAS,oBAAoB;AAC7B,OAAO,QAAQ;AACf,OAAO,UAAU;AASjB,IAAM,mBAAmB;AAGzB,IAAI,gBAA2C;AAGxC,SAAS,gBAAoC;AAClD,MAAI,cAAe,QAAO;AAC1B,QAAM,aAAa;AAAA;AAAA,IAEjB,KAAK,QAAQ,YAAY,SAAS,gBAAgB;AAAA;AAAA;AAAA,IAGlD,KAAK,QAAQ,YAAY,SAAS,MAAM,gBAAgB;AAAA,IACxD,KAAK,QAAQ,YAAY,SAAS,MAAM,MAAM,gBAAgB;AAAA;AAAA,IAE9D,KAAK,QAAQ,YAAY,SAAS,OAAO,gBAAgB;AAAA,EAC3D;AAEA,aAAW,OAAO,YAAY;AAC5B,QAAI,CAAC,GAAG,WAAW,GAAG,EAAG;AACzB,UAAM,QAAQ,GAAG,YAAY,GAAG,EAAE,OAAO,OAAK,EAAE,SAAS,OAAO,CAAC;AACjE,QAAI,MAAM,WAAW,EAAG;AACxB,oBAAgB,MAAM,IAAI,OAAK;AAC7B,YAAM,MAAM,YAAAA,QAAK,MAAM,GAAG,aAAa,KAAK,KAAK,KAAK,CAAC,GAAG,OAAO,CAAC;AAClE,aAAO,uBAAuB,MAAM,GAAG;AAAA,IACzC,CAAC;AACD,WAAO;AAAA,EACT;AACA,SAAO,CAAC;AACV;AAGA,SAAS,eAAe,QAAyB;AAC/C,MAAI;AACF,iBAAa,SAAS,CAAC,MAAM,GAAG,EAAE,OAAO,OAAO,CAAC;AACjD,WAAO;AAAA,EACT,QAAQ;AACN,WAAO;AAAA,EACT;AACF;AAGO,SAAS,gBAAgB,aAAyC;AACvE,QAAM,YAAY,cAAc;AAChC,SAAO,UAAU,IAAI,eAAa;AAAA,IAChC;AAAA,IACA,aAAa,eAAe,SAAS,MAAM;AAAA,IAC3C,gBAAgB,GAAG,WAAW,KAAK,KAAK,aAAa,SAAS,SAAS,CAAC;AAAA,EAC1E,EAAE,EAAE,OAAO,OAAK,EAAE,eAAe,EAAE,cAAc;AACnD;AAGO,SAAS,qBAA6B;AAC3C,SAAO,gBAAgB,YAAY,OAAO,KAAK,QAAQ,IAAI;AAC7D;","names":["YAML"]}
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/constants.ts"],"sourcesContent":["/**\n * Shared constants for the Myco codebase.\n * Per CLAUDE.md: \"No Magic Literals — Numeric and string constants\n * MUST NOT appear inline in logic.\"\n */\n\nexport { LOG_KINDS, type LogKind, kindToComponent } from './constants/log-kinds.js';\n\n// --- Agent phase prompt composition ---\n/**\n * Maximum chars per phase summary passed to subsequent phases.\n * Set to 4000 to ensure the digest-assess phase findings pass\n * untruncated to parallel tier phases.\n */\nexport const PHASE_SUMMARY_MAX_CHARS = 4000;\n\n// --- Token estimation ---\n/** Approximate characters per token for the chars/4 heuristic. */\nexport const CHARS_PER_TOKEN = 4;\n\n/** Estimate token count from character length using the CHARS_PER_TOKEN heuristic. */\nexport function estimateTokens(text: string): number {\n return Math.ceil(text.length / CHARS_PER_TOKEN);\n}\n\n// --- Time (primitives — must precede derived constants) ---\n/** Milliseconds per second. */\nexport const MS_PER_SECOND = 1000;\n\n// --- Embedding ---\n/** Max characters of text sent to the embedding model. */\nexport const EMBEDDING_INPUT_LIMIT = 8000;\n\n/** Max rows per embedding worker cycle. */\nexport const EMBEDDING_BATCH_SIZE = 10;\n\n/** Content hash algorithm for staleness detection. */\nexport const CONTENT_HASH_ALGORITHM = 'sha256';\n\n// --- Truncation limits (display/preview) ---\n/** Max chars for a user prompt preview in event summaries. */\nexport const PROMPT_PREVIEW_CHARS = 300;\n/** Max chars for an AI response preview in event summaries. */\nexport const AI_RESPONSE_PREVIEW_CHARS = 500;\n/** Max chars for a command string preview. */\nexport const COMMAND_PREVIEW_CHARS = 80;\n/** Max chars for a content snippet in search results. */\nexport const CONTENT_SNIPPET_CHARS = 120;\n/** Max chars for a tool output preview in hooks. */\nexport const TOOL_OUTPUT_PREVIEW_CHARS = 200;\n/** Max chars for a session summary preview in MCP tools. */\nexport const SESSION_SUMMARY_PREVIEW_CHARS = 300;\n/** Max chars for a recall summary preview. */\nexport const RECALL_SUMMARY_PREVIEW_CHARS = 200;\n/** Max chars for search result and hydrated context previews. */\nexport const SEARCH_PREVIEW_CHARS = 300;\n\n// --- Log preview limits (short previews for structured log fields) ---\n/** Max chars for a user prompt preview in log entries. */\nexport const LOG_PROMPT_PREVIEW_CHARS = 50;\n/** Max chars for an assistant message preview in log entries. */\nexport const LOG_MESSAGE_PREVIEW_CHARS = 80;\n/** Max chars for injected context preview in log entries. */\nexport const LOG_CONTEXT_PREVIEW_CHARS = 200;\n\n// --- Context injection layer budgets (chars, not tokens — used with .slice()) ---\nexport const CONTEXT_SESSION_PREVIEW_CHARS = 80;\nexport const CONTEXT_SPORE_PREVIEW_CHARS = 80;\n\n// --- Processor maxTokens budgets ---\n/** Response token budget for observation extraction. */\nexport const EXTRACTION_MAX_TOKENS = 2048;\n/** Response token budget for session summary. */\nexport const SUMMARY_MAX_TOKENS = 512;\n/** Response token budget for session title generation. */\nexport const TITLE_MAX_TOKENS = 32;\n\n// --- Timeouts ---\n/** Daemon client HTTP request timeout (ms). */\nexport const DAEMON_CLIENT_TIMEOUT_MS = 2000;\n/** Health check timeout (ms) — fail fast if daemon isn't responding. */\nexport const DAEMON_HEALTH_CHECK_TIMEOUT_MS = 500;\n/** LLM request timeout (ms). All LLM calls are background daemon work — no need to be aggressive. */\nexport const LLM_REQUEST_TIMEOUT_MS = 180_000;\n/** Embedding request timeout (ms). Embeddings run in background batch processing — generous timeout. */\nexport const EMBEDDING_REQUEST_TIMEOUT_MS = 60_000;\n/** Digest LLM request timeout (ms). Digest cycles use large context windows and may need model loading time. */\nexport const DIGEST_LLM_REQUEST_TIMEOUT_MS = 600_000;\n/** Stdin read timeout for hooks (ms). */\nexport const STDIN_TIMEOUT_MS = 100;\n/** Provider detection timeout for detect-providers CLI command (ms). */\nexport const PROVIDER_DETECT_TIMEOUT_MS = 3000;\n\n// --- Time ---\n/** Milliseconds in one day. */\nexport const MS_PER_DAY = 24 * 60 * 60 * 1000;\n\n/** Current Unix epoch in seconds. */\nexport function epochSeconds(): number {\n return Math.floor(Date.now() / MS_PER_SECOND);\n}\n\n// --- Buffer cleanup ---\n/** Max age for stale buffer files before cleanup (ms). */\nexport const STALE_BUFFER_MAX_AGE_MS = 1 * MS_PER_DAY;\n\n// --- Retry backoff ---\n/** Retry delays for daemon health check (ms). */\nexport const DAEMON_HEALTH_RETRY_DELAYS = [100, 200, 400, 800, 1500];\n\n/** Grace period after daemon.json is written before stale checks can trigger a restart (ms).\n * Prevents rapid restart loops from concurrent hooks or session reloads. */\nexport const DAEMON_STALE_GRACE_PERIOD_MS = 60_000;\n\n/** Grace period for SIGTERM before escalating to SIGKILL (ms).\n * Gives the old daemon a chance to shut down cleanly, but force-kills\n * to guarantee the configured port is reclaimed. */\nexport const DAEMON_EVICT_TIMEOUT_MS = 3000;\n/** Poll interval when waiting for an evicted daemon to die (ms). */\nexport const DAEMON_EVICT_POLL_MS = 100;\n\n// --- Slug limits ---\n/** Max length for slugified artifact IDs. */\n\n// --- Turn rendering ---\n/** Max file paths displayed per turn in session notes. */\nexport const TURN_MAX_FILES_DISPLAYED = 10;\n\n// --- Transcript mining ---\n/** Minimum content length to consider a transcript entry meaningful. */\nexport const MIN_TRANSCRIPT_CONTENT_LENGTH = 10;\n\n// --- Graph edge types (lineage — auto-created by daemon) ---\n/** Spore was extracted during this session. */\nexport const EDGE_TYPE_FROM_SESSION = 'FROM_SESSION';\n/** Spore was extracted from this prompt batch. */\nexport const EDGE_TYPE_EXTRACTED_FROM = 'EXTRACTED_FROM';\n/** Wisdom spore was derived from (consolidated) this source spore. */\nexport const EDGE_TYPE_DERIVED_FROM = 'DERIVED_FROM';\n/** Session contains this prompt batch. */\nexport const EDGE_TYPE_HAS_BATCH = 'HAS_BATCH';\n// --- Query defaults ---\n/** Default row limit for query module list operations. */\nexport const QUERY_DEFAULT_LIST_LIMIT = 100;\n/** Default confidence score for graph edges. */\nexport const GRAPH_EDGE_DEFAULT_CONFIDENCE = 1.0;\n\n// --- Query limits ---\n/** Max recent sessions to check for lineage heuristics. */\nexport const LINEAGE_RECENT_SESSIONS_LIMIT = 5;\n/** Max related spores to query for session notes. */\nexport const RELATED_SPORES_LIMIT = 50;\n\n// --- Context injection ---\n/** Max spores to inject per prompt. */\nexport const PROMPT_CONTEXT_MAX_SPORES = 3;\n/** Minimum similarity score for prompt context injection (0-1). */\nexport const PROMPT_CONTEXT_MIN_SIMILARITY = 0.3;\n/** Max token budget for session-start context injection. */\nexport const SESSION_CONTEXT_MAX_TOKENS = 500;\n/** Max token budget for per-prompt context injection. */\nexport const PROMPT_CONTEXT_MAX_TOKENS = 300;\n/** Minimum prompt length to trigger context search. */\nexport const PROMPT_CONTEXT_MIN_LENGTH = 10;\n\n/** Over-fetch multiplier for vector search to compensate for post-filtering. */\nexport const PROMPT_VECTOR_OVER_FETCH = 2;\n\n// --- Spore status filtering ---\n/** Spore statuses excluded from search results and context injection. */\nexport const EXCLUDED_SPORE_STATUSES = new Set(['superseded', 'archived']);\n\n// --- Agent identity ---\n/** Default agent ID for the built-in intelligence agent. */\nexport const DEFAULT_AGENT_ID = 'myco-agent';\n/** Agent ID for user-initiated MCP operations. */\nexport const USER_AGENT_ID = 'user';\n/** Agent name for user-initiated MCP operations. */\nexport const USER_AGENT_NAME = 'User (MCP)';\n\n// --- MCP tool defaults ---\n/** Default result limit for myco_search. */\nexport const MCP_SEARCH_DEFAULT_LIMIT = 10;\n/** Default result limit for myco_sessions. */\nexport const MCP_SESSIONS_DEFAULT_LIMIT = 20;\n/** Default result limit for myco_logs. */\nexport const MCP_LOGS_DEFAULT_LIMIT = 50;\n\n// --- Feed ---\n/** Default number of entries returned by the activity feed. */\nexport const FEED_DEFAULT_LIMIT = 50;\n\n// --- Digest — Tiers ---\n/** Available token-budget tiers for digest synthesis. */\nexport const DIGEST_TIERS = [1500, 5000, 10000] as const;\nexport type DigestTier = (typeof DIGEST_TIERS)[number];\n\n// --- Digest — Context window minimums per tier ---\n/** Minimum context window (tokens) required to run a digest at a given tier. */\nexport const DIGEST_TIER_MIN_CONTEXT: Record<number, number> = {\n 1500: 6500,\n 5000: 18500,\n 10000: 30500,\n};\n\n// --- Digest — Substrate ---\n/** Default minimum substrate notes required before a digest cycle runs. */\nexport const DIGEST_MIN_NOTES_FOR_CYCLE = 10;\n\n/** Scoring weights by note type when selecting substrate for synthesis. */\nexport const DIGEST_SUBSTRATE_TYPE_WEIGHTS: Record<string, number> = {\n session: 3,\n spore: 3,\n plan: 2,\n artifact: 1,\n team: 1,\n};\n\n// --- LLM reasoning control ---\n/** Reasoning mode for all Myco LLM calls. Suppresses chain-of-thought tokens from reasoning models. */\nexport const LLM_REASONING_MODE = 'off' as const;\n\n// --- Digest — System prompt overhead estimate ---\n\n// --- Vault intelligence ---\n/** Max candidate spores after post-filtering for supersession check. */\nexport const SUPERSESSION_CANDIDATE_LIMIT = 5;\n\n/** Over-fetch from vector index before post-filtering by status/type. */\nexport const SUPERSESSION_VECTOR_FETCH_LIMIT = 20;\n\n/** Max output tokens for supersession LLM evaluation. */\nexport const SUPERSESSION_MAX_TOKENS = 256;\n\n/** Similarity threshold for clustering related spores in batch agent processing. */\nexport const AGENT_CLUSTER_SIMILARITY = 0.75;\n\n// --- Search ---\n/** Default number of results returned by vector search and fullTextSearch. */\nexport const SEARCH_RESULTS_DEFAULT_LIMIT = 20;\n/** Minimum cosine similarity score for semantic search results (0-1). */\nexport const SEARCH_SIMILARITY_THRESHOLD = 0.3;\n\n// --- Pipeline processing ---\n/** Default page size for pipeline items API listing. */\nexport const PIPELINE_ITEMS_DEFAULT_LIMIT = 50;\n\n// --- Pipeline retry ---\n/** Max retries for parse (structural) pipeline failures — fail fast. */\nexport const PIPELINE_PARSE_MAX_RETRIES = 1;\n/** Exponential backoff multiplier for successive pipeline retries. */\nexport const PIPELINE_BACKOFF_MULTIPLIER = 4;\n\n// --- Pipeline stages (ordered) ---\nexport const PIPELINE_STAGES = ['capture', 'extraction', 'embedding', 'consolidation', 'digest'] as const;\nexport type PipelineStage = typeof PIPELINE_STAGES[number];\n\n// --- Pipeline statuses ---\nexport const PIPELINE_STATUSES = ['pending', 'processing', 'succeeded', 'failed', 'blocked', 'skipped', 'poisoned'] as const;\nexport type PipelineStatus = typeof PIPELINE_STATUSES[number];\n\n// --- Provider roles for circuit breakers ---\nexport const PIPELINE_PROVIDER_ROLES = ['llm', 'embedding', 'digest-llm'] as const;\nexport type PipelineProviderRole = typeof PIPELINE_PROVIDER_ROLES[number];\n\n// --- Stage to provider role mapping ---\nexport const STAGE_PROVIDER_MAP: Record<PipelineStage, PipelineProviderRole | null> = {\n capture: null,\n extraction: 'llm',\n embedding: 'embedding',\n consolidation: 'digest-llm',\n digest: 'digest-llm',\n};\n\n/**\n * Stages processed by the pipeline tick timer.\n * Capture is handled at registration time, digest is gated by the metabolism timer.\n */\nexport const PIPELINE_TICK_STAGES: PipelineStage[] = ['extraction', 'embedding', 'consolidation'];\n\n// --- Item type to applicable stages ---\n// Sessions skip consolidation — consolidation applies to the spores\n// extracted FROM sessions, not the session work item itself.\n// Lineage detection stays outside the pipeline (fire-and-forget, non-critical).\nexport const ITEM_STAGE_MAP: Record<string, PipelineStage[]> = {\n session: ['capture', 'extraction', 'embedding', 'digest'],\n spore: ['capture', 'embedding', 'consolidation', 'digest'],\n artifact: ['capture', 'embedding', 'digest'],\n};\n\n// --- User task registry ---\n/** Subdirectory within the vault for user-created task YAML files. */\nexport const USER_TASKS_DIR = 'tasks';\n\n/** Source label for user-created tasks. */\nexport const USER_TASK_SOURCE = 'user';\n\n/** Source label for built-in tasks shipped with the package. */\nexport const BUILT_IN_SOURCE = 'built-in';\n\n/** Task name validation pattern (lowercase, hyphens, digits). */\nexport const TASK_NAME_PATTERN = /^[a-z0-9][a-z0-9-]*[a-z0-9]$|^[a-z0-9]$/;\n\n/** Maximum length for task names. */\nexport const MAX_TASK_NAME_LENGTH = 50;\n\n// --- Automatic consolidation ---\n/** Minimum cluster size required before asking LLM to consolidate. */\nexport const CONSOLIDATION_MIN_CLUSTER_SIZE = 3;\n\n/** Over-fetch from vector index before post-filtering by status/type. */\nexport const CONSOLIDATION_VECTOR_FETCH_LIMIT = 20;\n\n/** Max output tokens for consolidation LLM synthesis.\n * Must be large enough for the full JSON response including content field. */\nexport const CONSOLIDATION_MAX_TOKENS = 2048;\n\n// --- Power management ---\n/** Time without activity before transitioning to idle (ms). */\nexport const POWER_IDLE_THRESHOLD_MS = 5 * 60 * MS_PER_SECOND;\n/** Time without activity before transitioning to sleep (ms). */\nexport const POWER_SLEEP_THRESHOLD_MS = 30 * 60 * MS_PER_SECOND;\n/** Time without activity before transitioning to deep sleep (ms). */\nexport const POWER_DEEP_SLEEP_THRESHOLD_MS = 90 * 60 * MS_PER_SECOND;\n/** Job cycle interval during active/idle states (ms). */\nexport const POWER_ACTIVE_INTERVAL_MS = 60 * MS_PER_SECOND;\n/** Job cycle interval during sleep state (ms). */\nexport const POWER_SLEEP_INTERVAL_MS = 5 * 60 * MS_PER_SECOND;\n\n// --- Session maintenance ---\n/** Time without new prompts before an active session is auto-completed (ms). */\nexport const STALE_SESSION_THRESHOLD_MS = 60 * 60 * MS_PER_SECOND;\n/** Max prompt count for a session to be considered dead and auto-deleted. */\nexport const DEAD_SESSION_MAX_PROMPTS = 1;\n\n// --- Init wizard ---\n/** Minimum Node.js major version required by Myco. */\nexport const MIN_NODE_MAJOR_VERSION = 22;\n\n/** Recommended context window for local intelligence models. */\nexport const RECOMMENDED_LOCAL_CONTEXT_WINDOW = 8192;\n\n/** Default Ollama embedding model recommended during init. */\nexport const DEFAULT_OLLAMA_EMBEDDING_MODEL = 'bge-m3';\n\n/** Default OpenAI embedding model recommended during init. */\nexport const DEFAULT_OPENAI_EMBEDDING_MODEL = 'text-embedding-3-small';\n\n// --- Sync protocol ---\n/** Protocol version for backup and team sync wire format. */\nexport const SYNC_PROTOCOL_VERSION = 1;\n\n// --- Team sync ---\n/** Default machine ID for rows created before multi-machine support. */\nexport const DEFAULT_MACHINE_ID = 'local';\n/** Prefix for team search result source attribution. */\nexport const TEAM_SOURCE_PREFIX = 'team:';\n/** Timeout for team search requests (ms). */\nexport const TEAM_SEARCH_TIMEOUT_MS = 3000;\n/** Timeout for team health check requests (ms). */\nexport const TEAM_HEALTH_TIMEOUT_MS = 5000;\n/** Secrets key for the team API key in secrets.env. */\nexport const TEAM_API_KEY_SECRET = 'MYCO_TEAM_API_KEY';\n/** Timeout for wrangler CLI commands (ms). */\nexport const WRANGLER_COMMAND_TIMEOUT_MS = 60_000;\n"],"mappings":";;;AAcO,IAAM,0BAA0B;AAIhC,IAAM,kBAAkB;AAGxB,SAAS,eAAe,MAAsB;AACnD,SAAO,KAAK,KAAK,KAAK,SAAS,eAAe;AAChD;AAIO,IAAM,gBAAgB;AAOtB,IAAM,uBAAuB;AAG7B,IAAM,yBAAyB;AAI/B,IAAM,uBAAuB;AAM7B,IAAM,wBAAwB;AAE9B,IAAM,4BAA4B;AAMlC,IAAM,uBAAuB;AAI7B,IAAM,2BAA2B;AAEjC,IAAM,4BAA4B;AAElC,IAAM,4BAA4B;AAGlC,IAAM,gCAAgC;AACtC,IAAM,8BAA8B;AAYpC,IAAM,2BAA2B;AAEjC,IAAM,iCAAiC;AAEvC,IAAM,yBAAyB;AAE/B,IAAM,+BAA+B;AAIrC,IAAM,mBAAmB;AAEzB,IAAM,6BAA6B;AAInC,IAAM,aAAa,KAAK,KAAK,KAAK;AAGlC,SAAS,eAAuB;AACrC,SAAO,KAAK,MAAM,KAAK,IAAI,IAAI,aAAa;AAC9C;AAIO,IAAM,0BAA0B,IAAI;AAIpC,IAAM,6BAA6B,CAAC,KAAK,KAAK,KAAK,KAAK,IAAI;AAI5D,IAAM,+BAA+B;AAKrC,IAAM,0BAA0B;AAEhC,IAAM,uBAAuB;AAe7B,IAAM,yBAAyB;AAE/B,IAAM,2BAA2B;AAEjC,IAAM,yBAAyB;AAE/B,IAAM,sBAAsB;AAG5B,IAAM,2BAA2B;AAEjC,IAAM,gCAAgC;AAYtC,IAAM,gCAAgC;AAItC,IAAM,4BAA4B;AAElC,IAAM,4BAA4B;AAGlC,IAAM,2BAA2B;AAIjC,IAAM,0BAA0B,oBAAI,IAAI,CAAC,cAAc,UAAU,CAAC;AAIlE,IAAM,mBAAmB;AAEzB,IAAM,gBAAgB;AAEtB,IAAM,kBAAkB;AAIxB,IAAM,2BAA2B;AAEjC,IAAM,6BAA6B;AAMnC,IAAM,qBAAqB;AAI3B,IAAM,eAAe,CAAC,MAAM,KAAM,GAAK;AA6CvC,IAAM,+BAA+B;AAErC,IAAM,8BAA8B;AAmDpC,IAAM,iBAAiB;AAGvB,IAAM,mBAAmB;AAGzB,IAAM,kBAAkB;AAGxB,IAAM,oBAAoB;AAG1B,IAAM,uBAAuB;AAe7B,IAAM,0BAA0B,IAAI,KAAK;AAEzC,IAAM,2BAA2B,KAAK,KAAK;AAE3C,IAAM,gCAAgC,KAAK,KAAK;AAEhD,IAAM,2BAA2B,KAAK;AAEtC,IAAM,0BAA0B,IAAI,KAAK;AAIzC,IAAM,6BAA6B,KAAK,KAAK;AAE7C,IAAM,2BAA2B;AAOjC,IAAM,mCAAmC;AAGzC,IAAM,iCAAiC;AAGvC,IAAM,iCAAiC;AAIvC,IAAM,wBAAwB;AAI9B,IAAM,qBAAqB;AAE3B,IAAM,qBAAqB;AAE3B,IAAM,yBAAyB;AAE/B,IAAM,yBAAyB;AAE/B,IAAM,sBAAsB;AAE5B,IAAM,8BAA8B;","names":[]}
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/hooks/send-event.ts"],"sourcesContent":["/**\n * Shared hook helper — sends an event to the daemon, buffers on failure.\n *\n * Every hook follows the same pattern: read stdin, POST to daemon /events,\n * buffer to disk if the daemon is unreachable. This helper extracts that\n * skeleton so each hook is a one-liner mapping input fields to event fields.\n */\n\nimport { DaemonClient } from './client.js';\nimport { readStdin } from './read-stdin.js';\nimport { EventBuffer } from '../capture/buffer.js';\nimport { resolveVaultDir } from '../vault/resolve.js';\nimport fs from 'node:fs';\nimport path from 'node:path';\n\n/**\n * Read hook stdin, POST event to daemon, buffer on failure.\n *\n * @param hookName — used for error logging (e.g., 'subagent-start')\n * @param buildEvent — maps the raw hook input to the event payload.\n * Receives the parsed stdin JSON and the resolved session ID.\n * Return the full event object (must include `type`).\n */\nexport async function sendEvent(\n hookName: string,\n buildEvent: (input: Record<string, unknown>, sessionId: string) => Record<string, unknown>,\n): Promise<void> {\n const VAULT_DIR = resolveVaultDir();\n if (!fs.existsSync(path.join(VAULT_DIR, 'myco.yaml'))) return;\n\n try {\n const input = JSON.parse(await readStdin()) as Record<string, unknown>;\n const sessionId = (input.session_id as string) ?? process.env.MYCO_SESSION_ID ?? `s-${Date.now()}`;\n\n const event = buildEvent(input, sessionId);\n\n const client = new DaemonClient(VAULT_DIR);\n const result = await client.post('/events', { ...event, session_id: sessionId });\n\n if (!result.ok) {\n const buffer = new EventBuffer(path.join(VAULT_DIR, 'buffer'), sessionId);\n // Strip session_id from buffer entry — it's in the filename\n const { session_id: _, ...bufferPayload } = event;\n buffer.append(bufferPayload);\n }\n } catch (error) {\n process.stderr.write(`[myco] ${hookName} error: ${(error as Error).message}\\n`);\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;AAYA,OAAO,QAAQ;AACf,OAAO,UAAU;AAUjB,eAAsB,UACpB,UACA,YACe;AACf,QAAM,YAAY,gBAAgB;AAClC,MAAI,CAAC,GAAG,WAAW,KAAK,KAAK,WAAW,WAAW,CAAC,EAAG;AAEvD,MAAI;AACF,UAAM,QAAQ,KAAK,MAAM,MAAM,UAAU,CAAC;AAC1C,UAAM,YAAa,MAAM,cAAyB,QAAQ,IAAI,mBAAmB,KAAK,KAAK,IAAI,CAAC;AAEhG,UAAM,QAAQ,WAAW,OAAO,SAAS;AAEzC,UAAM,SAAS,IAAI,aAAa,SAAS;AACzC,UAAM,SAAS,MAAM,OAAO,KAAK,WAAW,EAAE,GAAG,OAAO,YAAY,UAAU,CAAC;AAE/E,QAAI,CAAC,OAAO,IAAI;AACd,YAAM,SAAS,IAAI,YAAY,KAAK,KAAK,WAAW,QAAQ,GAAG,SAAS;AAExE,YAAM,EAAE,YAAY,GAAG,GAAG,cAAc,IAAI;AAC5C,aAAO,OAAO,aAAa;AAAA,IAC7B;AAAA,EACF,SAAS,OAAO;AACd,YAAQ,OAAO,MAAM,UAAU,QAAQ,WAAY,MAAgB,OAAO;AAAA,CAAI;AAAA,EAChF;AACF;","names":[]}
@@ -1,21 +0,0 @@
1
- import { createRequire as __cr } from 'node:module'; const require = __cr(import.meta.url);
2
- import {
3
- STDIN_TIMEOUT_MS
4
- } from "./chunk-76ZO5RGT.js";
5
-
6
- // src/hooks/read-stdin.ts
7
- function readStdin() {
8
- return new Promise((resolve) => {
9
- let data = "";
10
- process.stdin.on("data", (chunk) => {
11
- data += chunk;
12
- });
13
- process.stdin.on("end", () => resolve(data));
14
- setTimeout(() => resolve(data || "{}"), STDIN_TIMEOUT_MS);
15
- });
16
- }
17
-
18
- export {
19
- readStdin
20
- };
21
- //# sourceMappingURL=chunk-J4RVYUH4.js.map
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/hooks/read-stdin.ts"],"sourcesContent":["import { STDIN_TIMEOUT_MS } from '../constants.js';\n\nexport function readStdin(): Promise<string> {\n return new Promise((resolve) => {\n let data = '';\n process.stdin.on('data', (chunk: Buffer) => { data += chunk; });\n process.stdin.on('end', () => resolve(data));\n setTimeout(() => resolve(data || '{}'), STDIN_TIMEOUT_MS);\n });\n}\n"],"mappings":";;;;;;AAEO,SAAS,YAA6B;AAC3C,SAAO,IAAI,QAAQ,CAAC,YAAY;AAC9B,QAAI,OAAO;AACX,YAAQ,MAAM,GAAG,QAAQ,CAAC,UAAkB;AAAE,cAAQ;AAAA,IAAO,CAAC;AAC9D,YAAQ,MAAM,GAAG,OAAO,MAAM,QAAQ,IAAI,CAAC;AAC3C,eAAW,MAAM,QAAQ,QAAQ,IAAI,GAAG,gBAAgB;AAAA,EAC1D,CAAC;AACH;","names":[]}
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/db/queries/search.ts"],"sourcesContent":["/**\n * Full-text search using SQLite FTS5.\n *\n * Searches prompt_batches and activities via their FTS5 virtual tables.\n * Semantic search (vector similarity) is handled by the external VectorStore —\n * this module covers text-based retrieval only.\n *\n * All queries use parameterized placeholders throughout.\n */\n\nimport { getDatabase } from '@myco/db/client.js';\nimport {\n SEARCH_RESULTS_DEFAULT_LIMIT,\n SEARCH_PREVIEW_CHARS,\n} from '@myco/constants.js';\nimport type { VectorSearchResult } from '@myco/daemon/embedding/types.js';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\n/** All result types that can appear in search results. */\nexport type SearchResultType =\n | 'session'\n | 'spore'\n | 'plan'\n | 'artifact'\n | 'prompt_batch'\n | 'activity';\n\n/** A single result returned from full-text or semantic search. */\nexport interface SearchResult {\n id: string;\n type: SearchResultType;\n title: string;\n preview: string;\n score: number;\n session_id?: string;\n}\n\n/** Options for fullTextSearch. */\nexport interface SearchOptions {\n /** Restrict results to a single type. */\n type?: string;\n /** Maximum number of results to return (default: SEARCH_RESULTS_DEFAULT_LIMIT). */\n limit?: number;\n}\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Full-text search across capture tables using SQLite FTS5.\n *\n * Searches prompt_batches (indexed on user_prompt) and activities (indexed\n * on tool_name, tool_input, file_path). The raw query string is passed\n * directly to FTS5 MATCH — callers should sanitize if needed.\n *\n * FTS5 `rank` values are negative (lower = better match). This function\n * converts them to positive scores via `Math.abs()` so higher = better\n * in the returned results.\n *\n * When `options.type` is specified, only the matching table branch is queried.\n *\n * @param query — search string (FTS5 MATCH syntax)\n * @param options — optional type filter and result limit\n * @returns SearchResult[] ordered by score DESC\n */\nexport function fullTextSearch(\n query: string,\n options: SearchOptions = {},\n): SearchResult[] {\n const db = getDatabase();\n const limit = options.limit ?? SEARCH_RESULTS_DEFAULT_LIMIT;\n const typeFilter = options.type;\n\n const results: SearchResult[] = [];\n\n // -- prompt_batches branch ------------------------------------------------\n if (typeFilter === undefined || typeFilter === 'prompt_batch') {\n const batchRows = db.prepare(\n `SELECT pb.id, pb.prompt_number, pb.session_id,\n substr(COALESCE(pb.user_prompt, ''), 1, ?) AS preview,\n fts.rank\n FROM prompt_batches_fts fts\n JOIN prompt_batches pb ON pb.id = fts.rowid\n WHERE prompt_batches_fts MATCH ?\n ORDER BY fts.rank\n LIMIT ?`\n ).all(SEARCH_PREVIEW_CHARS, query, limit) as Array<{\n id: number;\n prompt_number: number | null;\n session_id: string | null;\n preview: string;\n rank: number;\n }>;\n\n for (const row of batchRows) {\n results.push({\n id: String(row.id),\n type: 'prompt_batch',\n title: row.prompt_number != null\n ? `Batch #${row.prompt_number}`\n : `Batch ${row.id}`,\n preview: row.preview,\n score: Math.abs(row.rank),\n ...(row.session_id != null ? { session_id: row.session_id } : {}),\n });\n }\n }\n\n // -- activities branch ----------------------------------------------------\n if (typeFilter === undefined || typeFilter === 'activity') {\n const activityRows = db.prepare(\n `SELECT a.id, a.tool_name, a.tool_input, a.file_path, a.session_id,\n fts.rank\n FROM activities_fts fts\n JOIN activities a ON a.id = fts.rowid\n WHERE activities_fts MATCH ?\n ORDER BY fts.rank\n LIMIT ?`\n ).all(query, limit) as Array<{\n id: number;\n tool_name: string;\n tool_input: string | null;\n file_path: string | null;\n session_id: string | null;\n rank: number;\n }>;\n\n for (const row of activityRows) {\n const preview = (row.tool_input ?? row.file_path ?? '').slice(0, SEARCH_PREVIEW_CHARS);\n results.push({\n id: String(row.id),\n type: 'activity',\n title: row.tool_name,\n preview,\n score: Math.abs(row.rank),\n ...(row.session_id != null ? { session_id: row.session_id } : {}),\n });\n }\n }\n\n // Sort combined results by score DESC and apply limit.\n results.sort((a, b) => b.score - a.score);\n return results.slice(0, limit);\n}\n\n// ---------------------------------------------------------------------------\n// Hydration — convert VectorSearchResults into SearchResults\n// ---------------------------------------------------------------------------\n\n/** Row shape returned from sessions table for hydration. */\ninterface SessionRow {\n id: string;\n title: string | null;\n summary: string | null;\n session_id?: undefined;\n}\n\n/** Row shape returned from spores table for hydration. */\ninterface SporeRow {\n id: string;\n observation_type: string;\n content: string;\n session_id: string | null;\n}\n\n/** Row shape returned from plans table for hydration. */\ninterface PlanRow {\n id: string;\n title: string | null;\n content: string | null;\n}\n\n/** Row shape returned from artifacts table for hydration. */\ninterface ArtifactRow {\n id: string;\n title: string;\n content: string | null;\n}\n\n/**\n * Hydrate vector search results into SearchResults by fetching full records\n * from the record store.\n *\n * Groups results by namespace, queries each table for the relevant IDs, then\n * maps them into SearchResult format with titles and previews.\n */\nexport function hydrateSearchResults(\n vectorResults: VectorSearchResult[],\n): SearchResult[] {\n if (vectorResults.length === 0) return [];\n\n const db = getDatabase();\n const results: SearchResult[] = [];\n\n // Group result IDs by namespace\n const byNamespace = new Map<string, VectorSearchResult[]>();\n for (const vr of vectorResults) {\n const group = byNamespace.get(vr.namespace) ?? [];\n group.push(vr);\n byNamespace.set(vr.namespace, group);\n }\n\n // Use json_each so the statement text is stable and SQLite can cache the plan.\n const sessionStmt = db.prepare(\n `SELECT id, title, summary FROM sessions WHERE id IN (SELECT value FROM json_each(?))`,\n );\n const sporeStmt = db.prepare(\n `SELECT id, observation_type, content, session_id FROM spores WHERE id IN (SELECT value FROM json_each(?))`,\n );\n const planStmt = db.prepare(\n `SELECT id, title, content FROM plans WHERE id IN (SELECT value FROM json_each(?))`,\n );\n const artifactStmt = db.prepare(\n `SELECT id, title, content FROM artifacts WHERE id IN (SELECT value FROM json_each(?))`,\n );\n\n // --- sessions ---\n const sessionResults = byNamespace.get('sessions');\n if (sessionResults && sessionResults.length > 0) {\n const ids = sessionResults.map((r) => r.id);\n const rows = sessionStmt.all(JSON.stringify(ids)) as SessionRow[];\n\n const rowMap = new Map(rows.map((r) => [r.id, r]));\n for (const vr of sessionResults) {\n const row = rowMap.get(vr.id);\n if (!row) continue;\n results.push({\n id: row.id,\n type: 'session',\n title: row.title ?? `Session ${row.id.slice(-6)}`,\n preview: (row.summary ?? '').slice(0, SEARCH_PREVIEW_CHARS),\n score: vr.similarity,\n });\n }\n }\n\n // --- spores ---\n const sporeResults = byNamespace.get('spores');\n if (sporeResults && sporeResults.length > 0) {\n const ids = sporeResults.map((r) => r.id);\n const rows = sporeStmt.all(JSON.stringify(ids)) as SporeRow[];\n\n const rowMap = new Map(rows.map((r) => [r.id, r]));\n for (const vr of sporeResults) {\n const row = rowMap.get(vr.id);\n if (!row) continue;\n results.push({\n id: row.id,\n type: 'spore',\n title: row.observation_type,\n preview: row.content.slice(0, SEARCH_PREVIEW_CHARS),\n score: vr.similarity,\n ...(row.session_id != null ? { session_id: row.session_id } : {}),\n });\n }\n }\n\n // --- plans ---\n const planResults = byNamespace.get('plans');\n if (planResults && planResults.length > 0) {\n const ids = planResults.map((r) => r.id);\n const rows = planStmt.all(JSON.stringify(ids)) as PlanRow[];\n\n const rowMap = new Map(rows.map((r) => [r.id, r]));\n for (const vr of planResults) {\n const row = rowMap.get(vr.id);\n if (!row) continue;\n results.push({\n id: row.id,\n type: 'plan',\n title: row.title ?? `Plan ${row.id.slice(-6)}`,\n preview: (row.content ?? '').slice(0, SEARCH_PREVIEW_CHARS),\n score: vr.similarity,\n });\n }\n }\n\n // --- artifacts ---\n const artifactResults = byNamespace.get('artifacts');\n if (artifactResults && artifactResults.length > 0) {\n const ids = artifactResults.map((r) => r.id);\n const rows = artifactStmt.all(JSON.stringify(ids)) as ArtifactRow[];\n\n const rowMap = new Map(rows.map((r) => [r.id, r]));\n for (const vr of artifactResults) {\n const row = rowMap.get(vr.id);\n if (!row) continue;\n results.push({\n id: row.id,\n type: 'artifact',\n title: row.title,\n preview: (row.content ?? '').slice(0, SEARCH_PREVIEW_CHARS),\n score: vr.similarity,\n });\n }\n }\n\n // Preserve the original similarity-based ordering from vector search\n results.sort((a, b) => b.score - a.score);\n return results;\n}\n"],"mappings":"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","names":[]}