@goondocks/myco 0.19.5 → 0.20.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 (188) hide show
  1. package/dist/{agent-run-3IQXE5PI.js → agent-run-4HUXVRHW.js} +8 -8
  2. package/dist/{agent-tasks-5DIA3CE5.js → agent-tasks-JF45ELB6.js} +8 -8
  3. package/dist/{chunk-DURKJTVO.js → chunk-3WOS4TAR.js} +9 -1
  4. package/dist/chunk-3WOS4TAR.js.map +1 -0
  5. package/dist/{chunk-27ZDDWIA.js → chunk-4LCIKVDM.js} +49 -21
  6. package/dist/chunk-4LCIKVDM.js.map +1 -0
  7. package/dist/{chunk-Q4QD6LJT.js → chunk-4M7EWPIA.js} +3 -3
  8. package/dist/{chunk-FGKCE5AE.js → chunk-4YFKBL3F.js} +2 -2
  9. package/dist/{chunk-KYH4V4ML.js → chunk-57O67XVF.js} +3 -3
  10. package/dist/{chunk-7ONVLO43.js → chunk-5XIVBO25.js} +2 -2
  11. package/dist/{chunk-QLCD77AN.js → chunk-6RFZWV4R.js} +18 -1
  12. package/dist/chunk-6RFZWV4R.js.map +1 -0
  13. package/dist/{chunk-VH7XYQFL.js → chunk-ACQ2AIEM.js} +2 -2
  14. package/dist/{chunk-6ZDJXSEO.js → chunk-BPRIYNLE.js} +3 -3
  15. package/dist/chunk-CUDIZJY7.js +36 -0
  16. package/dist/chunk-CUDIZJY7.js.map +1 -0
  17. package/dist/{chunk-WKNAKQKA.js → chunk-DCSGJ7W4.js} +13 -19
  18. package/dist/chunk-DCSGJ7W4.js.map +1 -0
  19. package/dist/{chunk-Q6OEZM3S.js → chunk-EVDQKYCG.js} +237 -10
  20. package/dist/chunk-EVDQKYCG.js.map +1 -0
  21. package/dist/{chunk-I54KLC6H.js → chunk-FLLBJLHM.js} +3 -1
  22. package/dist/{chunk-I54KLC6H.js.map → chunk-FLLBJLHM.js.map} +1 -1
  23. package/dist/{chunk-PMT2LSTQ.js → chunk-FMRZ26U5.js} +2 -2
  24. package/dist/{chunk-3J6TUJSV.js → chunk-KHT24OWC.js} +3 -3
  25. package/dist/{chunk-5OXBT5MD.js → chunk-L6XFAJIF.js} +65 -14
  26. package/dist/chunk-L6XFAJIF.js.map +1 -0
  27. package/dist/{chunk-6DDRJQ4X.js → chunk-MYOZLMB2.js} +2 -2
  28. package/dist/{chunk-UVKQ62II.js → chunk-NGROSFOH.js} +24 -2
  29. package/dist/chunk-NGROSFOH.js.map +1 -0
  30. package/dist/{chunk-K2QX43GC.js → chunk-P3DN5EWW.js} +4 -4
  31. package/dist/{chunk-IQ5LQTV7.js → chunk-POR75WM6.js} +4 -4
  32. package/dist/{chunk-KABTXALI.js → chunk-QS5TWZBL.js} +4 -4
  33. package/dist/{chunk-UTSCRMJE.js → chunk-SRXTSI25.js} +110 -4
  34. package/dist/chunk-SRXTSI25.js.map +1 -0
  35. package/dist/{chunk-2QJCV3UL.js → chunk-UOQQENDW.js} +3 -3
  36. package/dist/{chunk-GFR542SM.js → chunk-US4LNCAT.js} +5 -11
  37. package/dist/chunk-US4LNCAT.js.map +1 -0
  38. package/dist/{chunk-44PZCAYS.js → chunk-XL75KZGI.js} +23 -13
  39. package/dist/chunk-XL75KZGI.js.map +1 -0
  40. package/dist/{chunk-5WPTS6A4.js → chunk-YSNIAJ5D.js} +7 -4
  41. package/dist/chunk-YSNIAJ5D.js.map +1 -0
  42. package/dist/chunk-ZXZPJJN3.js +54 -0
  43. package/dist/chunk-ZXZPJJN3.js.map +1 -0
  44. package/dist/{cli-RTUSGLTM.js → cli-AHTINAHY.js} +43 -43
  45. package/dist/{client-YWE5YJB7.js → client-LHENCAV3.js} +4 -4
  46. package/dist/{config-I5MJ6RXI.js → config-XPV5GDE4.js} +8 -16
  47. package/dist/config-XPV5GDE4.js.map +1 -0
  48. package/dist/{detect-BEOIHGBC.js → detect-PXNM6TA7.js} +2 -2
  49. package/dist/{detect-providers-2EY55EHK.js → detect-providers-5KOPZ7J2.js} +4 -4
  50. package/dist/{doctor-FIG7VEYV.js → doctor-XPCF5HV5.js} +13 -13
  51. package/dist/{executor-2TMGOVEA.js → executor-ACDHGTRH.js} +115 -77
  52. package/dist/executor-ACDHGTRH.js.map +1 -0
  53. package/dist/{init-3536BYDC.js → init-V3KCC36O.js} +14 -14
  54. package/dist/{installer-YH3WQISI.js → installer-ZNK4JSQA.js} +4 -4
  55. package/dist/{llm-SWDDQQWY.js → llm-TH4NLIRM.js} +4 -4
  56. package/dist/{loader-K4WF4EEJ.js → loader-H7OFASVC.js} +15 -3
  57. package/dist/{loader-AAZ6VUIA.js → loader-TSB5M7FD.js} +3 -3
  58. package/dist/{logs-KNKPQE5A.js → logs-7YVGGBIS.js} +2 -2
  59. package/dist/{main-R5ZD5OIZ.js → main-5S4MDCIO.js} +770 -176
  60. package/dist/main-5S4MDCIO.js.map +1 -0
  61. package/dist/{open-5UD5JQIM.js → open-AB5ULZIB.js} +8 -8
  62. package/dist/{post-compact-ZJFE66O3.js → post-compact-P2B7C7FE.js} +9 -8
  63. package/dist/{post-compact-ZJFE66O3.js.map → post-compact-P2B7C7FE.js.map} +1 -1
  64. package/dist/{post-tool-use-CAR2USJP.js → post-tool-use-LXL6NXDS.js} +8 -7
  65. package/dist/{post-tool-use-CAR2USJP.js.map → post-tool-use-LXL6NXDS.js.map} +1 -1
  66. package/dist/{post-tool-use-failure-OMIKVEVR.js → post-tool-use-failure-WAYVVKGR.js} +9 -8
  67. package/dist/{post-tool-use-failure-OMIKVEVR.js.map → post-tool-use-failure-WAYVVKGR.js.map} +1 -1
  68. package/dist/{pre-compact-6SXYI5CD.js → pre-compact-BCXUCF4V.js} +9 -8
  69. package/dist/{pre-compact-6SXYI5CD.js.map → pre-compact-BCXUCF4V.js.map} +1 -1
  70. package/dist/{provider-check-WCM3SDTM.js → provider-check-43LAMSMH.js} +4 -4
  71. package/dist/{registry-OCM4WAPJ.js → registry-MGJSJBAS.js} +4 -4
  72. package/dist/{remove-NJSFVZXW.js → remove-KAPX5NT2.js} +10 -10
  73. package/dist/{restart-U5ZGJON7.js → restart-HQO36FTG.js} +9 -9
  74. package/dist/{search-HO7CXV6H.js → search-YOMOKAAI.js} +9 -9
  75. package/dist/{server-BUSZIUZV.js → server-2N23P6F2.js} +40 -27
  76. package/dist/{server-BUSZIUZV.js.map → server-2N23P6F2.js.map} +1 -1
  77. package/dist/{session-RVT2QELH.js → session-WW2JLHPX.js} +9 -10
  78. package/dist/{session-RVT2QELH.js.map → session-WW2JLHPX.js.map} +1 -1
  79. package/dist/{session-end-4W6SZVGH.js → session-end-4WRTIBVQ.js} +8 -7
  80. package/dist/{session-end-4W6SZVGH.js.map → session-end-4WRTIBVQ.js.map} +1 -1
  81. package/dist/{session-start-PMPKAST4.js → session-start-HRWTZXQR.js} +15 -15
  82. package/dist/session-start-HRWTZXQR.js.map +1 -0
  83. package/dist/{setup-llm-6UAJUHQE.js → setup-llm-HFWSBUAF.js} +10 -9
  84. package/dist/{setup-llm-6UAJUHQE.js.map → setup-llm-HFWSBUAF.js.map} +1 -1
  85. package/dist/src/agent/definitions/tasks/full-intelligence.yaml +37 -8
  86. package/dist/src/agent/prompts/agent.md +2 -2
  87. package/dist/src/cli.js +1 -1
  88. package/dist/src/daemon/main.js +1 -1
  89. package/dist/src/hooks/post-tool-use.js +1 -1
  90. package/dist/src/hooks/session-end.js +1 -1
  91. package/dist/src/hooks/session-start.js +1 -1
  92. package/dist/src/hooks/stop.js +1 -1
  93. package/dist/src/hooks/user-prompt-submit.js +1 -1
  94. package/dist/src/mcp/server.js +1 -1
  95. package/dist/src/symbionts/manifests/codex.yaml +28 -0
  96. package/dist/{stats-W47FF6RD.js → stats-7A4CJ4MS.js} +9 -9
  97. package/dist/{stop-6TAO2UU2.js → stop-R2GDHMRA.js} +8 -7
  98. package/dist/{stop-6TAO2UU2.js.map → stop-R2GDHMRA.js.map} +1 -1
  99. package/dist/{stop-failure-R76SULCV.js → stop-failure-773KR4VZ.js} +9 -8
  100. package/dist/{stop-failure-R76SULCV.js.map → stop-failure-773KR4VZ.js.map} +1 -1
  101. package/dist/{subagent-start-TJMUZLP2.js → subagent-start-IDECNBHW.js} +9 -8
  102. package/dist/{subagent-start-TJMUZLP2.js.map → subagent-start-IDECNBHW.js.map} +1 -1
  103. package/dist/{subagent-stop-M3DAFJWQ.js → subagent-stop-3JH7DR2S.js} +9 -8
  104. package/dist/{subagent-stop-M3DAFJWQ.js.map → subagent-stop-3JH7DR2S.js.map} +1 -1
  105. package/dist/{task-completed-2KVR5JV6.js → task-completed-AYVHPHDR.js} +9 -8
  106. package/dist/{task-completed-2KVR5JV6.js.map → task-completed-AYVHPHDR.js.map} +1 -1
  107. package/dist/{team-2IAT6MKD.js → team-3JKF7VAD.js} +5 -5
  108. package/dist/{turns-3ZQAF6HF.js → turns-YFNI5CQC.js} +6 -4
  109. package/dist/ui/assets/index-C2JuNtRB.css +1 -0
  110. package/dist/ui/assets/index-JLVaQKV2.js +832 -0
  111. package/dist/ui/favicon-dusk.svg +11 -0
  112. package/dist/ui/favicon-moss.svg +11 -0
  113. package/dist/ui/favicon-plum.svg +11 -0
  114. package/dist/ui/favicon-sage.svg +11 -0
  115. package/dist/ui/favicon-slate.svg +11 -0
  116. package/dist/ui/favicon-terracotta.svg +11 -0
  117. package/dist/ui/index.html +3 -3
  118. package/dist/{update-TB34JEB7.js → update-YWYW55JM.js} +10 -10
  119. package/dist/{user-prompt-submit-O4TP7NJ6.js → user-prompt-submit-YELSR6XI.js} +9 -8
  120. package/dist/{user-prompt-submit-O4TP7NJ6.js.map → user-prompt-submit-YELSR6XI.js.map} +1 -1
  121. package/dist/{verify-SESZXGVY.js → verify-JS44DVKJ.js} +5 -5
  122. package/dist/{version-QBORV23E.js → version-K5NETYIL.js} +2 -2
  123. package/package.json +1 -1
  124. package/skills/myco/SKILL.md +78 -43
  125. package/skills/myco/references/vault-status.md +1 -1
  126. package/dist/chunk-27ZDDWIA.js.map +0 -1
  127. package/dist/chunk-44PZCAYS.js.map +0 -1
  128. package/dist/chunk-5OXBT5MD.js.map +0 -1
  129. package/dist/chunk-5WPTS6A4.js.map +0 -1
  130. package/dist/chunk-5ZT2Q6P5.js +0 -25
  131. package/dist/chunk-5ZT2Q6P5.js.map +0 -1
  132. package/dist/chunk-AULBWINA.js +0 -227
  133. package/dist/chunk-AULBWINA.js.map +0 -1
  134. package/dist/chunk-DURKJTVO.js.map +0 -1
  135. package/dist/chunk-GFR542SM.js.map +0 -1
  136. package/dist/chunk-Q6OEZM3S.js.map +0 -1
  137. package/dist/chunk-QLCD77AN.js.map +0 -1
  138. package/dist/chunk-UTSCRMJE.js.map +0 -1
  139. package/dist/chunk-UVKQ62II.js.map +0 -1
  140. package/dist/chunk-VQF5E4ZX.js +0 -91
  141. package/dist/chunk-VQF5E4ZX.js.map +0 -1
  142. package/dist/chunk-WKNAKQKA.js.map +0 -1
  143. package/dist/config-I5MJ6RXI.js.map +0 -1
  144. package/dist/executor-2TMGOVEA.js.map +0 -1
  145. package/dist/main-R5ZD5OIZ.js.map +0 -1
  146. package/dist/resolution-events-PYLSI6QT.js +0 -15
  147. package/dist/session-start-PMPKAST4.js.map +0 -1
  148. package/dist/ui/assets/index-C-6W8e3m.js +0 -842
  149. package/dist/ui/assets/index-CRmkSi63.css +0 -1
  150. package/dist/version-QBORV23E.js.map +0 -1
  151. /package/dist/{agent-run-3IQXE5PI.js.map → agent-run-4HUXVRHW.js.map} +0 -0
  152. /package/dist/{agent-tasks-5DIA3CE5.js.map → agent-tasks-JF45ELB6.js.map} +0 -0
  153. /package/dist/{chunk-Q4QD6LJT.js.map → chunk-4M7EWPIA.js.map} +0 -0
  154. /package/dist/{chunk-FGKCE5AE.js.map → chunk-4YFKBL3F.js.map} +0 -0
  155. /package/dist/{chunk-KYH4V4ML.js.map → chunk-57O67XVF.js.map} +0 -0
  156. /package/dist/{chunk-7ONVLO43.js.map → chunk-5XIVBO25.js.map} +0 -0
  157. /package/dist/{chunk-VH7XYQFL.js.map → chunk-ACQ2AIEM.js.map} +0 -0
  158. /package/dist/{chunk-6ZDJXSEO.js.map → chunk-BPRIYNLE.js.map} +0 -0
  159. /package/dist/{chunk-PMT2LSTQ.js.map → chunk-FMRZ26U5.js.map} +0 -0
  160. /package/dist/{chunk-3J6TUJSV.js.map → chunk-KHT24OWC.js.map} +0 -0
  161. /package/dist/{chunk-6DDRJQ4X.js.map → chunk-MYOZLMB2.js.map} +0 -0
  162. /package/dist/{chunk-K2QX43GC.js.map → chunk-P3DN5EWW.js.map} +0 -0
  163. /package/dist/{chunk-IQ5LQTV7.js.map → chunk-POR75WM6.js.map} +0 -0
  164. /package/dist/{chunk-KABTXALI.js.map → chunk-QS5TWZBL.js.map} +0 -0
  165. /package/dist/{chunk-2QJCV3UL.js.map → chunk-UOQQENDW.js.map} +0 -0
  166. /package/dist/{cli-RTUSGLTM.js.map → cli-AHTINAHY.js.map} +0 -0
  167. /package/dist/{client-YWE5YJB7.js.map → client-LHENCAV3.js.map} +0 -0
  168. /package/dist/{detect-BEOIHGBC.js.map → detect-PXNM6TA7.js.map} +0 -0
  169. /package/dist/{detect-providers-2EY55EHK.js.map → detect-providers-5KOPZ7J2.js.map} +0 -0
  170. /package/dist/{doctor-FIG7VEYV.js.map → doctor-XPCF5HV5.js.map} +0 -0
  171. /package/dist/{init-3536BYDC.js.map → init-V3KCC36O.js.map} +0 -0
  172. /package/dist/{installer-YH3WQISI.js.map → installer-ZNK4JSQA.js.map} +0 -0
  173. /package/dist/{llm-SWDDQQWY.js.map → llm-TH4NLIRM.js.map} +0 -0
  174. /package/dist/{loader-AAZ6VUIA.js.map → loader-H7OFASVC.js.map} +0 -0
  175. /package/dist/{loader-K4WF4EEJ.js.map → loader-TSB5M7FD.js.map} +0 -0
  176. /package/dist/{logs-KNKPQE5A.js.map → logs-7YVGGBIS.js.map} +0 -0
  177. /package/dist/{open-5UD5JQIM.js.map → open-AB5ULZIB.js.map} +0 -0
  178. /package/dist/{provider-check-WCM3SDTM.js.map → provider-check-43LAMSMH.js.map} +0 -0
  179. /package/dist/{registry-OCM4WAPJ.js.map → registry-MGJSJBAS.js.map} +0 -0
  180. /package/dist/{remove-NJSFVZXW.js.map → remove-KAPX5NT2.js.map} +0 -0
  181. /package/dist/{restart-U5ZGJON7.js.map → restart-HQO36FTG.js.map} +0 -0
  182. /package/dist/{search-HO7CXV6H.js.map → search-YOMOKAAI.js.map} +0 -0
  183. /package/dist/{stats-W47FF6RD.js.map → stats-7A4CJ4MS.js.map} +0 -0
  184. /package/dist/{resolution-events-PYLSI6QT.js.map → team-3JKF7VAD.js.map} +0 -0
  185. /package/dist/{team-2IAT6MKD.js.map → turns-YFNI5CQC.js.map} +0 -0
  186. /package/dist/{update-TB34JEB7.js.map → update-YWYW55JM.js.map} +0 -0
  187. /package/dist/{verify-SESZXGVY.js.map → verify-JS44DVKJ.js.map} +0 -0
  188. /package/dist/{turns-3ZQAF6HF.js.map → version-K5NETYIL.js.map} +0 -0
@@ -2,10 +2,10 @@ import { createRequire as __cr } from 'node:module'; const require = __cr(import
2
2
  import {
3
3
  DaemonLogger,
4
4
  LEVEL_ORDER
5
- } from "./chunk-DURKJTVO.js";
5
+ } from "./chunk-3WOS4TAR.js";
6
6
  import {
7
7
  withTaskConfig
8
- } from "./chunk-GFR542SM.js";
8
+ } from "./chunk-US4LNCAT.js";
9
9
  import {
10
10
  EMBEDDABLE_TABLES,
11
11
  EMBEDDABLE_TEXT_COLUMNS,
@@ -15,7 +15,7 @@ import {
15
15
  getEmbeddingQueueDepth,
16
16
  getUnembedded,
17
17
  markEmbedded
18
- } from "./chunk-K2QX43GC.js";
18
+ } from "./chunk-P3DN5EWW.js";
19
19
  import {
20
20
  getTeamPackageVersion,
21
21
  loadSecrets,
@@ -23,7 +23,7 @@ import {
23
23
  readSecrets,
24
24
  resolveVaultConfigPath,
25
25
  writeSecret
26
- } from "./chunk-KABTXALI.js";
26
+ } from "./chunk-QS5TWZBL.js";
27
27
  import {
28
28
  buildTaskInstruction,
29
29
  closeOpenBatches,
@@ -53,6 +53,7 @@ import {
53
53
  incrementActivityCount,
54
54
  incrementSkillUsageCount,
55
55
  insertBatchStateless,
56
+ insertResolutionEvent,
56
57
  isInstructionRequiredTask,
57
58
  listBatchesBySession,
58
59
  listCandidatesWithCount,
@@ -71,27 +72,27 @@ import {
71
72
  setResponseSummary,
72
73
  updateCandidate,
73
74
  updateNotificationStatus
74
- } from "./chunk-5OXBT5MD.js";
75
+ } from "./chunk-L6XFAJIF.js";
75
76
  import {
76
77
  fullTextSearch,
77
78
  hydrateSearchResults
78
- } from "./chunk-7ONVLO43.js";
79
+ } from "./chunk-5XIVBO25.js";
79
80
  import {
80
81
  copyTaskToUser,
81
82
  deleteUserTask,
82
83
  loadAllTasks,
83
84
  validateTaskName,
84
85
  writeUserTask
85
- } from "./chunk-KYH4V4ML.js";
86
+ } from "./chunk-57O67XVF.js";
86
87
  import {
87
88
  AgentTaskSchema,
88
89
  registerAgent,
89
90
  resolveDefinitionsDir,
90
91
  taskFromParsed
91
- } from "./chunk-Q4QD6LJT.js";
92
+ } from "./chunk-4M7EWPIA.js";
92
93
  import {
93
94
  listTurnsByRun
94
- } from "./chunk-QLCD77AN.js";
95
+ } from "./chunk-6RFZWV4R.js";
95
96
  import {
96
97
  cleanupStagedSkill,
97
98
  listStaleStagingDirs
@@ -99,7 +100,7 @@ import {
99
100
  import {
100
101
  Anthropic,
101
102
  createEmbeddingProvider
102
- } from "./chunk-3J6TUJSV.js";
103
+ } from "./chunk-KHT24OWC.js";
103
104
  import {
104
105
  getMachineId
105
106
  } from "./chunk-ENWBFX7F.js";
@@ -109,84 +110,93 @@ import {
109
110
  listBufferSessionIds
110
111
  } from "./chunk-V7XG6V6C.js";
111
112
  import "./chunk-POEPHBQK.js";
112
- import "./chunk-5WPTS6A4.js";
113
+ import "./chunk-YSNIAJ5D.js";
113
114
  import "./chunk-SAKJMNSR.js";
114
115
  import {
115
116
  SymbiontInstaller
116
- } from "./chunk-27ZDDWIA.js";
117
+ } from "./chunk-4LCIKVDM.js";
117
118
  import {
118
119
  checkLocalProvider
119
- } from "./chunk-6ZDJXSEO.js";
120
+ } from "./chunk-BPRIYNLE.js";
120
121
  import {
121
122
  LmStudioBackend,
122
123
  OllamaBackend
123
- } from "./chunk-PMT2LSTQ.js";
124
+ } from "./chunk-FMRZ26U5.js";
124
125
  import {
125
126
  countSpores,
126
127
  getSpore,
127
128
  insertSpore,
128
129
  listSpores,
129
130
  updateSporeStatus
130
- } from "./chunk-FGKCE5AE.js";
131
+ } from "./chunk-4YFKBL3F.js";
131
132
  import {
133
+ backfillUnsynced,
132
134
  closeSession,
135
+ countDeadLettered,
136
+ countPending,
133
137
  countSessions,
134
138
  deleteSessionCascade,
139
+ enqueueOutbox,
135
140
  getSession,
136
141
  getSessionImpact,
137
- incrementSessionToolCount,
138
- listSessions,
139
- reactivateSessionIfCompleted,
140
- updateSession,
141
- upsertSession
142
- } from "./chunk-Q6OEZM3S.js";
143
- import {
144
- backfillUnsynced,
145
- countDeadLettered,
146
- countPending,
147
- enqueueOutbox,
148
142
  getTeamMachineId,
149
143
  incrementRetryCount,
144
+ incrementSessionToolCount,
150
145
  initTeamContext,
151
146
  isTeamSyncEnabled,
152
147
  listPending,
148
+ listSessions,
153
149
  markSent,
154
150
  markSourceRowsSynced,
155
151
  pruneOld,
152
+ reactivateSessionIfCompleted,
156
153
  retryDeadLettered,
157
- syncRow
158
- } from "./chunk-AULBWINA.js";
154
+ syncRow,
155
+ updateSession,
156
+ upsertSession
157
+ } from "./chunk-EVDQKYCG.js";
158
+ import {
159
+ evaluateSessionCaptureRules,
160
+ readTranscriptMeta
161
+ } from "./chunk-XL75KZGI.js";
159
162
  import {
160
163
  EMBEDDING_DIMENSIONS,
161
164
  REST_SETTABLE_STATUSES,
162
165
  SCHEMA_VERSION,
163
166
  createSchema
164
- } from "./chunk-6DDRJQ4X.js";
167
+ } from "./chunk-MYOZLMB2.js";
165
168
  import {
166
169
  CONFIG_FILENAME,
167
170
  MycoConfigSchema,
171
+ deepMergeConfig,
168
172
  getEnabledSymbiontNames,
169
173
  loadConfig,
174
+ loadLocalConfig,
175
+ loadMergedConfig,
170
176
  updateBackupConfig,
171
177
  updateConfig,
178
+ updateLocalConfig,
172
179
  updateTeamConfig
173
- } from "./chunk-UTSCRMJE.js";
180
+ } from "./chunk-SRXTSI25.js";
174
181
  import {
175
182
  closeDatabase,
176
183
  getDatabase,
177
184
  initDatabase,
178
185
  vaultDbPath
179
186
  } from "./chunk-MYX5NCRH.js";
187
+ import {
188
+ unsetAtPath
189
+ } from "./chunk-ZXZPJJN3.js";
180
190
  import {
181
191
  resolveCliEntryPath
182
- } from "./chunk-2QJCV3UL.js";
192
+ } from "./chunk-UOQQENDW.js";
183
193
  import {
184
194
  getPluginVersion
185
- } from "./chunk-VH7XYQFL.js";
195
+ } from "./chunk-ACQ2AIEM.js";
186
196
  import {
187
197
  loadManifests,
188
198
  resolvePackageRoot
189
- } from "./chunk-UVKQ62II.js";
199
+ } from "./chunk-NGROSFOH.js";
190
200
  import {
191
201
  findPackageRoot
192
202
  } from "./chunk-LPUQPDC2.js";
@@ -203,6 +213,7 @@ import {
203
213
  FEED_DEFAULT_LIMIT,
204
214
  LOG_MESSAGE_PREVIEW_CHARS,
205
215
  LOG_PROMPT_PREVIEW_CHARS,
216
+ MCP_SESSIONS_DEFAULT_LIMIT,
206
217
  MS_PER_DAY,
207
218
  MS_PER_HOUR,
208
219
  MS_PER_SECOND,
@@ -224,6 +235,7 @@ import {
224
235
  RESTART_RESPONSE_FLUSH_MS,
225
236
  SEARCH_RESULTS_DEFAULT_LIMIT,
226
237
  SEARCH_SIMILARITY_THRESHOLD,
238
+ SESSION_SUMMARY_PREVIEW_CHARS,
227
239
  STALE_BUFFER_MAX_AGE_MS,
228
240
  STALE_SESSION_THRESHOLD_MS,
229
241
  SYNC_PROTOCOL_VERSION,
@@ -243,7 +255,7 @@ import {
243
255
  USER_TASK_SOURCE,
244
256
  epochSeconds,
245
257
  estimateTokens
246
- } from "./chunk-I54KLC6H.js";
258
+ } from "./chunk-FLLBJLHM.js";
247
259
  import {
248
260
  LOG_KINDS,
249
261
  kindToComponent
@@ -1377,76 +1389,121 @@ function extractTurnsFromBuffer(events) {
1377
1389
  return turns;
1378
1390
  }
1379
1391
 
1380
- // src/daemon/api/config.ts
1381
- function mergeConfigSections(current, incoming) {
1382
- return {
1383
- ...current,
1384
- daemon: { ...current.daemon, ...incoming.daemon },
1385
- embedding: { ...current.embedding, ...incoming.embedding },
1386
- capture: { ...current.capture, ...incoming.capture },
1387
- agent: { ...current.agent, ...incoming.agent },
1388
- context: { ...current.context, ...incoming.context },
1389
- backup: { ...current.backup, ...incoming.backup },
1390
- team: { ...current.team, ...incoming.team },
1391
- notifications: { ...current.notifications, ...incoming.notifications }
1392
- };
1392
+ // src/daemon/config-reactions/touched-paths.ts
1393
+ function enumerateLeafPaths(obj, prefix = "") {
1394
+ if (obj === null || typeof obj !== "object" || Array.isArray(obj)) {
1395
+ return prefix ? [prefix] : [];
1396
+ }
1397
+ const out = [];
1398
+ for (const [key, value] of Object.entries(obj)) {
1399
+ const next = prefix ? `${prefix}.${key}` : key;
1400
+ out.push(...enumerateLeafPaths(value, next));
1401
+ }
1402
+ return out;
1393
1403
  }
1404
+ function computeTouchedPaths(patch, clear) {
1405
+ const patchLeaves = patch && typeof patch === "object" ? enumerateLeafPaths(patch) : [];
1406
+ const clearList = Array.isArray(clear) ? clear : [];
1407
+ return [.../* @__PURE__ */ new Set([...patchLeaves, ...clearList])];
1408
+ }
1409
+
1410
+ // src/daemon/api/config.ts
1394
1411
  async function handleGetConfig(vaultDir) {
1395
1412
  const config = loadConfig(vaultDir);
1396
1413
  return { body: config };
1397
1414
  }
1398
- async function handlePutConfig(vaultDir, body) {
1399
- const result = MycoConfigSchema.safeParse(body);
1400
- if (!result.success) {
1401
- return {
1402
- status: 400,
1403
- body: { error: "validation_failed", issues: result.error.issues }
1404
- };
1415
+ async function handleGetMergedConfig(vaultDir) {
1416
+ const config = loadMergedConfig(vaultDir);
1417
+ return { body: config };
1418
+ }
1419
+ async function handleGetLocalConfig(vaultDir) {
1420
+ return { body: loadLocalConfig(vaultDir) };
1421
+ }
1422
+ var SCOPED_CONFIG_SCOPES = ["project", "local"];
1423
+ function isScopedConfigScope(value) {
1424
+ return typeof value === "string" && SCOPED_CONFIG_SCOPES.includes(value);
1425
+ }
1426
+ function validateClearList(clear) {
1427
+ if (clear === void 0) return [];
1428
+ if (!Array.isArray(clear)) {
1429
+ return { status: 400, body: { error: "clear must be an array of dot-paths" } };
1405
1430
  }
1406
- const updated = updateConfig(vaultDir, (current) => mergeConfigSections(current, result.data));
1407
- return { body: updated };
1431
+ const invalidEntry = clear.find((entry) => typeof entry !== "string" || entry.trim().length === 0);
1432
+ if (invalidEntry !== void 0) {
1433
+ return { status: 400, body: { error: "clear entries must be non-empty strings" } };
1434
+ }
1435
+ return clear;
1408
1436
  }
1409
- function createPlanDirHandlers(deps) {
1410
- const { vaultDir, symbiontPlanDirsByAgent, symbiontPlanDirs } = deps;
1411
- async function handleGetPlanDirs(_req) {
1412
- const config = loadConfig(vaultDir);
1413
- return {
1414
- body: {
1415
- symbiont: symbiontPlanDirsByAgent,
1416
- custom: deps.planWatchConfig.watchDirs.filter((d) => !symbiontPlanDirs.includes(d)),
1417
- ignore_plan_dirs_in_git: config.capture.ignore_plan_dirs_in_git
1418
- }
1419
- };
1437
+ function pathsOverlap(a, b) {
1438
+ return a === b || a.startsWith(`${b}.`) || b.startsWith(`${a}.`);
1439
+ }
1440
+ async function handlePutScopedConfig(vaultDir, body) {
1441
+ const payload = body ?? {};
1442
+ if (!isScopedConfigScope(payload.scope)) {
1443
+ return { status: 400, body: { error: "scope must be project or local" } };
1420
1444
  }
1421
- async function handleUpdatePlanDirs(req) {
1422
- const body = req.body;
1423
- if (!Array.isArray(body.plan_dirs)) {
1424
- return { status: 400, body: { error: "plan_dirs must be an array" } };
1425
- }
1426
- if (body.ignore_plan_dirs_in_git !== void 0 && typeof body.ignore_plan_dirs_in_git !== "boolean") {
1427
- return { status: 400, body: { error: "ignore_plan_dirs_in_git must be a boolean" } };
1428
- }
1429
- const updated = updateConfig(vaultDir, (cfg) => ({
1430
- ...cfg,
1431
- capture: {
1432
- ...cfg.capture,
1433
- plan_dirs: body.plan_dirs,
1434
- ignore_plan_dirs_in_git: body.ignore_plan_dirs_in_git ?? cfg.capture.ignore_plan_dirs_in_git
1445
+ const scope = payload.scope;
1446
+ const patch = payload.patch ?? {};
1447
+ const clearListOrError = validateClearList(payload.clear);
1448
+ if (Array.isArray(clearListOrError) === false) return clearListOrError;
1449
+ const clearList = clearListOrError;
1450
+ if (typeof patch !== "object" || patch === null || Array.isArray(patch)) {
1451
+ return { status: 400, body: { error: "patch must be an object" } };
1452
+ }
1453
+ const patchLeaves = enumerateLeafPaths(patch);
1454
+ const hasPatch = patchLeaves.length > 0;
1455
+ const hasClear = clearList.length > 0;
1456
+ if (!hasPatch && !hasClear) {
1457
+ return { status: 400, body: { error: "patch or clear required" } };
1458
+ }
1459
+ const overlap = patchLeaves.filter((leaf) => clearList.some((clearPath) => pathsOverlap(leaf, clearPath)));
1460
+ if (overlap.length > 0) {
1461
+ return { status: 400, body: { error: "patch_clear_overlap", keys: overlap } };
1462
+ }
1463
+ if (scope === "local") {
1464
+ try {
1465
+ const project = loadConfig(vaultDir);
1466
+ const updated = updateLocalConfig(vaultDir, (local) => {
1467
+ const working = structuredClone(local);
1468
+ for (const key of clearList) unsetAtPath(working, key);
1469
+ const nextLocal = deepMergeConfig(
1470
+ working,
1471
+ patch
1472
+ );
1473
+ const merged = deepMergeConfig(
1474
+ project,
1475
+ nextLocal
1476
+ );
1477
+ MycoConfigSchema.parse(merged);
1478
+ return nextLocal;
1479
+ });
1480
+ return { body: updated };
1481
+ } catch (err) {
1482
+ if (err instanceof external_exports.ZodError) {
1483
+ return { status: 400, body: { error: "validation_failed", issues: err.issues } };
1435
1484
  }
1436
- }));
1437
- deps.setPlanWatchConfig({
1438
- ...deps.planWatchConfig,
1439
- watchDirs: [.../* @__PURE__ */ new Set([...symbiontPlanDirs, ...body.plan_dirs])]
1485
+ throw err;
1486
+ }
1487
+ }
1488
+ try {
1489
+ const updated = updateConfig(vaultDir, (current) => {
1490
+ const working = structuredClone(current);
1491
+ for (const key of clearList) unsetAtPath(working, key);
1492
+ return deepMergeConfig(working, patch);
1440
1493
  });
1441
- deps.reconcileProjectFiles?.();
1442
- return {
1443
- body: {
1444
- custom: updated.capture.plan_dirs,
1445
- ignore_plan_dirs_in_git: updated.capture.ignore_plan_dirs_in_git
1446
- }
1447
- };
1494
+ return { body: updated };
1495
+ } catch (err) {
1496
+ if (err instanceof external_exports.ZodError) {
1497
+ return { status: 400, body: { error: "validation_failed", issues: err.issues } };
1498
+ }
1499
+ throw err;
1448
1500
  }
1449
- return { handleGetPlanDirs, handleUpdatePlanDirs };
1501
+ }
1502
+ function createPlanDirHandlers(deps) {
1503
+ async function handleGetPlanDirs(_req) {
1504
+ return { body: { symbiont: deps.symbiontPlanDirsByAgent } };
1505
+ }
1506
+ return { handleGetPlanDirs };
1450
1507
  }
1451
1508
 
1452
1509
  // src/utils/parse-csv-list.ts
@@ -2229,8 +2286,8 @@ function getConfiguredManifests(projectRoot, config) {
2229
2286
  }
2230
2287
  return allManifests.filter((manifest) => fs12.existsSync(path12.join(projectRoot, manifest.configDir)));
2231
2288
  }
2232
- function reconcileConfiguredSymbionts(projectRoot, vaultDir = path12.join(projectRoot, ".myco")) {
2233
- const config = loadConfig(vaultDir);
2289
+ function reconcileConfiguredSymbionts(projectRoot, vaultDir = path12.join(projectRoot, ".myco"), preloadedConfig) {
2290
+ const config = preloadedConfig ?? loadConfig(vaultDir);
2234
2291
  const manifests = getConfiguredManifests(projectRoot, config);
2235
2292
  const packageRoot = resolvePackageRoot();
2236
2293
  let updatedCount = 0;
@@ -2772,7 +2829,7 @@ function createTeamHandlers(deps) {
2772
2829
  return { body: { retried: count } };
2773
2830
  }
2774
2831
  async function handleUpgradeWorker(_req) {
2775
- const { upgradeWorker } = await import("./team-2IAT6MKD.js");
2832
+ const { upgradeWorker } = await import("./team-3JKF7VAD.js");
2776
2833
  logger.info("team-sync.upgrade.start", "Starting worker upgrade");
2777
2834
  const result = upgradeWorker(vaultDir);
2778
2835
  if (!result.success) {
@@ -3164,7 +3221,7 @@ function createSkillRecordDeleteHandler(deps) {
3164
3221
  logger.warn(LOG_KINDS.PROCESSOR_BATCH, "Failed to remove skill directory", { name: record.name, error: String(err) });
3165
3222
  }
3166
3223
  try {
3167
- const { syncSkillSymlinks } = await import("./installer-YH3WQISI.js");
3224
+ const { syncSkillSymlinks } = await import("./installer-ZNK4JSQA.js");
3168
3225
  syncSkillSymlinks(projectRoot, record.name, { remove: true });
3169
3226
  } catch (err) {
3170
3227
  logger.warn(LOG_KINDS.PROCESSOR_BATCH, "Failed to remove skill symlinks", { name: record.name, error: String(err) });
@@ -3714,6 +3771,14 @@ function upsertPlan(data) {
3714
3771
  syncRow("plans", row);
3715
3772
  return row;
3716
3773
  }
3774
+ function getPlan(id) {
3775
+ const db = getDatabase();
3776
+ const row = db.prepare(
3777
+ `SELECT ${SELECT_COLUMNS4} FROM plans WHERE id = ?`
3778
+ ).get(id);
3779
+ if (!row) return null;
3780
+ return toPlanRow(row);
3781
+ }
3717
3782
  function listPlans(options = {}) {
3718
3783
  const db = getDatabase();
3719
3784
  const conditions = [];
@@ -3788,7 +3853,7 @@ async function triggerTitleSummary(sessionId, deps) {
3788
3853
  if (config.agent.summary_batch_interval <= 0) return;
3789
3854
  if (config.agent.event_tasks_enabled === false) return;
3790
3855
  try {
3791
- const { runAgent } = await import("./executor-2TMGOVEA.js");
3856
+ const { runAgent } = await import("./executor-ACDHGTRH.js");
3792
3857
  runAgent(vaultDir, {
3793
3858
  task: "title-summary",
3794
3859
  instruction: `Process session ${sessionId} only`,
@@ -3900,6 +3965,9 @@ var DEFAULT_LIST_OFFSET3 = 0;
3900
3965
  var DEFAULT_GRAPH_DEPTH = 1;
3901
3966
  var MAX_GRAPH_DEPTH = 3;
3902
3967
  var SPORE_NAME_PREVIEW_CHARS = 60;
3968
+ var GRAPH_SEED_ENTITY_LIMIT = 4;
3969
+ var GRAPH_SEED_SPORE_LIMIT = 4;
3970
+ var GRAPH_SEED_SESSION_LIMIT = 4;
3903
3971
  var EXCLUDED_GRAPH_EDGE_TYPES = /* @__PURE__ */ new Set(["HAS_BATCH", "EXTRACTED_FROM"]);
3904
3972
  async function handleListSpores(req) {
3905
3973
  const agentId = req.query.agent_id;
@@ -3940,11 +4008,93 @@ async function handleListEntities(req) {
3940
4008
  });
3941
4009
  return { body: { entities } };
3942
4010
  }
4011
+ async function handleGetGraphSeeds(_req) {
4012
+ const db = getDatabase();
4013
+ const sporeRows = db.prepare(
4014
+ `SELECT id, observation_type, status, content, created_at
4015
+ FROM spores
4016
+ WHERE agent_id = ? AND status = 'active'
4017
+ ORDER BY created_at DESC
4018
+ LIMIT ?`
4019
+ ).all(DEFAULT_AGENT_ID, GRAPH_SEED_SPORE_LIMIT);
4020
+ const sessionRows = db.prepare(
4021
+ `SELECT id, title, summary, status, started_at as created_at
4022
+ FROM sessions
4023
+ WHERE status != 'active'
4024
+ ORDER BY started_at DESC
4025
+ LIMIT ?`
4026
+ ).all(GRAPH_SEED_SESSION_LIMIT);
4027
+ const entityRows = db.prepare(
4028
+ `SELECT e.id, e.type, e.name, e.status, e.first_seen as created_at, COUNT(em.entity_id) as mention_count
4029
+ FROM entities e
4030
+ LEFT JOIN entity_mentions em ON em.entity_id = e.id
4031
+ WHERE e.agent_id = ? AND e.status = 'active'
4032
+ GROUP BY e.id
4033
+ ORDER BY mention_count DESC, e.last_seen DESC
4034
+ LIMIT ?`
4035
+ ).all(DEFAULT_AGENT_ID, GRAPH_SEED_ENTITY_LIMIT);
4036
+ const sporeSeeds = sporeRows.map((row) => ({
4037
+ id: row.id,
4038
+ name: (row.content ?? "").slice(0, SPORE_NAME_PREVIEW_CHARS),
4039
+ type: "spore",
4040
+ status: row.status ?? void 0,
4041
+ created_at: row.created_at,
4042
+ content: row.content,
4043
+ observation_type: row.observation_type
4044
+ }));
4045
+ const sessionSeeds = sessionRows.map((row) => ({
4046
+ id: row.id,
4047
+ name: row.title ?? `Session ${row.id.slice(-6)}`,
4048
+ type: "session",
4049
+ status: row.status ?? void 0,
4050
+ created_at: row.created_at,
4051
+ content: row.summary ?? void 0
4052
+ }));
4053
+ const entitySeeds = entityRows.map((row) => ({
4054
+ id: row.id,
4055
+ name: row.name,
4056
+ type: row.type,
4057
+ status: row.status ?? void 0,
4058
+ created_at: row.created_at,
4059
+ mention_count: Number(row.mention_count) || 0
4060
+ }));
4061
+ const seeds = [
4062
+ ...entitySeeds,
4063
+ ...sessionSeeds,
4064
+ ...sporeSeeds
4065
+ ];
4066
+ const recommendedId = entitySeeds[0]?.id ?? sessionSeeds[0]?.id ?? sporeSeeds[0]?.id ?? null;
4067
+ return {
4068
+ body: {
4069
+ seeds,
4070
+ recommended_id: recommendedId
4071
+ }
4072
+ };
4073
+ }
3943
4074
  async function handleGetGraph(req) {
3944
4075
  const depth = Math.min(Number(req.query.depth) || DEFAULT_GRAPH_DEPTH, MAX_GRAPH_DEPTH);
3945
- const center = getEntity(req.params.id);
3946
- if (!center) return { status: 404, body: { error: "not_found" } };
3947
- const graph = getGraphForNode(req.params.id, "entity", { depth });
4076
+ const id = req.params.id;
4077
+ let centerNode = null;
4078
+ let centerType = "entity";
4079
+ const entity = getEntity(id);
4080
+ if (entity) {
4081
+ centerNode = entity;
4082
+ centerType = "entity";
4083
+ } else {
4084
+ const spore = getSpore(id);
4085
+ if (spore) {
4086
+ centerNode = spore;
4087
+ centerType = "spore";
4088
+ } else {
4089
+ const session = getSession(id);
4090
+ if (session) {
4091
+ centerNode = session;
4092
+ centerType = "session";
4093
+ }
4094
+ }
4095
+ }
4096
+ if (!centerNode) return { status: 404, body: { error: "not_found" } };
4097
+ const graph = getGraphForNode(id, centerType, { depth });
3948
4098
  const filteredEdges = graph.edges.filter(
3949
4099
  (e) => !EXCLUDED_GRAPH_EDGE_TYPES.has(e.type)
3950
4100
  );
@@ -3953,24 +4103,26 @@ async function handleGetGraph(req) {
3953
4103
  const sporeIds = /* @__PURE__ */ new Set();
3954
4104
  const sessionIds = /* @__PURE__ */ new Set();
3955
4105
  for (const edge of filteredEdges) {
3956
- for (const [id, type] of [
4106
+ for (const [nodeId, type] of [
3957
4107
  [edge.source_id, edge.source_type],
3958
4108
  [edge.target_id, edge.target_type]
3959
4109
  ]) {
3960
4110
  switch (type) {
3961
4111
  case "entity":
3962
- entityIds.add(id);
4112
+ entityIds.add(nodeId);
3963
4113
  break;
3964
4114
  case "spore":
3965
- sporeIds.add(id);
4115
+ sporeIds.add(nodeId);
3966
4116
  break;
3967
4117
  case "session":
3968
- sessionIds.add(id);
4118
+ sessionIds.add(nodeId);
3969
4119
  break;
3970
4120
  }
3971
4121
  }
3972
4122
  }
3973
- entityIds.add(center.id);
4123
+ if (centerType === "entity") entityIds.add(id);
4124
+ if (centerType === "spore") sporeIds.add(id);
4125
+ if (centerType === "session") sessionIds.add(id);
3974
4126
  const entityIdArray = Array.from(entityIds);
3975
4127
  let entityNodes = [];
3976
4128
  if (entityIdArray.length > 0) {
@@ -4038,17 +4190,17 @@ async function handleGetGraph(req) {
4038
4190
  content: n.summary ?? void 0
4039
4191
  }))
4040
4192
  ];
4041
- const centerNode = allNodes.find((n) => n.id === center.id);
4042
4193
  const uiEdges = filteredEdges.map((e) => ({
4043
4194
  source_id: e.source_id,
4044
4195
  target_id: e.target_id,
4045
4196
  label: e.type,
4046
4197
  weight: e.confidence
4047
4198
  }));
4199
+ const centerResponseNode = allNodes.find((n) => n.id === id);
4048
4200
  return {
4049
4201
  body: {
4050
- center: centerNode ?? { ...center, mention_count: mentionCounts.get(center.id) ?? 0 },
4051
- nodes: allNodes.filter((n) => n.id !== center.id),
4202
+ center: centerResponseNode,
4203
+ nodes: allNodes.filter((n) => n.id !== id),
4052
4204
  edges: uiEdges,
4053
4205
  depth
4054
4206
  }
@@ -5818,8 +5970,8 @@ function registerBuiltinDomains() {
5818
5970
  domain: "agents",
5819
5971
  label: "Agent Tasks",
5820
5972
  types: [
5821
- { id: "agent.task.success", label: "Task completed", defaultMode: "banner", defaultLevel: "success" },
5822
- { id: "agent.task.failure", label: "Task failed", defaultMode: "banner", defaultLevel: "error" }
5973
+ { id: "agent.task.success", label: "Task completed", defaultMode: "summary", defaultLevel: "success" },
5974
+ { id: "agent.task.failure", label: "Task failed", defaultMode: "summary", defaultLevel: "error" }
5823
5975
  ]
5824
5976
  });
5825
5977
  register({
@@ -5835,8 +5987,8 @@ function registerBuiltinDomains() {
5835
5987
  label: "Skills",
5836
5988
  types: [
5837
5989
  { id: "skill.surveyed", label: "Skill candidate surveyed", defaultMode: "summary", defaultLevel: "info" },
5838
- { id: "skill.created", label: "Skill created", defaultMode: "banner", defaultLevel: "success" },
5839
- { id: "skill.evolved", label: "Skill evolved", defaultMode: "banner", defaultLevel: "info" }
5990
+ { id: "skill.created", label: "Skill created", defaultMode: "summary", defaultLevel: "success" },
5991
+ { id: "skill.evolved", label: "Skill evolved", defaultMode: "summary", defaultLevel: "info" }
5840
5992
  ]
5841
5993
  });
5842
5994
  register({
@@ -5851,7 +6003,14 @@ function registerBuiltinDomains() {
5851
6003
  domain: "daemon",
5852
6004
  label: "Daemon",
5853
6005
  types: [
5854
- { id: "daemon.version_sync", label: "Version sync restart", defaultMode: "banner", defaultLevel: "info" }
6006
+ { id: "daemon.version_sync", label: "Version sync restart", defaultMode: "summary", defaultLevel: "info" }
6007
+ ]
6008
+ });
6009
+ register({
6010
+ domain: "settings",
6011
+ label: "Settings",
6012
+ types: [
6013
+ { id: "settings.saved", label: "Settings saved", defaultMode: "banner", defaultLevel: "success" }
5855
6014
  ]
5856
6015
  });
5857
6016
  }
@@ -6258,7 +6417,7 @@ async function registerScheduledTasks(powerManager, deps) {
6258
6417
  logger.info(LOG_KINDS.AGENT_RUN, "Scheduled agent tasks disabled globally (agent.scheduled_tasks_enabled: false)");
6259
6418
  return;
6260
6419
  }
6261
- const { loadAllTasks: loadAllTasks2 } = await import("./registry-OCM4WAPJ.js");
6420
+ const { loadAllTasks: loadAllTasks2 } = await import("./registry-MGJSJBAS.js");
6262
6421
  const allTasks = Array.from(loadAllTasks2(definitionsDir, vaultDir).values());
6263
6422
  const taskAgentMap = /* @__PURE__ */ new Map();
6264
6423
  for (const task of allTasks) {
@@ -6284,7 +6443,7 @@ async function registerScheduledTasks(powerManager, deps) {
6284
6443
  else runningTasks.delete(name);
6285
6444
  },
6286
6445
  runTask: async (taskName) => {
6287
- const { runAgent } = await import("./executor-2TMGOVEA.js");
6446
+ const { runAgent } = await import("./executor-ACDHGTRH.js");
6288
6447
  const taskConfig = config.agent.tasks?.[taskName];
6289
6448
  const projectRoot = resolve(vaultDir, "..");
6290
6449
  const built = buildTaskInstruction(taskName, taskConfig?.params, taskAgentMap.get(taskName), projectRoot, embeddingManager);
@@ -6323,7 +6482,7 @@ async function registerScheduledTasks(powerManager, deps) {
6323
6482
  link: `/agent?run=${result.runId}`,
6324
6483
  metadata: { taskName, runId: result.runId }
6325
6484
  }, config);
6326
- const { countToolCallsByRun } = await import("./turns-3ZQAF6HF.js");
6485
+ const { countToolCallsByRun } = await import("./turns-YFNI5CQC.js");
6327
6486
  const counts = countToolCallsByRun(result.runId, ["vault_create_spore", "vault_write_digest"]);
6328
6487
  const sporeCount = counts["vault_create_spore"] ?? 0;
6329
6488
  const digestCount = counts["vault_write_digest"] ?? 0;
@@ -6400,6 +6559,7 @@ function listTeamMembers() {
6400
6559
  // src/daemon/api/mcp-proxy.ts
6401
6560
  var SPORE_ID_RANDOM_BYTES = 4;
6402
6561
  var RESOLUTION_ID_RANDOM_BYTES = 8;
6562
+ var MIN_CONSOLIDATE_SOURCES = 2;
6403
6563
  var RememberBody = external_exports.object({
6404
6564
  content: external_exports.string(),
6405
6565
  type: external_exports.string().optional(),
@@ -6410,19 +6570,53 @@ var SupersedeBody = external_exports.object({
6410
6570
  new_spore_id: external_exports.string(),
6411
6571
  reason: external_exports.string().optional()
6412
6572
  });
6573
+ function isoToEpochSeconds(iso) {
6574
+ const ms = Date.parse(iso);
6575
+ return Number.isNaN(ms) ? void 0 : Math.floor(ms / 1e3);
6576
+ }
6577
+ function registerMcpUserAgent(createdAt) {
6578
+ registerAgent({
6579
+ id: USER_AGENT_ID,
6580
+ name: USER_AGENT_NAME,
6581
+ created_at: createdAt
6582
+ });
6583
+ }
6584
+ function toPlanProgress(content) {
6585
+ const planContent = content ?? "";
6586
+ const checked = (planContent.match(/- \[x\]/gi) ?? []).length;
6587
+ const unchecked = (planContent.match(/- \[ \]/g) ?? []).length;
6588
+ const total = checked + unchecked;
6589
+ return total === 0 ? "N/A" : `${checked}/${total}`;
6590
+ }
6591
+ function toPlanTags(tags) {
6592
+ return tags ? tags.split(",").map((tag) => tag.trim()) : [];
6593
+ }
6594
+ var ConsolidateBody = external_exports.object({
6595
+ source_spore_ids: external_exports.array(external_exports.string()).min(MIN_CONSOLIDATE_SOURCES),
6596
+ consolidated_content: external_exports.string().min(1),
6597
+ observation_type: external_exports.string(),
6598
+ tags: external_exports.array(external_exports.string()).optional(),
6599
+ reason: external_exports.string().optional()
6600
+ });
6413
6601
  function createMcpProxyHandlers(deps) {
6414
6602
  const { machineId, embeddingManager } = deps;
6603
+ function toPlanSummary(row) {
6604
+ return {
6605
+ id: row.id,
6606
+ title: row.title,
6607
+ status: row.status,
6608
+ progress: toPlanProgress(row.content),
6609
+ tags: toPlanTags(row.tags),
6610
+ created_at: row.created_at
6611
+ };
6612
+ }
6415
6613
  async function handleRemember(req) {
6416
6614
  const { content, type, tags } = RememberBody.parse(req.body);
6417
6615
  const { randomBytes } = await import("crypto");
6418
6616
  const observationType = type ?? "discovery";
6419
6617
  const id = `${observationType}-${randomBytes(SPORE_ID_RANDOM_BYTES).toString("hex")}`;
6420
6618
  const now = epochSeconds();
6421
- registerAgent({
6422
- id: USER_AGENT_ID,
6423
- name: USER_AGENT_NAME,
6424
- created_at: now
6425
- });
6619
+ registerMcpUserAgent(now);
6426
6620
  const spore = insertSpore({
6427
6621
  id,
6428
6622
  agent_id: USER_AGENT_ID,
@@ -6455,12 +6649,7 @@ function createMcpProxyHandlers(deps) {
6455
6649
  embeddingManager.onStatusChanged("spores", old_spore_id, "superseded");
6456
6650
  } catch {
6457
6651
  }
6458
- registerAgent({
6459
- id: USER_AGENT_ID,
6460
- name: USER_AGENT_NAME,
6461
- created_at: now
6462
- });
6463
- const { insertResolutionEvent } = await import("./resolution-events-PYLSI6QT.js");
6652
+ registerMcpUserAgent(now);
6464
6653
  const resolutionId = `res-${randomBytes(RESOLUTION_ID_RANDOM_BYTES).toString("hex")}`;
6465
6654
  insertResolutionEvent({
6466
6655
  id: resolutionId,
@@ -6480,31 +6669,95 @@ function createMcpProxyHandlers(deps) {
6480
6669
  }
6481
6670
  };
6482
6671
  }
6672
+ async function handleConsolidate(req) {
6673
+ const { source_spore_ids, consolidated_content, observation_type, tags, reason } = ConsolidateBody.parse(req.body);
6674
+ const { randomBytes } = await import("crypto");
6675
+ const now = epochSeconds();
6676
+ const newSporeId = `${observation_type}-${randomBytes(SPORE_ID_RANDOM_BYTES).toString("hex")}`;
6677
+ const db = getDatabase();
6678
+ registerMcpUserAgent(now);
6679
+ const { wisdom, sourcesSuperseded } = db.transaction(() => {
6680
+ const insertedWisdom = insertSpore({
6681
+ id: newSporeId,
6682
+ agent_id: USER_AGENT_ID,
6683
+ machine_id: machineId,
6684
+ observation_type,
6685
+ content: consolidated_content,
6686
+ tags: tags ? tags.join(", ") : null,
6687
+ created_at: now
6688
+ });
6689
+ const supersededSourceIds = [];
6690
+ for (const sourceId of source_spore_ids) {
6691
+ updateSporeStatus(sourceId, "superseded", now);
6692
+ insertResolutionEvent({
6693
+ id: `res-${randomBytes(RESOLUTION_ID_RANDOM_BYTES).toString("hex")}`,
6694
+ agent_id: USER_AGENT_ID,
6695
+ machine_id: machineId,
6696
+ spore_id: sourceId,
6697
+ action: "consolidate",
6698
+ new_spore_id: newSporeId,
6699
+ reason: reason ?? null,
6700
+ created_at: now
6701
+ });
6702
+ supersededSourceIds.push(sourceId);
6703
+ }
6704
+ return { wisdom: insertedWisdom, sourcesSuperseded: supersededSourceIds };
6705
+ })();
6706
+ embeddingManager.onContentWritten("spores", wisdom.id, consolidated_content, {
6707
+ status: "active",
6708
+ observation_type
6709
+ }).catch(() => {
6710
+ });
6711
+ for (const sourceId of sourcesSuperseded) {
6712
+ try {
6713
+ embeddingManager.onStatusChanged("spores", sourceId, "superseded");
6714
+ } catch {
6715
+ }
6716
+ }
6717
+ return {
6718
+ body: {
6719
+ new_spore_id: newSporeId,
6720
+ sources_superseded: sourcesSuperseded,
6721
+ status: "consolidated",
6722
+ created_at: now
6723
+ }
6724
+ };
6725
+ }
6483
6726
  async function handlePlans(req) {
6727
+ const id = typeof req.query.id === "string" ? req.query.id : void 0;
6728
+ if (id) {
6729
+ const row = getPlan(id);
6730
+ if (!row) return { body: { plans: [] } };
6731
+ return {
6732
+ body: {
6733
+ plans: [{
6734
+ ...toPlanSummary(row),
6735
+ content: row.content
6736
+ }]
6737
+ }
6738
+ };
6739
+ }
6484
6740
  const statusFilter = req.query.status === "all" ? void 0 : req.query.status;
6485
6741
  const limit = req.query.limit ? Number(req.query.limit) : void 0;
6486
6742
  const rows = listPlans({ status: statusFilter, limit });
6487
- const plans = rows.map((row) => {
6488
- const content = row.content ?? "";
6489
- const checked = (content.match(/- \[x\]/gi) ?? []).length;
6490
- const unchecked = (content.match(/- \[ \]/g) ?? []).length;
6491
- const total = checked + unchecked;
6492
- const progress = total === 0 ? "N/A" : `${checked}/${total}`;
6493
- return {
6494
- id: row.id,
6495
- title: row.title,
6496
- status: row.status,
6497
- progress,
6498
- tags: row.tags ? row.tags.split(",").map((t) => t.trim()) : [],
6499
- created_at: row.created_at
6500
- };
6501
- });
6743
+ const plans = rows.map(toPlanSummary);
6502
6744
  return { body: { plans } };
6503
6745
  }
6504
6746
  async function handleSessions(req) {
6505
- const limit = req.query.limit ? Number(req.query.limit) : 20;
6506
- const status = req.query.status;
6507
- const rows = listSessions({ limit, status });
6747
+ const limit = req.query.limit ? Number(req.query.limit) : MCP_SESSIONS_DEFAULT_LIMIT;
6748
+ const status = typeof req.query.status === "string" ? req.query.status : void 0;
6749
+ const branch = typeof req.query.branch === "string" ? req.query.branch : void 0;
6750
+ const user = typeof req.query.user === "string" ? req.query.user : void 0;
6751
+ const plan = typeof req.query.plan === "string" ? req.query.plan : void 0;
6752
+ const sinceRaw = typeof req.query.since === "string" ? req.query.since : void 0;
6753
+ const since = sinceRaw ? isoToEpochSeconds(sinceRaw) : void 0;
6754
+ let id;
6755
+ if (plan) {
6756
+ const planRow = getPlan(plan);
6757
+ if (!planRow || !planRow.session_id) return { body: { sessions: [] } };
6758
+ id = planRow.session_id;
6759
+ }
6760
+ const rows = listSessions({ limit, status, branch, user, since, id });
6508
6761
  const sessions = rows.map((row) => ({
6509
6762
  id: row.id,
6510
6763
  agent: row.agent,
@@ -6514,7 +6767,7 @@ function createMcpProxyHandlers(deps) {
6514
6767
  ended_at: row.ended_at,
6515
6768
  status: row.status,
6516
6769
  title: row.title,
6517
- summary: (row.summary ?? "").slice(0, 300),
6770
+ summary: (row.summary ?? "").slice(0, SESSION_SUMMARY_PREVIEW_CHARS),
6518
6771
  prompt_count: row.prompt_count,
6519
6772
  tool_count: row.tool_count,
6520
6773
  parent_session_id: row.parent_session_id
@@ -6535,6 +6788,7 @@ function createMcpProxyHandlers(deps) {
6535
6788
  return {
6536
6789
  handleRemember,
6537
6790
  handleSupersede,
6791
+ handleConsolidate,
6538
6792
  handlePlans,
6539
6793
  handleSessions,
6540
6794
  handleTeam
@@ -6588,7 +6842,7 @@ function createAgentRunHandlers(deps) {
6588
6842
  };
6589
6843
  }
6590
6844
  }
6591
- const { runAgent } = await import("./executor-2TMGOVEA.js");
6845
+ const { runAgent } = await import("./executor-ACDHGTRH.js");
6592
6846
  const resultPromise = runAgent(vaultDir, {
6593
6847
  task,
6594
6848
  instruction,
@@ -6599,13 +6853,29 @@ function createAgentRunHandlers(deps) {
6599
6853
  const effectiveAgentId = agentId ?? "myco-agent";
6600
6854
  const runId = getLatestRunId(effectiveAgentId, task);
6601
6855
  resultPromise.then((result) => {
6856
+ const taskName = task ?? "agent run";
6602
6857
  if (result.status === "failed") {
6858
+ notify(vaultDir, {
6859
+ domain: "agents",
6860
+ type: "agent.task.failure",
6861
+ title: `Task failed: ${taskName}`,
6862
+ message: result.error ?? "Unknown error",
6863
+ link: `/agent?run=${result.runId}`,
6864
+ metadata: { taskName: task ?? null, runId: result.runId }
6865
+ }, mycoConfig);
6603
6866
  logger.error(LOG_KINDS.AGENT_ERROR, "Agent run failed", {
6604
6867
  runId: result.runId,
6605
6868
  error: result.error ?? "No error message",
6606
6869
  phases: result.phases?.map((p) => `${p.name}:${p.status}`) ?? []
6607
6870
  });
6608
6871
  } else {
6872
+ notify(vaultDir, {
6873
+ domain: "agents",
6874
+ type: "agent.task.success",
6875
+ title: `Task completed: ${taskName}`,
6876
+ link: `/agent?run=${result.runId}`,
6877
+ metadata: { taskName: task ?? null, runId: result.runId }
6878
+ }, mycoConfig);
6609
6879
  logger.info(LOG_KINDS.AGENT_RUN, "Agent run completed", {
6610
6880
  runId: result.runId,
6611
6881
  status: result.status,
@@ -6730,6 +7000,207 @@ function reconcileLogBuffer(logDir, sinceTimestamp) {
6730
7000
  return replayed;
6731
7001
  }
6732
7002
 
7003
+ // src/config/focus.ts
7004
+ var CONFIG_FOCUS_SECTION_PARAM = "configSection";
7005
+ var CONFIG_FOCUS_FIELD_PARAM = "configField";
7006
+ var CONFIG_SECTION_IDS = {
7007
+ appearance: "config-section-appearance",
7008
+ settingsAgent: "config-section-settings-agent",
7009
+ settingsEmbedding: "config-section-settings-embedding",
7010
+ settingsContextInjection: "config-section-settings-context-injection",
7011
+ settingsNotifications: "config-section-settings-notifications",
7012
+ settingsPlanCapture: "config-section-settings-plan-capture",
7013
+ settingsProject: "config-section-settings-project",
7014
+ agentOperations: "config-section-agent-operations",
7015
+ operationsMaintenance: "config-section-operations-maintenance",
7016
+ operationsBackup: "config-section-operations-backup"
7017
+ };
7018
+ var SECTION_RULES = [
7019
+ {
7020
+ prefix: "appearance",
7021
+ page: "/settings",
7022
+ sectionId: CONFIG_SECTION_IDS.appearance,
7023
+ sectionLabel: "Appearance"
7024
+ },
7025
+ {
7026
+ prefix: "agent.provider",
7027
+ page: "/settings",
7028
+ sectionId: CONFIG_SECTION_IDS.settingsAgent,
7029
+ sectionLabel: "Myco Agent"
7030
+ },
7031
+ {
7032
+ prefix: "embedding",
7033
+ page: "/settings",
7034
+ sectionId: CONFIG_SECTION_IDS.settingsEmbedding,
7035
+ sectionLabel: "Embedding"
7036
+ },
7037
+ {
7038
+ prefix: "context",
7039
+ page: "/settings",
7040
+ sectionId: CONFIG_SECTION_IDS.settingsContextInjection,
7041
+ sectionLabel: "Context Injection"
7042
+ },
7043
+ {
7044
+ prefix: "notifications",
7045
+ page: "/settings",
7046
+ sectionId: CONFIG_SECTION_IDS.settingsNotifications,
7047
+ sectionLabel: "Notifications"
7048
+ },
7049
+ {
7050
+ prefix: "capture",
7051
+ page: "/settings",
7052
+ sectionId: CONFIG_SECTION_IDS.settingsPlanCapture,
7053
+ sectionLabel: "Plan Capture"
7054
+ },
7055
+ {
7056
+ prefix: "daemon",
7057
+ page: "/settings",
7058
+ sectionId: CONFIG_SECTION_IDS.settingsProject,
7059
+ sectionLabel: "Project"
7060
+ },
7061
+ {
7062
+ prefix: "agent.scheduled_tasks_enabled",
7063
+ page: "/agent",
7064
+ sectionId: CONFIG_SECTION_IDS.agentOperations,
7065
+ sectionLabel: "Agent Operations",
7066
+ searchParams: { tab: "config" }
7067
+ },
7068
+ {
7069
+ prefix: "agent.event_tasks_enabled",
7070
+ page: "/agent",
7071
+ sectionId: CONFIG_SECTION_IDS.agentOperations,
7072
+ sectionLabel: "Agent Operations",
7073
+ searchParams: { tab: "config" }
7074
+ },
7075
+ {
7076
+ prefix: "agent.summary_batch_interval",
7077
+ page: "/agent",
7078
+ sectionId: CONFIG_SECTION_IDS.agentOperations,
7079
+ sectionLabel: "Agent Operations",
7080
+ searchParams: { tab: "config" }
7081
+ },
7082
+ {
7083
+ prefix: "maintenance",
7084
+ page: "/operations",
7085
+ sectionId: CONFIG_SECTION_IDS.operationsMaintenance,
7086
+ sectionLabel: "Scheduled Maintenance"
7087
+ },
7088
+ {
7089
+ prefix: "backup",
7090
+ page: "/operations",
7091
+ sectionId: CONFIG_SECTION_IDS.operationsBackup,
7092
+ sectionLabel: "Backup & Restore"
7093
+ }
7094
+ ];
7095
+ var EXACT_FIELD_LABELS = {
7096
+ "appearance.theme": "Color Theme",
7097
+ "appearance.mode": "Mode",
7098
+ "appearance.font": "Font",
7099
+ "appearance.density": "Density",
7100
+ "agent.provider": "Provider",
7101
+ "agent.provider.type": "Provider",
7102
+ "agent.provider.model": "Model",
7103
+ "agent.provider.base_url": "Base URL",
7104
+ "agent.provider.context_length": "Context Length",
7105
+ "embedding.provider": "Provider",
7106
+ "embedding.model": "Model",
7107
+ "embedding.base_url": "Base URL",
7108
+ "context.digest_tier": "Digest Tier",
7109
+ "context.prompt_search": "Prompt Search",
7110
+ "context.prompt_max_spores": "Max Spores per Prompt",
7111
+ "notifications.enabled": "Notifications",
7112
+ "notifications.default_mode": "Default Display",
7113
+ "notifications.system_notifications": "Browser Notifications",
7114
+ "capture.ignore_plan_dirs_in_git": "Ignore Custom Plan Dirs In Git",
7115
+ "capture.plan_dirs": "Custom Directories",
7116
+ "daemon.port": "Daemon Port",
7117
+ "daemon.log_level": "Log Level",
7118
+ "daemon.log_retention_days": "Log Retention (days)",
7119
+ "agent.scheduled_tasks_enabled": "Scheduled Tasks",
7120
+ "agent.event_tasks_enabled": "Event-Driven Tasks",
7121
+ "agent.summary_batch_interval": "Title & Summary Batch Interval",
7122
+ "maintenance.auto_optimize": "Auto-optimize",
7123
+ "maintenance.auto_optimize_interval_hours": "Auto-optimize Interval",
7124
+ "backup.dir": "Backup Directory"
7125
+ };
7126
+ var DYNAMIC_FIELD_LABEL_RULES = [
7127
+ {
7128
+ prefix: "notifications.domains.",
7129
+ format: (path23) => {
7130
+ const match = /^notifications\.domains\.([^.]+)\.(enabled|mode)$/.exec(path23);
7131
+ if (!match) return null;
7132
+ const [, domain, leaf] = match;
7133
+ const domainLabel = humanizeToken(domain);
7134
+ return leaf === "mode" ? `${domainLabel} Display` : `${domainLabel} Notifications`;
7135
+ }
7136
+ }
7137
+ ];
7138
+ var SAVE_MESSAGE_LABEL_LIMIT = 3;
7139
+ function resolveConfigFocusTarget(path23) {
7140
+ const section = findSectionRule(path23);
7141
+ if (!section) return null;
7142
+ return {
7143
+ ...section,
7144
+ fieldPath: path23,
7145
+ fieldLabel: resolveFieldLabel(path23)
7146
+ };
7147
+ }
7148
+ function buildConfigFocusLink(target) {
7149
+ const params = new URLSearchParams(target.searchParams);
7150
+ params.set(CONFIG_FOCUS_SECTION_PARAM, target.sectionId);
7151
+ params.set(CONFIG_FOCUS_FIELD_PARAM, target.fieldPath);
7152
+ return `${target.page}?${params.toString()}`;
7153
+ }
7154
+ function buildScopedConfigSaveNotification(scope, touchedPaths) {
7155
+ const uniquePaths = [...new Set(touchedPaths)];
7156
+ const scopeLabel = scope === "local" ? "Personal" : "Project";
7157
+ const focusTarget = uniquePaths.map(resolveConfigFocusTarget).find((target) => target !== null) ?? null;
7158
+ const fieldLabels = uniquePaths.map(resolveFieldLabel);
7159
+ const primaryLabel = fieldLabels[0] ?? "Setting";
7160
+ const labelList = fieldLabels.slice(0, SAVE_MESSAGE_LABEL_LIMIT).join(", ");
7161
+ const remainingCount = Math.max(0, fieldLabels.length - SAVE_MESSAGE_LABEL_LIMIT);
7162
+ const messageLabel = remainingCount > 0 ? `${labelList}, +${remainingCount} more` : labelList;
7163
+ return {
7164
+ title: uniquePaths.length === 1 ? `${primaryLabel} saved` : `${uniquePaths.length} settings saved`,
7165
+ message: focusTarget ? `${focusTarget.sectionLabel} \xB7 ${messageLabel} \xB7 ${scopeLabel}` : `${messageLabel} \xB7 ${scopeLabel}`,
7166
+ link: focusTarget ? buildConfigFocusLink(focusTarget) : null,
7167
+ metadata: {
7168
+ scope,
7169
+ touched_paths: uniquePaths,
7170
+ field_labels: fieldLabels,
7171
+ focus_target: focusTarget ? {
7172
+ page: focusTarget.page,
7173
+ section_id: focusTarget.sectionId,
7174
+ field_path: focusTarget.fieldPath,
7175
+ field_label: focusTarget.fieldLabel
7176
+ } : null
7177
+ }
7178
+ };
7179
+ }
7180
+ function findSectionRule(path23) {
7181
+ for (const rule of SECTION_RULES) {
7182
+ if (path23 === rule.prefix || path23.startsWith(`${rule.prefix}.`)) {
7183
+ const { page, sectionId, sectionLabel, searchParams } = rule;
7184
+ return { page, sectionId, sectionLabel, searchParams };
7185
+ }
7186
+ }
7187
+ return null;
7188
+ }
7189
+ function resolveFieldLabel(path23) {
7190
+ const exact = EXACT_FIELD_LABELS[path23];
7191
+ if (exact) return exact;
7192
+ for (const rule of DYNAMIC_FIELD_LABEL_RULES) {
7193
+ if (path23 === rule.prefix || path23.startsWith(rule.prefix)) {
7194
+ const label = rule.format(path23);
7195
+ if (label) return label;
7196
+ }
7197
+ }
7198
+ return humanizeToken(path23.split(".").pop() ?? "setting");
7199
+ }
7200
+ function humanizeToken(value) {
7201
+ return value.split(/[-_]/g).filter(Boolean).map((part) => part.charAt(0).toUpperCase() + part.slice(1)).join(" ");
7202
+ }
7203
+
6733
7204
  // src/daemon/power.ts
6734
7205
  var PowerManager = class {
6735
7206
  state = "active";
@@ -6926,7 +7397,7 @@ function registerPowerJobs(powerManager, deps) {
6926
7397
  name: "log-retention",
6927
7398
  runIn: ["idle", "sleep"],
6928
7399
  fn: async () => {
6929
- const retentionDays = config.daemon.log_retention_days;
7400
+ const retentionDays = loadMergedConfig(vaultDir).daemon.log_retention_days;
6930
7401
  const cutoff = new Date(Date.now() - retentionDays * MS_PER_DAY).toISOString();
6931
7402
  const deleted = deleteOldLogs(cutoff);
6932
7403
  if (deleted > 0) {
@@ -7401,11 +7872,22 @@ function createStopProcessor(deps) {
7401
7872
  const sessionTitleCache = /* @__PURE__ */ new Map();
7402
7873
  const StopBody = external_exports.object({
7403
7874
  session_id: external_exports.string(),
7875
+ agent: external_exports.string().optional(),
7404
7876
  user: external_exports.string().optional(),
7405
7877
  transcript_path: external_exports.string().nullish(),
7406
7878
  last_assistant_message: external_exports.string().nullish()
7407
7879
  });
7408
7880
  const triggerTitleSummary2 = (sessionId) => triggerTitleSummary(sessionId, { vaultDir, embeddingManager, config, logger });
7881
+ function cleanupInvalidCapturedSession(sessionId) {
7882
+ registry.unregister(sessionId);
7883
+ sessionBuffers.delete(sessionId);
7884
+ sessionTitleCache.delete(sessionId);
7885
+ const result = deleteSessionCascade(sessionId);
7886
+ if (!result.deleted) return false;
7887
+ cleanupAfterSessionCascade(sessionId, result, embeddingManager, vaultDir).catch(() => {
7888
+ });
7889
+ return true;
7890
+ }
7409
7891
  async function processStopEvent(sessionId, user, sessionMeta, hookTranscriptPath, lastAssistantMessage) {
7410
7892
  const transcriptResult = transcriptMiner.getAllTurnsWithSource(sessionId, hookTranscriptPath);
7411
7893
  let allTurns = transcriptResult.turns;
@@ -7578,7 +8060,30 @@ function createStopProcessor(deps) {
7578
8060
  });
7579
8061
  }
7580
8062
  const handleStopRoute = async (req) => {
7581
- const { session_id: sessionId, user, transcript_path: hookTranscriptPath, last_assistant_message: lastAssistantMessage } = StopBody.parse(req.body);
8063
+ const {
8064
+ session_id: sessionId,
8065
+ agent,
8066
+ user,
8067
+ transcript_path: hookTranscriptPath,
8068
+ last_assistant_message: lastAssistantMessage
8069
+ } = StopBody.parse(req.body);
8070
+ if (hookTranscriptPath) {
8071
+ const transcriptMeta = readTranscriptMeta(hookTranscriptPath) ?? void 0;
8072
+ const detectedAgent = agent ?? getSession(sessionId)?.agent ?? "claude-code";
8073
+ const decision = evaluateSessionCaptureRules(loadManifests(), detectedAgent, {
8074
+ transcriptPath: hookTranscriptPath,
8075
+ transcriptMeta
8076
+ });
8077
+ if (decision.action === "drop") {
8078
+ const deleted = cleanupInvalidCapturedSession(sessionId);
8079
+ logger.info(LOG_KINDS.HOOKS_STOP, "Stop ignored \u2014 invalid captured session", {
8080
+ session_id: sessionId,
8081
+ reason: decision.reason ?? "rule",
8082
+ deleted_existing_session: deleted
8083
+ });
8084
+ return { body: { ok: true, ignored: decision.reason ?? "rule" } };
8085
+ }
8086
+ }
7582
8087
  const existingSessionMeta = registry.getSession(sessionId);
7583
8088
  if (!hookTranscriptPath && !existingSessionMeta) {
7584
8089
  logger.info(LOG_KINDS.HOOKS_STOP, "Stop ignored \u2014 ephemeral sub-invocation", {
@@ -7866,6 +8371,62 @@ function createEventDispatcher(deps) {
7866
8371
  };
7867
8372
  }
7868
8373
 
8374
+ // src/daemon/config-reactions/registry.ts
8375
+ function createConfigReactionRegistry(logger) {
8376
+ const entries = [];
8377
+ return {
8378
+ on(paths, fn) {
8379
+ entries.push({ paths, fn });
8380
+ },
8381
+ async fire(touchedPaths, ctx) {
8382
+ for (const entry of entries) {
8383
+ if (!shouldFire(entry.paths, touchedPaths)) continue;
8384
+ try {
8385
+ await entry.fn(ctx);
8386
+ } catch (err) {
8387
+ logger.error("config-reactions", "reaction threw", { error: String(err) });
8388
+ }
8389
+ }
8390
+ }
8391
+ };
8392
+ }
8393
+ function shouldFire(registeredPaths, touched) {
8394
+ if (registeredPaths.length === 0) return true;
8395
+ for (const prefix of registeredPaths) {
8396
+ for (const path23 of touched) {
8397
+ if (path23 === prefix || path23.startsWith(`${prefix}.`)) return true;
8398
+ }
8399
+ }
8400
+ return false;
8401
+ }
8402
+
8403
+ // src/daemon/config-reactions/context.ts
8404
+ function loadReactionContext(vaultDir, logger) {
8405
+ try {
8406
+ return loadMergedConfig(vaultDir);
8407
+ } catch (err) {
8408
+ if (err instanceof external_exports.ZodError) {
8409
+ logger.warn("config-reactions", "skipping reactions because merged config is invalid", {
8410
+ issues: err.issues.map((issue) => ({
8411
+ path: issue.path.join("."),
8412
+ message: issue.message
8413
+ }))
8414
+ });
8415
+ return null;
8416
+ }
8417
+ throw err;
8418
+ }
8419
+ }
8420
+
8421
+ // src/daemon/plan-watch-reaction.ts
8422
+ function createPlanWatchReaction(deps) {
8423
+ return (ctx) => {
8424
+ const customDirs = ctx.capture.plan_dirs ?? [];
8425
+ deps.planWatchConfig.watchDirs = [.../* @__PURE__ */ new Set([...deps.symbiontPlanDirs, ...customDirs])];
8426
+ deps.planWatchConfig.extensions = ctx.capture.artifact_extensions;
8427
+ };
8428
+ }
8429
+
7869
8430
  // src/daemon/main.ts
7870
8431
  import fs23 from "fs";
7871
8432
  import os8 from "os";
@@ -7900,7 +8461,7 @@ async function main() {
7900
8461
  const symbiontPlanDirs = manifests.flatMap((m) => m.capture?.planDirs ?? []);
7901
8462
  const symbiontPlanTags = [...new Set(manifests.flatMap((m) => m.capture?.planTags ?? []))];
7902
8463
  const projectRoot = process.cwd();
7903
- let planWatchConfig = {
8464
+ const planWatchConfig = {
7904
8465
  watchDirs: [.../* @__PURE__ */ new Set([...symbiontPlanDirs, ...config.capture.plan_dirs ?? []])],
7905
8466
  projectRoot,
7906
8467
  extensions: config.capture.artifact_extensions
@@ -8010,7 +8571,7 @@ async function main() {
8010
8571
  const databaseManager = new DatabaseMaintenanceManager(vaultDbPath(vaultDir), vaultDir, logger);
8011
8572
  let definitionsDir;
8012
8573
  try {
8013
- const { registerBuiltInAgentsAndTasks, resolveDefinitionsDir: resolveDefinitionsDir2 } = await import("./loader-AAZ6VUIA.js");
8574
+ const { registerBuiltInAgentsAndTasks, resolveDefinitionsDir: resolveDefinitionsDir2 } = await import("./loader-TSB5M7FD.js");
8014
8575
  definitionsDir = resolveDefinitionsDir2();
8015
8576
  await registerBuiltInAgentsAndTasks(definitionsDir, vaultDir);
8016
8577
  logger.info(LOG_KINDS.AGENT_TASK, "Built-in agents and tasks registered");
@@ -8020,12 +8581,23 @@ async function main() {
8020
8581
  try {
8021
8582
  const staleDb = getDatabase();
8022
8583
  const staleRows = staleDb.prepare(
8023
- `SELECT id FROM agent_runs WHERE status = 'running'`
8584
+ `SELECT id, task FROM agent_runs WHERE status = 'running'`
8024
8585
  ).all();
8025
8586
  if (staleRows.length > 0) {
8587
+ const completedAt = epochSeconds();
8026
8588
  staleDb.prepare(
8027
8589
  `UPDATE agent_runs SET status = 'failed', completed_at = ?, error = 'Daemon restarted while run was in progress' WHERE status = 'running'`
8028
- ).run(epochSeconds());
8590
+ ).run(completedAt);
8591
+ for (const row of staleRows) {
8592
+ notify(vaultDir, {
8593
+ domain: "agents",
8594
+ type: "agent.task.failure",
8595
+ title: `Task failed: ${row.task ?? "agent run"}`,
8596
+ message: "Daemon restarted while run was in progress",
8597
+ link: `/agent?run=${row.id}`,
8598
+ metadata: { taskName: row.task, runId: row.id, reason: "daemon_restart" }
8599
+ }, config);
8600
+ }
8029
8601
  logger.info(LOG_KINDS.AGENT_RUN, "Cleaned stale running agent runs", {
8030
8602
  count: staleRows.length,
8031
8603
  ids: staleRows.map((r) => r.id)
@@ -8122,39 +8694,59 @@ async function main() {
8122
8694
  let configHash = computeConfigHash(vaultDir);
8123
8695
  server.registerRoute("GET", "/api/config", async () => handleGetConfig(vaultDir));
8124
8696
  server.registerRoute("GET", "/api/symbionts", async () => handleListSymbionts(vaultDir));
8125
- server.registerRoute("PUT", "/api/config", async (req) => {
8126
- const result = await handlePutConfig(vaultDir, req.body);
8127
- if (!result.status || result.status < 400) {
8128
- reconcileConfiguredSymbionts(path22.dirname(vaultDir), vaultDir);
8129
- configHash = computeConfigHash(vaultDir);
8130
- }
8131
- return result;
8132
- });
8697
+ server.registerRoute("GET", "/api/config/merged", async () => handleGetMergedConfig(vaultDir));
8698
+ server.registerRoute("GET", "/api/config/local", async () => handleGetLocalConfig(vaultDir));
8133
8699
  const symbiontPlanDirsByAgent = {};
8134
8700
  for (const m of manifests) {
8135
8701
  const dirs = m.capture?.planDirs ?? [];
8136
8702
  if (dirs.length > 0) symbiontPlanDirsByAgent[m.displayName] = dirs;
8137
8703
  }
8138
- const planDirHandlers = createPlanDirHandlers({
8139
- vaultDir,
8140
- symbiontPlanDirsByAgent,
8704
+ const reactions = createConfigReactionRegistry(logger);
8705
+ reactions.on([], () => {
8706
+ configHash = computeConfigHash(vaultDir);
8707
+ });
8708
+ reactions.on(["capture", "symbionts"], (ctx) => {
8709
+ reconcileConfiguredSymbionts(path22.dirname(vaultDir), vaultDir, ctx);
8710
+ });
8711
+ reactions.on(["capture"], createPlanWatchReaction({
8141
8712
  symbiontPlanDirs,
8142
- planWatchConfig,
8143
- setPlanWatchConfig: (cfg) => {
8144
- planWatchConfig = cfg;
8145
- },
8146
- reconcileProjectFiles: () => {
8147
- reconcileConfiguredSymbionts(path22.dirname(vaultDir), vaultDir);
8713
+ planWatchConfig
8714
+ }));
8715
+ reactions.on(["daemon.log_level"], (ctx) => {
8716
+ logger.setLevel(ctx.daemon.log_level);
8717
+ if (ctx.daemon.log_level === "debug") {
8718
+ process.env.MYCO_AGENT_DEBUG = "1";
8719
+ } else {
8720
+ delete process.env.MYCO_AGENT_DEBUG;
8148
8721
  }
8149
8722
  });
8150
- server.registerRoute("GET", "/api/config/plan-dirs", planDirHandlers.handleGetPlanDirs);
8151
- server.registerRoute("POST", "/api/config/plan-dirs", async (req) => {
8152
- const result = await planDirHandlers.handleUpdatePlanDirs(req);
8723
+ server.registerRoute("PUT", "/api/config/scoped", async (req) => {
8724
+ const result = await handlePutScopedConfig(vaultDir, req.body);
8153
8725
  if (!result.status || result.status < 400) {
8154
- configHash = computeConfigHash(vaultDir);
8726
+ const body = req.body;
8727
+ const touchedPaths = computeTouchedPaths(body.patch, body.clear);
8728
+ const reactionContext = loadReactionContext(vaultDir, logger);
8729
+ if (reactionContext) {
8730
+ await reactions.fire(touchedPaths, reactionContext);
8731
+ const summary = buildScopedConfigSaveNotification(body.scope, touchedPaths);
8732
+ notify(vaultDir, {
8733
+ domain: "settings",
8734
+ type: "settings.saved",
8735
+ title: summary.title,
8736
+ message: summary.message,
8737
+ link: summary.link ?? void 0,
8738
+ metadata: summary.metadata
8739
+ }, reactionContext);
8740
+ } else {
8741
+ configHash = computeConfigHash(vaultDir);
8742
+ }
8155
8743
  }
8156
8744
  return result;
8157
8745
  });
8746
+ const planDirHandlers = createPlanDirHandlers({
8747
+ symbiontPlanDirsByAgent
8748
+ });
8749
+ server.registerRoute("GET", "/api/config/plan-dirs", planDirHandlers.handleGetPlanDirs);
8158
8750
  const configHashRef = { get: () => configHash };
8159
8751
  server.registerRoute("GET", "/api/stats", createLiveStatsHandler({
8160
8752
  vaultDir,
@@ -8206,6 +8798,7 @@ async function main() {
8206
8798
  server.registerRoute("GET", "/api/spores", handleListSpores);
8207
8799
  server.registerRoute("GET", "/api/spores/:id", handleGetSpore);
8208
8800
  server.registerRoute("GET", "/api/entities", handleListEntities);
8801
+ server.registerRoute("GET", "/api/graph/seeds", handleGetGraphSeeds);
8209
8802
  server.registerRoute("GET", "/api/graph", handleGetFullGraph);
8210
8803
  server.registerRoute("GET", "/api/graph/:id", handleGetGraph);
8211
8804
  server.registerRoute("GET", "/api/digest", handleGetDigest);
@@ -8231,6 +8824,7 @@ async function main() {
8231
8824
  const mcpProxy = createMcpProxyHandlers({ machineId, embeddingManager });
8232
8825
  server.registerRoute("POST", "/api/mcp/remember", mcpProxy.handleRemember);
8233
8826
  server.registerRoute("POST", "/api/mcp/supersede", mcpProxy.handleSupersede);
8827
+ server.registerRoute("POST", "/api/mcp/consolidate", mcpProxy.handleConsolidate);
8234
8828
  server.registerRoute("GET", "/api/mcp/plans", mcpProxy.handlePlans);
8235
8829
  server.registerRoute("GET", "/api/mcp/sessions", mcpProxy.handleSessions);
8236
8830
  server.registerRoute("GET", "/api/mcp/team", mcpProxy.handleTeam);
@@ -8339,4 +8933,4 @@ export {
8339
8933
  handleUserPrompt,
8340
8934
  main
8341
8935
  };
8342
- //# sourceMappingURL=main-R5ZD5OIZ.js.map
8936
+ //# sourceMappingURL=main-5S4MDCIO.js.map