@askexenow/exe-os 0.9.166 → 0.9.167

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 (244) hide show
  1. package/deploy/compose/backup.sh +45 -7
  2. package/deploy/compose/setup.sh +7 -0
  3. package/deploy/stack-manifests/v0.9.json +40 -1
  4. package/dist/{active-agent-R2KMWMR6.js → active-agent-DGTIJN2U.js} +2 -2
  5. package/dist/{active-agent-CYMM3QQA.js → active-agent-HVMLG6FH.js} +2 -2
  6. package/dist/{agentic-ontology-GKAKYNPE.js → agentic-ontology-S54AFODT.js} +1 -1
  7. package/dist/{backfill-metadata-Z5SYUWAV.js → backfill-metadata-74IWETRF.js} +4 -3
  8. package/dist/{behaviors-QGU6XI5R.js → behaviors-LZVAVHTC.js} +2 -2
  9. package/dist/bin/agentic-ontology-backfill.js +5 -4
  10. package/dist/bin/agentic-reflection-backfill.js +6 -5
  11. package/dist/bin/agentic-semantic-label.js +5 -4
  12. package/dist/bin/backfill-conversations.js +5 -4
  13. package/dist/bin/backfill-responses.js +5 -4
  14. package/dist/bin/backfill-vectors.js +6 -5
  15. package/dist/bin/bulk-sync-postgres.js +6 -5
  16. package/dist/bin/cleanup-stale-review-tasks.js +9 -9
  17. package/dist/bin/cli.js +16 -13
  18. package/dist/bin/daily-summary.js +0 -217
  19. package/dist/bin/deferred-daemon-restart.js +8 -0
  20. package/dist/bin/exe-agent-config.js +1 -1
  21. package/dist/bin/exe-agent.js +10 -10
  22. package/dist/bin/exe-assign.js +7 -6
  23. package/dist/bin/exe-boot.js +20 -19
  24. package/dist/bin/exe-call.js +4 -4
  25. package/dist/bin/exe-cloud.js +3 -3
  26. package/dist/bin/exe-dispatch.js +9 -9
  27. package/dist/bin/exe-doctor.js +1 -1
  28. package/dist/bin/exe-export-behaviors.js +7 -6
  29. package/dist/bin/exe-forget.js +6 -5
  30. package/dist/bin/exe-gateway.js +5 -5
  31. package/dist/bin/exe-heartbeat.js +9 -9
  32. package/dist/bin/exe-kill.js +13 -12
  33. package/dist/bin/exe-launch-agent.js +11 -10
  34. package/dist/bin/exe-new-employee.js +6 -6
  35. package/dist/bin/exe-pending-messages.js +10 -10
  36. package/dist/bin/exe-pending-notifications.js +9 -9
  37. package/dist/bin/exe-pending-reviews.js +9 -9
  38. package/dist/bin/exe-rename.js +4 -4
  39. package/dist/bin/exe-review.js +12 -11
  40. package/dist/bin/exe-search.js +5 -4
  41. package/dist/bin/exe-session-cleanup.js +19 -14
  42. package/dist/bin/exe-settings.js +3 -3
  43. package/dist/bin/exe-start-codex.js +11 -10
  44. package/dist/bin/exe-start-opencode.js +8 -7
  45. package/dist/bin/exe-status.js +10 -10
  46. package/dist/bin/exe-team.js +2 -2
  47. package/dist/bin/git-sweep.js +9 -9
  48. package/dist/bin/graph-backfill.js +4 -3
  49. package/dist/bin/graph-export.js +5 -4
  50. package/dist/bin/import-history.js +171 -0
  51. package/dist/bin/install-launchd.js +41 -0
  52. package/dist/bin/install.js +50 -74
  53. package/dist/bin/intercom-check.js +4 -4
  54. package/dist/bin/postgres-agentic-reflection-backfill.js +2 -2
  55. package/dist/bin/postgres-agentic-semantic-backfill.js +4 -4
  56. package/dist/bin/pre-publish.js +1 -1
  57. package/dist/bin/scan-tasks.js +22 -12
  58. package/dist/bin/setup.js +1 -1
  59. package/dist/bin/shard-migrate.js +4 -3
  60. package/dist/bin/stack-update.js +61 -857
  61. package/dist/bin/vps-backup.js +170 -0
  62. package/dist/bin/vps-health-gate.js +232 -0
  63. package/dist/{capacity-monitor-ZEAE4WP2.js → capacity-monitor-JBZB2S4P.js} +10 -10
  64. package/dist/{catchup-brief-OGWCHENC.js → catchup-brief-HE2EMZS5.js} +12 -11
  65. package/dist/{chunk-DJJNB47C.js → chunk-27DO3EZO.js} +1 -1
  66. package/dist/{chunk-45FYZIHI.js → chunk-32YUET3Y.js} +2 -2
  67. package/dist/{chunk-Y75ECPO5.js → chunk-3FW5LUGI.js} +2 -2
  68. package/dist/{chunk-4OZGQZ4U.js → chunk-3M3O56VT.js} +636 -179
  69. package/dist/{chunk-77WQOD6J.js → chunk-4CXUZ4NI.js} +2 -2
  70. package/dist/{chunk-PBXWPHEK.js → chunk-4VEHJZ6R.js} +1 -1
  71. package/dist/{chunk-TH22QIEC.js → chunk-6A4COFDG.js} +1 -1
  72. package/dist/{chunk-ACBTCC2L.js → chunk-7OJH2A6I.js} +1 -1
  73. package/dist/{chunk-NHCOTCI6.js → chunk-A7SGEBXJ.js} +2 -2
  74. package/dist/{chunk-5MPQSNZF.js → chunk-AUTCT6AY.js} +1 -1
  75. package/dist/{chunk-OEKSTOTE.js → chunk-AZAZ2C75.js} +1 -1
  76. package/dist/chunk-CHCA3ZM2.js +167 -0
  77. package/dist/{chunk-X347L57O.js → chunk-CSTJQDOE.js} +4 -3
  78. package/dist/{chunk-B234R3VW.js → chunk-D7WLV6WD.js} +2 -2
  79. package/dist/{chunk-GMXF3AHJ.js → chunk-DGAONW36.js} +1 -1
  80. package/dist/chunk-EAT5YL3W.js +229 -0
  81. package/dist/{chunk-OD4H5YCJ.js → chunk-EKTQE2R5.js} +8 -8
  82. package/dist/{chunk-Z44PC42G.js → chunk-ELUBA7XL.js} +2 -2
  83. package/dist/{chunk-ZWS6XQER.js → chunk-F5AKOE4P.js} +7 -7
  84. package/dist/{chunk-T5YULDDO.js → chunk-FVI4UBKO.js} +27 -4
  85. package/dist/{chunk-ESRI7MFI.js → chunk-GAN7PW6G.js} +28 -24
  86. package/dist/{chunk-K4OWYJSP.js → chunk-GM2WZTG3.js} +2 -2
  87. package/dist/{chunk-TAB5QGIK.js → chunk-GZYQTPTF.js} +3 -3
  88. package/dist/{chunk-CXDU5DE3.js → chunk-IAUNGATJ.js} +1 -1
  89. package/dist/{chunk-YS63NS6M.js → chunk-IHSM5GR4.js} +1 -1
  90. package/dist/{chunk-23PTS2ZD.js → chunk-IP7KJAUW.js} +117 -15
  91. package/dist/{chunk-D6IMJAV2.js → chunk-J64P2LB2.js} +2 -2
  92. package/dist/{chunk-CXAVSQZM.js → chunk-JXMSCKRM.js} +1 -1
  93. package/dist/{chunk-RQMK3IQH.js → chunk-K4OTJP6N.js} +14 -7
  94. package/dist/{chunk-L7ROZR2H.js → chunk-KXAUMIOX.js} +1 -1
  95. package/dist/{chunk-TPC3LAP7.js → chunk-LGY2BIOT.js} +13 -0
  96. package/dist/{chunk-RPIDSBK7.js → chunk-LLHRJEE4.js} +3 -3
  97. package/dist/{chunk-6WG2VIKC.js → chunk-LM7H6XU4.js} +1 -1
  98. package/dist/{chunk-Y6GMKZZ2.js → chunk-LOFFGJSY.js} +150 -23
  99. package/dist/{chunk-W7SDGBEC.js → chunk-MFI5OXYW.js} +52 -84
  100. package/dist/{chunk-KNPEVPYG.js → chunk-MSSQWF6X.js} +2 -2
  101. package/dist/{chunk-QIQAO3VG.js → chunk-NEFFFKMD.js} +3 -3
  102. package/dist/{chunk-YUC552KZ.js → chunk-NEHONJJC.js} +3 -3
  103. package/dist/{chunk-KZ7SXZ2V.js → chunk-NFMQRLCD.js} +1 -1
  104. package/dist/{chunk-52HCNDPG.js → chunk-O4TATDOV.js} +1 -1
  105. package/dist/{chunk-AR3OYGLB.js → chunk-PEFBRL4S.js} +28 -6
  106. package/dist/{chunk-AEUXUEJG.js → chunk-PEXVU3HU.js} +5 -3
  107. package/dist/chunk-Q2G5C3HV.js +217 -0
  108. package/dist/{chunk-KOO56JVC.js → chunk-Q6N6LDEJ.js} +1 -1
  109. package/dist/{chunk-TXSJ2L5O.js → chunk-QI4IXJN7.js} +1 -1
  110. package/dist/{chunk-HLVQ5Y7B.js → chunk-RE4VLK45.js} +1 -1
  111. package/dist/{chunk-TF6SZGDT.js → chunk-SA2PH6WY.js} +1 -1
  112. package/dist/{chunk-5RSYY7BE.js → chunk-SJYOPYXH.js} +117 -9
  113. package/dist/{chunk-PJGHBANY.js → chunk-TTJE7CCU.js} +1 -1
  114. package/dist/{chunk-A7KEWR6S.js → chunk-TXWQPL2U.js} +1 -1
  115. package/dist/{chunk-XXSJ35J5.js → chunk-U5ZH52FB.js} +2 -2
  116. package/dist/{chunk-G4FDG3LK.js → chunk-UVNDLF74.js} +63 -40
  117. package/dist/{chunk-5OD3AFRW.js → chunk-V6RCZ25F.js} +1 -1
  118. package/dist/{chunk-LHMBIFKD.js → chunk-VYNNN2S3.js} +4 -4
  119. package/dist/chunk-WCYT54XP.js +934 -0
  120. package/dist/{chunk-5AMSQRHT.js → chunk-XGYSTVUH.js} +1 -1
  121. package/dist/{chunk-MKZBHM6A.js → chunk-XLWF3C4R.js} +4 -4
  122. package/dist/{chunk-YL36L2SN.js → chunk-Y7YHLV57.js} +1 -1
  123. package/dist/{chunk-HZC4MR4H.js → chunk-YBKB2PXY.js} +1 -1
  124. package/dist/{chunk-NWM3A4TK.js → chunk-ZDNLKXZA.js} +1 -1
  125. package/dist/{chunk-O7KW6QMH.js → chunk-ZW4TKQUM.js} +15 -5
  126. package/dist/{chunk-6BURHBE6.js → chunk-ZXB44R3E.js} +32 -11
  127. package/dist/co-occurrence-WCED475N.js +73 -0
  128. package/dist/{code-context-index-B6VIWPSF.js → code-context-index-LSZ3DKTJ.js} +2 -2
  129. package/dist/{crdt-sync-XA22KI3S.js → crdt-sync-PBXZTHZC.js} +1 -1
  130. package/dist/{crm-webhook-CIZNOEY4.js → crm-webhook-W7Q25VZU.js} +2 -2
  131. package/dist/{cto-delegation-gate-H5IULFRC.js → cto-delegation-gate-JKULOLMC.js} +8 -8
  132. package/dist/{daemon-orchestration-VO5XQIJL.js → daemon-orchestration-CHV6MB42.js} +13 -11
  133. package/dist/{exe-drift-DMT75WR3.js → exe-drift-PW36OULT.js} +2 -2
  134. package/dist/{exe-export-2RZWOSX6.js → exe-export-XQOD3KE6.js} +6 -5
  135. package/dist/{exe-import-NFNYATHL.js → exe-import-QOFP67LW.js} +6 -5
  136. package/dist/{exe-key-4D7CF3BU.js → exe-key-WQ34UZR6.js} +1 -1
  137. package/dist/{fast-db-init-LAEISZQ2.js → fast-db-init-UKETGWQI.js} +1 -1
  138. package/dist/gateway/index.js +6 -6
  139. package/dist/{git-staleness-M46AYLPP.js → git-staleness-ATV5CGAP.js} +1 -1
  140. package/dist/{git-task-sweep-PXOS56YT.js → git-task-sweep-KXZRIP4T.js} +9 -9
  141. package/dist/{global-procedures-KROQQX54.js → global-procedures-G6IKCYKM.js} +3 -3
  142. package/dist/{graph-auto-extract-QJ2BBJM2.js → graph-auto-extract-ZJXJOLE2.js} +1 -1
  143. package/dist/hooks/bug-report-worker.js +10 -10
  144. package/dist/hooks/codex-stop-task-finalizer.js +10 -10
  145. package/dist/hooks/commit-complete.js +11 -11
  146. package/dist/hooks/error-recall.js +8 -7
  147. package/dist/hooks/exe-heartbeat-hook.js +2 -2
  148. package/dist/hooks/ingest-worker.js +3 -3
  149. package/dist/hooks/ingest.js +9 -9
  150. package/dist/hooks/instructions-loaded.js +3 -3
  151. package/dist/hooks/notification.js +3 -3
  152. package/dist/hooks/post-compact.js +10 -10
  153. package/dist/hooks/post-tool-combined.js +5 -5
  154. package/dist/hooks/pre-compact.js +16 -16
  155. package/dist/hooks/pre-tool-use.js +14 -14
  156. package/dist/hooks/prompt-submit.js +30 -29
  157. package/dist/hooks/session-end.js +46 -25
  158. package/dist/hooks/session-start.js +48 -10
  159. package/dist/hooks/stop.js +17 -17
  160. package/dist/hooks/subagent-stop.js +10 -10
  161. package/dist/hooks/summary-worker.js +17 -16
  162. package/dist/index.js +17 -17
  163. package/dist/{installer-SDBLJBAB.js → installer-DE2LH5EC.js} +4 -4
  164. package/dist/{installer-ZA6QNQ4P.js → installer-M2MDS7HC.js} +4 -4
  165. package/dist/{installer-6KAY6LD6.js → installer-VE23YFXU.js} +4 -4
  166. package/dist/{intercom-queue-K3DVKSPJ.js → intercom-queue-RNM6EPGA.js} +1 -1
  167. package/dist/keyword-extractor-UJHFWVZE.js +11 -0
  168. package/dist/lib/cloud-sync.js +3 -3
  169. package/dist/lib/consolidation.js +5 -4
  170. package/dist/lib/database.js +1 -1
  171. package/dist/lib/db-daemon-client.js +1 -1
  172. package/dist/lib/db.js +1 -1
  173. package/dist/lib/embed-worker.js +98 -0
  174. package/dist/lib/embedder.js +2 -2
  175. package/dist/lib/employee-templates.js +4 -4
  176. package/dist/lib/employees.js +1 -1
  177. package/dist/lib/exe-daemon-client.js +1 -1
  178. package/dist/lib/exe-daemon.js +523 -500
  179. package/dist/lib/hybrid-search.js +5 -6
  180. package/dist/lib/identity.js +1 -1
  181. package/dist/lib/messaging.js +9 -9
  182. package/dist/lib/reminders.js +2 -2
  183. package/dist/lib/schedules.js +5 -4
  184. package/dist/lib/skill-learning.js +3 -3
  185. package/dist/lib/store.js +4 -3
  186. package/dist/lib/task-router.js +2 -2
  187. package/dist/lib/tasks.js +9 -9
  188. package/dist/lib/tmux-routing.js +8 -8
  189. package/dist/lib/tmux-transport.js +1 -1
  190. package/dist/lib/token-spend.js +2 -2
  191. package/dist/lib/transport.js +2 -2
  192. package/dist/lib/ws-client.js +3 -1
  193. package/dist/mcp/register-tools.js +54 -51
  194. package/dist/mcp/server.js +58 -55
  195. package/dist/mcp/tools/complete-reminder.js +3 -3
  196. package/dist/mcp/tools/create-reminder.js +3 -3
  197. package/dist/mcp/tools/create-task.js +11 -11
  198. package/dist/mcp/tools/deactivate-behavior.js +4 -4
  199. package/dist/mcp/tools/list-reminders.js +3 -3
  200. package/dist/mcp/tools/list-tasks.js +11 -11
  201. package/dist/mcp/tools/send-message.js +11 -11
  202. package/dist/mcp/tools/update-task.js +10 -10
  203. package/dist/{mcp-http-config-LK2EDOEJ.js → mcp-http-config-Z2E4VUOF.js} +2 -2
  204. package/dist/{memory-cards-V3DKSRWL.js → memory-cards-SFDKDIAW.js} +1 -1
  205. package/dist/memory-graph-extractor-YD4GNH7T.js +16 -0
  206. package/dist/{memory-poisoning-defense-3B75HS74.js → memory-poisoning-defense-VEGNFELN.js} +1 -1
  207. package/dist/{memory-queue-client-LFPZPPQA.js → memory-queue-client-5HB2XUH7.js} +2 -2
  208. package/dist/{memory-reflection-HTDAUUE5.js → memory-reflection-MTPRQNI6.js} +2 -2
  209. package/dist/{notifications-76VCYXWW.js → notifications-6TCE6OBG.js} +8 -8
  210. package/dist/{orchestrator-CBNSBI5P.js → orchestrator-W2GYJR23.js} +10 -10
  211. package/dist/{plan-limits-SOR3QXKV.js → plan-limits-4EP46323.js} +2 -2
  212. package/dist/{projection-worker-FK5YOEIL.js → projection-worker-EBUYNMU2.js} +1 -1
  213. package/dist/{review-polling-ZLNDUKL4.js → review-polling-2N7KQFZZ.js} +9 -9
  214. package/dist/runtime/index.js +15 -15
  215. package/dist/{session-events-CUSPL25D.js → session-events-K47FHAXJ.js} +9 -9
  216. package/dist/{session-kill-telemetry-FLBRHBDP.js → session-kill-telemetry-275YUXM5.js} +2 -2
  217. package/dist/{session-scope-PX2ABSJO.js → session-scope-XSFJZEER.js} +8 -8
  218. package/dist/{setup-wizard-Y6PBZGFX.js → setup-wizard-UEO7HYLQ.js} +1 -1
  219. package/dist/{skill-refinement-L7PGKCYO.js → skill-refinement-WXBTANDQ.js} +1 -1
  220. package/dist/stack-update-2B2UXREV.js +50 -0
  221. package/dist/{task-enforcement-7FUILB63.js → task-enforcement-2JIJSXPU.js} +14 -16
  222. package/dist/{task-scope-2N45TE32.js → task-scope-W73Z3XWE.js} +8 -8
  223. package/dist/{tasks-crud-ADLCGHGH.js → tasks-crud-HPJKI3QQ.js} +8 -8
  224. package/dist/{tasks-review-PJ2DUI6N.js → tasks-review-MXLMPGNZ.js} +8 -8
  225. package/dist/{token-budget-T5DFXVTM.js → token-budget-BA46CVHX.js} +1 -1
  226. package/dist/{tool-capability-index-6JJN6ZRC.js → tool-capability-index-42VVN5BS.js} +1 -1
  227. package/dist/{tool-telemetry-72PVO5HV.js → tool-telemetry-GZ5E2AUL.js} +1 -1
  228. package/dist/tui/App.js +22 -18
  229. package/dist/{tui-data-63JHE6EZ.js → tui-data-PVXWQCJX.js} +8 -8
  230. package/dist/{worker-gate-REVBJUZ6.js → worker-gate-WTTK64TK.js} +1 -1
  231. package/dist/{workflow-engine-W2WNHJG5.js → workflow-engine-LT3WTT7V.js} +2 -2
  232. package/package.json +1 -1
  233. package/release-notes.json +209 -209
  234. /package/dist/{chunk-BNOZUS6J.js → chunk-6VVCAVRT.js} +0 -0
  235. /package/dist/{chunk-IC7GKK6I.js → chunk-CWQZZ7X3.js} +0 -0
  236. /package/dist/{chunk-ZI2ZVERO.js → chunk-EIW5GOBW.js} +0 -0
  237. /package/dist/{chunk-2BGGDNRD.js → chunk-IPPJEM26.js} +0 -0
  238. /package/dist/{chunk-4ISDU5KR.js → chunk-K5UR73PM.js} +0 -0
  239. /package/dist/{chunk-ZWRTVUQ6.js → chunk-KIMO5S45.js} +0 -0
  240. /package/dist/{chunk-S2FX5KJ4.js → chunk-WBLILGAP.js} +0 -0
  241. /package/dist/{core-memory-PCJ3L46L.js → core-memory-RAC6M67J.js} +0 -0
  242. /package/dist/{entity-boost-GHFPE6A2.js → entity-boost-5FIRFRDC.js} +0 -0
  243. /package/dist/{message-queue-client-CHRQYBH5.js → message-queue-client-PTQ2S7D7.js} +0 -0
  244. /package/dist/{wiki-acl-QYRAYYVQ.js → wiki-acl-MSDRCIAI.js} +0 -0
@@ -1,11 +1,34 @@
1
1
  import {
2
2
  getClient
3
- } from "./chunk-5RSYY7BE.js";
3
+ } from "./chunk-SJYOPYXH.js";
4
4
 
5
5
  // src/lib/session-kill-telemetry.ts
6
6
  import crypto from "crypto";
7
+ import { appendFileSync } from "fs";
8
+ import path from "path";
9
+ import os from "os";
10
+ var KILL_FILE_LOG = path.join(os.homedir(), ".exe-os", "logs", "session-kills.jsonl");
7
11
  var TOKENS_PER_IDLE_MINUTE = 50;
8
12
  async function recordSessionKill(input) {
13
+ const killedAt = (/* @__PURE__ */ new Date()).toISOString();
14
+ const id = crypto.randomUUID();
15
+ try {
16
+ const logEntry = JSON.stringify({
17
+ id,
18
+ timestamp: killedAt,
19
+ session: input.sessionName,
20
+ agent: input.agentId,
21
+ reason: input.reason,
22
+ ticksIdle: input.ticksIdle ?? null,
23
+ tokensSaved: input.estimatedTokensSaved ?? null
24
+ });
25
+ appendFileSync(KILL_FILE_LOG, logEntry + "\n");
26
+ } catch {
27
+ process.stderr.write(
28
+ `[session-kill-telemetry] file log write failed for ${input.sessionName}
29
+ `
30
+ );
31
+ }
9
32
  try {
10
33
  const client = getClient();
11
34
  await client.execute({
@@ -14,10 +37,10 @@ async function recordSessionKill(input) {
14
37
  ticks_idle, estimated_tokens_saved)
15
38
  VALUES (?, ?, ?, ?, ?, ?, ?)`,
16
39
  args: [
17
- crypto.randomUUID(),
40
+ id,
18
41
  input.sessionName,
19
42
  input.agentId,
20
- (/* @__PURE__ */ new Date()).toISOString(),
43
+ killedAt,
21
44
  input.reason,
22
45
  input.ticksIdle ?? null,
23
46
  input.estimatedTokensSaved ?? null
@@ -25,7 +48,7 @@ async function recordSessionKill(input) {
25
48
  });
26
49
  } catch (err) {
27
50
  process.stderr.write(
28
- `[session-kill-telemetry] write failed: ${err instanceof Error ? err.message : String(err)}
51
+ `[session-kill-telemetry] DB write failed: ${err instanceof Error ? err.message : String(err)}
29
52
  `
30
53
  );
31
54
  }
@@ -54,7 +54,7 @@ var ToolCapabilityIndex = class {
54
54
  * @param registerFn - function that registers tools on a server (e.g. registerAllTools)
55
55
  * @param categoryMap - optional map of registerFnName → category (from tool-gates TOOL_CATEGORIES)
56
56
  */
57
- async buildIndex(registerFn, categoryMap) {
57
+ async buildIndex(registerFn, categoryMap, directEmbedFn) {
58
58
  const captured = [];
59
59
  const fakeServer = {
60
60
  registerTool(name, config, _handler) {
@@ -66,35 +66,39 @@ var ToolCapabilityIndex = class {
66
66
  }
67
67
  };
68
68
  registerFn(fakeServer);
69
- let embedFn = null;
70
- try {
71
- const { embed } = await import("./lib/embedder.js");
72
- const test = await embed("test");
73
- if (test.length === EMBEDDING_DIM) {
74
- embedFn = embed;
75
- }
76
- } catch {
77
- }
78
- const capabilities = [];
69
+ const capabilityDocs = [];
79
70
  for (const tool of captured) {
80
71
  const paramSummary = extractParamNames(tool.inputSchema);
81
72
  const category = categoryMap ? categoryForToolName(tool.name, categoryMap) : "unknown";
82
- const capabilityDoc = `${tool.name}: ${tool.description}. Parameters: ${paramSummary}`;
83
- let vector = null;
84
- if (embedFn) {
85
- try {
86
- vector = await embedFn(capabilityDoc);
87
- } catch {
73
+ const doc = `${tool.name}: ${tool.description}. Parameters: ${paramSummary}`;
74
+ capabilityDocs.push({ name: tool.name, description: tool.description, category, paramSummary, doc });
75
+ }
76
+ let vectors = capabilityDocs.map(() => null);
77
+ try {
78
+ if (directEmbedFn) {
79
+ const allVectors = await directEmbedFn(capabilityDocs.map((c) => c.doc));
80
+ vectors = allVectors.map((v) => v.length === EMBEDDING_DIM ? v : null);
81
+ } else {
82
+ const { embed } = await import("./lib/embedder.js");
83
+ const test = await embed("test");
84
+ if (test.length === EMBEDDING_DIM) {
85
+ for (let i = 0; i < capabilityDocs.length; i++) {
86
+ try {
87
+ vectors[i] = await embed(capabilityDocs[i].doc);
88
+ } catch {
89
+ }
90
+ }
88
91
  }
89
92
  }
90
- capabilities.push({
91
- name: tool.name,
92
- description: tool.description,
93
- category,
94
- vector,
95
- paramSummary
96
- });
93
+ } catch {
97
94
  }
95
+ const capabilities = capabilityDocs.map((c, i) => ({
96
+ name: c.name,
97
+ description: c.description,
98
+ category: c.category,
99
+ vector: vectors[i] ?? null,
100
+ paramSummary: c.paramSummary
101
+ }));
98
102
  this.capabilities = capabilities;
99
103
  this.initialized = true;
100
104
  process.stderr.write(
@@ -1,9 +1,9 @@
1
1
  import {
2
2
  storeBehavior
3
- } from "./chunk-PJGHBANY.js";
3
+ } from "./chunk-TTJE7CCU.js";
4
4
  import {
5
5
  getClient
6
- } from "./chunk-5RSYY7BE.js";
6
+ } from "./chunk-SJYOPYXH.js";
7
7
  import {
8
8
  loadConfig
9
9
  } from "./chunk-4GXRETYL.js";
@@ -1,13 +1,13 @@
1
1
  import {
2
2
  deactivateBehavior
3
- } from "./chunk-PJGHBANY.js";
3
+ } from "./chunk-TTJE7CCU.js";
4
4
  import {
5
5
  getActiveAgent
6
- } from "./chunk-6WG2VIKC.js";
6
+ } from "./chunk-LM7H6XU4.js";
7
7
  import {
8
8
  canCoordinate,
9
9
  getClient
10
- } from "./chunk-5RSYY7BE.js";
10
+ } from "./chunk-SJYOPYXH.js";
11
11
 
12
12
  // src/mcp/tools/deactivate-behavior.ts
13
13
  import { z } from "zod";
@@ -1,7 +1,7 @@
1
1
  import {
2
2
  getCurrentSessionScope,
3
3
  strictSessionScopeFilter
4
- } from "./chunk-W7SDGBEC.js";
4
+ } from "./chunk-MFI5OXYW.js";
5
5
  import {
6
6
  getProjectName
7
7
  } from "./chunk-OPU3NYOO.js";
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  loadEmployees
3
- } from "./chunk-5RSYY7BE.js";
3
+ } from "./chunk-SJYOPYXH.js";
4
4
 
5
5
  // src/lib/agent-symlinks.ts
6
6
  import os from "os";
@@ -3,14 +3,13 @@ import {
3
3
  buildRawVisibilityFilter,
4
4
  buildWikiScopeFilter,
5
5
  searchMemories
6
- } from "./chunk-6BURHBE6.js";
6
+ } from "./chunk-ZXB44R3E.js";
7
7
  import {
8
8
  getClient
9
- } from "./chunk-5RSYY7BE.js";
9
+ } from "./chunk-SJYOPYXH.js";
10
10
 
11
11
  // src/lib/hybrid-search.ts
12
12
  var RRF_K = 60;
13
- var lastSearchDegraded = false;
14
13
  var _cardinalityCache = /* @__PURE__ */ new Map();
15
14
  var CARDINALITY_TTL_MS = 6e4;
16
15
  async function getCachedCardinality(agentId) {
@@ -49,6 +48,76 @@ function appendMemoryTypeFilter(sql, args, column, options) {
49
48
  }
50
49
  return sql;
51
50
  }
51
+ async function graphSearch(query, agentId, _options, limit) {
52
+ const client = getClient();
53
+ const queryWords = query.toLowerCase().split(/\s+/).filter((w) => w.length >= 3).map((w) => w.replace(/[^a-z0-9_-]/g, "")).filter((w) => w.length >= 3);
54
+ if (queryWords.length === 0) return [];
55
+ let entityIds = [];
56
+ try {
57
+ const matchExpr = queryWords.map((w) => `${w}*`).join(" OR ");
58
+ const ftsResult = await client.execute({
59
+ sql: `SELECT e.id FROM entities e
60
+ JOIN entities_fts fts ON e.rowid = fts.rowid
61
+ WHERE entities_fts MATCH ?
62
+ ORDER BY rank LIMIT 10`,
63
+ args: [matchExpr]
64
+ });
65
+ entityIds = ftsResult.rows.map((r) => String(r.id));
66
+ } catch {
67
+ try {
68
+ const conditions = queryWords.map(() => `LOWER(name) LIKE ?`);
69
+ const args = queryWords.map((w) => `%${w}%`);
70
+ const likeResult = await client.execute({
71
+ sql: `SELECT id FROM entities WHERE ${conditions.join(" OR ")} LIMIT 10`,
72
+ args: [...args]
73
+ });
74
+ entityIds = likeResult.rows.map((r) => String(r.id));
75
+ } catch {
76
+ return [];
77
+ }
78
+ }
79
+ if (entityIds.length === 0) return [];
80
+ const allEntityIds = new Set(entityIds);
81
+ try {
82
+ const placeholders2 = entityIds.map(() => "?").join(",");
83
+ const neighborResult = await client.execute({
84
+ sql: `SELECT DISTINCT target_entity_id FROM relationships
85
+ WHERE source_entity_id IN (${placeholders2})
86
+ UNION
87
+ SELECT DISTINCT source_entity_id FROM relationships
88
+ WHERE target_entity_id IN (${placeholders2})
89
+ LIMIT 30`,
90
+ args: [...entityIds, ...entityIds]
91
+ });
92
+ for (const row of neighborResult.rows) {
93
+ allEntityIds.add(String(row.target_entity_id ?? row.source_entity_id));
94
+ }
95
+ } catch {
96
+ }
97
+ const entityIdArr = Array.from(allEntityIds);
98
+ const placeholders = entityIdArr.map(() => "?").join(",");
99
+ try {
100
+ const memResult = await client.execute({
101
+ sql: `SELECT DISTINCT m.id, m.agent_id, m.agent_role, m.session_id, m.timestamp,
102
+ m.tool_name, m.project_name, m.has_error, m.raw_text, m.vector,
103
+ m.task_id, m.importance, m.status, m.confidence, m.last_accessed,
104
+ m.workspace_id, m.document_id, m.user_id, m.char_offset,
105
+ m.page_number, m.source_path, m.source_type, m.memory_type, m.strength
106
+ FROM memories m
107
+ JOIN entity_memories em ON m.id = em.memory_id
108
+ WHERE em.entity_id IN (${placeholders})
109
+ AND (m.agent_id = ? OR m.agent_id = 'wiki')
110
+ AND COALESCE(m.status, 'active') = 'active'
111
+ AND COALESCE(m.confidence, 0.7) >= 0.3
112
+ ORDER BY m.importance DESC, m.timestamp DESC
113
+ LIMIT ?`,
114
+ args: [...entityIdArr, agentId, limit]
115
+ });
116
+ return memResult.rows.map((row) => rowToMemoryRecord(row));
117
+ } catch {
118
+ return [];
119
+ }
120
+ }
52
121
  function extractEntitySubqueries(query) {
53
122
  const subqueries = [];
54
123
  const quoted = query.match(/"([^"]+)"/g);
@@ -174,9 +243,7 @@ async function hybridSearch(queryText, agentId, options) {
174
243
  try {
175
244
  const { embed } = await import("./lib/embedder.js");
176
245
  queryVector = await embed(effectiveQuery);
177
- lastSearchDegraded = false;
178
246
  } catch {
179
- lastSearchDegraded = true;
180
247
  if (!process.env.VITEST) {
181
248
  process.stderr.write("[hybrid-search] Embed daemon unavailable \u2014 FTS-only mode\n");
182
249
  }
@@ -203,12 +270,18 @@ async function hybridSearch(queryText, agentId, options) {
203
270
  (sq) => lightweightSearch(sq, agentId, { ...fetchOptions, limit: Math.min(fetchLimit, 20) }).catch(() => [])
204
271
  );
205
272
  const includeStructuredCards = effectiveIsBroad || effectiveOptions.includeStructuredCards === true;
206
- const [ftsResults, vectorResults, cardResults, reflectionResults, grepResults, ...subqueryResults] = await Promise.all([
273
+ const [ftsResults, vectorResults, graphResults, cardResults, reflectionResults, grepResults, ...subqueryResults] = await Promise.all([
207
274
  lightweightSearch(effectiveQuery, agentId, fetchOptions),
208
275
  queryVector ? searchMemories(queryVector, agentId, fetchOptions) : Promise.resolve([]),
276
+ // Graph search: first-class parallel signal via entity → memory linkage.
277
+ // Non-blocking with 2s timeout — graph is a bonus, not a requirement.
278
+ Promise.race([
279
+ graphSearch(effectiveQuery, agentId, fetchOptions, Math.min(fetchLimit, 20)),
280
+ new Promise((resolve) => setTimeout(() => resolve([]), 2e3))
281
+ ]).catch(() => []),
209
282
  includeStructuredCards ? (async () => {
210
283
  try {
211
- const { searchMemoryCards } = await import("./memory-cards-V3DKSRWL.js");
284
+ const { searchMemoryCards } = await import("./memory-cards-SFDKDIAW.js");
212
285
  return await searchMemoryCards(effectiveQuery, agentId, fetchOptions);
213
286
  } catch {
214
287
  return [];
@@ -217,7 +290,7 @@ async function hybridSearch(queryText, agentId, options) {
217
290
  // Reflection insights: patterns, contradictions, summaries across sessions
218
291
  includeStructuredCards ? (async () => {
219
292
  try {
220
- const { searchReflections } = await import("./memory-reflection-HTDAUUE5.js");
293
+ const { searchReflections } = await import("./memory-reflection-MTPRQNI6.js");
221
294
  const insights = await searchReflections(effectiveQuery, agentId, 5);
222
295
  return insights.map((ins) => ({
223
296
  id: ins.id,
@@ -235,6 +308,24 @@ async function hybridSearch(queryText, agentId, options) {
235
308
  grepPromise,
236
309
  ...subqueryPromises
237
310
  ]);
311
+ for (const r of ftsResults) {
312
+ r._source = "fts";
313
+ }
314
+ for (const r of vectorResults) {
315
+ r._source = "embed";
316
+ }
317
+ for (const r of graphResults) {
318
+ r._source = "graph";
319
+ }
320
+ for (const r of cardResults) {
321
+ r._source = "card";
322
+ }
323
+ for (const r of reflectionResults) {
324
+ r._source = "reflection";
325
+ }
326
+ for (const r of grepResults) {
327
+ r._source = "grep";
328
+ }
238
329
  const lists = [];
239
330
  const weights = [];
240
331
  if (ftsResults.length > 0) {
@@ -245,6 +336,10 @@ async function hybridSearch(queryText, agentId, options) {
245
336
  lists.push(vectorResults);
246
337
  weights.push(1);
247
338
  }
339
+ if (graphResults.length > 0) {
340
+ lists.push(graphResults);
341
+ weights.push(0.9);
342
+ }
248
343
  if (reflectionResults.length > 0) {
249
344
  lists.push(reflectionResults);
250
345
  weights.push(0.65);
@@ -271,7 +366,7 @@ async function hybridSearch(queryText, agentId, options) {
271
366
  let entityBoostRan = false;
272
367
  if (merged.length > 0) {
273
368
  try {
274
- const { applyEntityBoost } = await import("./entity-boost-GHFPE6A2.js");
369
+ const { applyEntityBoost } = await import("./entity-boost-5FIRFRDC.js");
275
370
  const boosted = await applyEntityBoost(merged, effectiveQuery, getClient());
276
371
  merged = boosted.results;
277
372
  graphContextMap = boosted.graphContext;
@@ -340,6 +435,7 @@ async function hybridSearch(queryText, agentId, options) {
340
435
  signals: {
341
436
  fts: ftsResults.length,
342
437
  vector: vectorResults.length,
438
+ graph: graphResults.length,
343
439
  cards: cardResults.length,
344
440
  reflections: reflectionResults.length,
345
441
  grep: grepResults.length,
@@ -472,11 +568,17 @@ function rrfMergeMulti(lists, limit, k = RRF_K, weights) {
472
568
  const weight = weights?.[listIdx] ?? 1;
473
569
  for (let i = 0; i < list.length; i++) {
474
570
  const rec = list[i];
475
- const entry = scores.get(rec.id) ?? { rrfScore: 0, record: rec };
571
+ const entry = scores.get(rec.id) ?? { rrfScore: 0, record: rec, sources: /* @__PURE__ */ new Set() };
476
572
  entry.rrfScore += weight * (1 / (k + i + 1));
573
+ if (rec._source) entry.sources.add(rec._source);
477
574
  scores.set(rec.id, entry);
478
575
  }
479
576
  }
577
+ for (const entry of scores.values()) {
578
+ if (entry.sources.size > 0) {
579
+ entry.record._source = Array.from(entry.sources).sort().join("+");
580
+ }
581
+ }
480
582
  const entries = Array.from(scores.values()).map((e) => {
481
583
  const recency = recencyScore(e.record.timestamp);
482
584
  const importance = normalizedImportance(e.record.importance);
@@ -593,10 +695,11 @@ async function lightweightSearch(queryText, agentId, options) {
593
695
  }
594
696
  const prefixTerms = terms.map((t) => `${t}*`);
595
697
  const useAnd = terms.length >= 3;
596
- const matchExpr = useAnd ? prefixTerms.join(" AND ") : prefixTerms.join(" OR ");
698
+ const innerExpr = useAnd ? prefixTerms.join(" AND ") : prefixTerms.join(" OR ");
699
+ const matchExpr = `{raw_text keywords}: ${innerExpr}`;
597
700
  const results = await ftsQuery(client, matchExpr, agentId, options, limit);
598
701
  if (useAnd && results.length < limit) {
599
- const orExpr = prefixTerms.join(" OR ");
702
+ const orExpr = `{raw_text keywords}: ${prefixTerms.join(" OR ")}`;
600
703
  const orResults = await ftsQuery(client, orExpr, agentId, options, limit);
601
704
  const seen = new Set(results.map((r) => r.id));
602
705
  for (const r of orResults) {
@@ -611,7 +714,7 @@ async function lightweightSearch(queryText, agentId, options) {
611
714
  }
612
715
  if (options?.includeStructuredCards !== true) return results;
613
716
  try {
614
- const { searchMemoryCards } = await import("./memory-cards-V3DKSRWL.js");
717
+ const { searchMemoryCards } = await import("./memory-cards-SFDKDIAW.js");
615
718
  const cardResults = await searchMemoryCards(queryText, agentId, options);
616
719
  if (cardResults.length > 0) {
617
720
  return rrfMergeMulti([results, cardResults], limit, RRF_K, [1, 0.85]);
@@ -672,7 +775,7 @@ async function ftsQuery(client, matchExpr, agentId, options, limit) {
672
775
  sql += ` AND (m.session_scope = ? OR m.session_scope IS NULL)`;
673
776
  args.push(options.sessionScope);
674
777
  }
675
- sql += ` ORDER BY rank LIMIT ?`;
778
+ sql += ` ORDER BY bm25(memories_fts, 1.0, 3.0) LIMIT ?`;
676
779
  args.push(limit);
677
780
  let result;
678
781
  try {
@@ -969,7 +1072,6 @@ async function trajectoryBypass(queryText, agentId, options, limit) {
969
1072
  }
970
1073
 
971
1074
  export {
972
- lastSearchDegraded,
973
1075
  hybridSearch,
974
1076
  estimateCardinality,
975
1077
  rrfMerge,
@@ -1,10 +1,10 @@
1
1
  import {
2
2
  initStore
3
- } from "./chunk-6BURHBE6.js";
3
+ } from "./chunk-ZXB44R3E.js";
4
4
  import {
5
5
  getClient,
6
6
  isInitialized
7
- } from "./chunk-5RSYY7BE.js";
7
+ } from "./chunk-SJYOPYXH.js";
8
8
 
9
9
  // src/lib/schedules.ts
10
10
  import crypto from "crypto";
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  completeReminder
3
- } from "./chunk-TH22QIEC.js";
3
+ } from "./chunk-6A4COFDG.js";
4
4
 
5
5
  // src/mcp/tools/complete-reminder.ts
6
6
  import { z } from "zod";
@@ -1,9 +1,13 @@
1
1
  import {
2
2
  vectorToBlob
3
- } from "./chunk-6BURHBE6.js";
3
+ } from "./chunk-ZXB44R3E.js";
4
+ import {
5
+ extractKeywords,
6
+ keywordsToString
7
+ } from "./chunk-CHCA3ZM2.js";
4
8
  import {
5
9
  isCoordinatorName
6
- } from "./chunk-5RSYY7BE.js";
10
+ } from "./chunk-SJYOPYXH.js";
7
11
 
8
12
  // src/lib/consolidation.ts
9
13
  import { randomUUID } from "crypto";
@@ -131,6 +135,8 @@ ${snippets}
131
135
 
132
136
  ${rolePrompt}
133
137
 
138
+ IMPORTANT: Preserve all specific names, file paths, technical terms, and proper nouns exactly as they appear. Front-load the most important terms in the first sentence of your summary. Never replace specific terms with generic descriptions (e.g. write "hybrid-search.ts" not "the search file", write "extractKeywords" not "the extraction function").
139
+
134
140
  Format each as a single sentence. Be specific \u2014 include file names,
135
141
  function names, and concrete details. Skip if no insight for a category.`;
136
142
  }
@@ -162,14 +168,15 @@ ${synthesisText}`;
162
168
  const memoryType = dominantMemoryType(cluster.memories);
163
169
  const scopes = new Set(cluster.memories.map((m) => m.session_scope ?? null));
164
170
  const sessionScope = scopes.size === 1 ? cluster.memories[0]?.session_scope ?? null : null;
171
+ const keywords = keywordsToString(extractKeywords(rawText));
165
172
  const insertSql = vector ? `INSERT INTO memories
166
173
  (id, agent_id, agent_role, session_id, timestamp,
167
- tool_name, project_name, has_error, raw_text, vector, version, consolidated, importance, memory_type, session_scope)
168
- VALUES (?, ?, 'consolidation', 'daemon-consolidation', ?, 'consolidation', ?, 0, ?, vector32(?), 0, 1, 9, ?, ?)` : `INSERT INTO memories
174
+ tool_name, project_name, has_error, raw_text, vector, version, consolidated, importance, memory_type, session_scope, keywords)
175
+ VALUES (?, ?, 'consolidation', 'daemon-consolidation', ?, 'consolidation', ?, 0, ?, vector32(?), 0, 1, 9, ?, ?, ?)` : `INSERT INTO memories
169
176
  (id, agent_id, agent_role, session_id, timestamp,
170
- tool_name, project_name, has_error, raw_text, vector, version, consolidated, importance, memory_type, session_scope)
171
- VALUES (?, ?, 'consolidation', 'daemon-consolidation', ?, 'consolidation', ?, 0, ?, NULL, 0, 1, 9, ?, ?)`;
172
- const insertArgs = vector ? [consolidatedId, cluster.agentId, now, cluster.projectName, rawText, vectorToBlob(vector), memoryType, sessionScope] : [consolidatedId, cluster.agentId, now, cluster.projectName, rawText, memoryType, sessionScope];
177
+ tool_name, project_name, has_error, raw_text, vector, version, consolidated, importance, memory_type, session_scope, keywords)
178
+ VALUES (?, ?, 'consolidation', 'daemon-consolidation', ?, 'consolidation', ?, 0, ?, NULL, 0, 1, 9, ?, ?, ?)`;
179
+ const insertArgs = vector ? [consolidatedId, cluster.agentId, now, cluster.projectName, rawText, vectorToBlob(vector), memoryType, sessionScope, keywords] : [consolidatedId, cluster.agentId, now, cluster.projectName, rawText, memoryType, sessionScope, keywords];
173
180
  await client.execute({ sql: insertSql, args: insertArgs });
174
181
  const sourceIds = cluster.memories.map((m) => m.id);
175
182
  const linkStmts = sourceIds.map((sourceId) => ({
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  loadEmployeesSync
3
- } from "./chunk-5RSYY7BE.js";
3
+ } from "./chunk-SJYOPYXH.js";
4
4
 
5
5
  // src/adapters/mcp-http-config.ts
6
6
  import { chmodSync, existsSync, mkdirSync, readFileSync, writeFileSync } from "fs";
@@ -193,6 +193,13 @@ var PLATFORM_PROCEDURES = [
193
193
  priority: "p1",
194
194
  content: "Fresh install: `npm install -g @askexenow/exe-os` then run `exe` to start the setup wizard. The wizard prompts for: encryption passphrase (creates master key), license key (exe_sk_* from AskExe team), COO name, and optional team members. No license key = free tier (1 employee, 5K memories). After setup: hooks install automatically, MCP server registers in ~/.claude.json, daemon starts. Verify health: run `exe-os healthcheck` or use mcp_ping() tool."
195
195
  },
196
+ // --- Observability ---
197
+ {
198
+ title: "Daemon logs and session lifecycle \u2014 full transparency for debugging",
199
+ domain: "operations",
200
+ priority: "p1",
201
+ content: "The exe-os daemon logs EVERYTHING to ~/.exe-os/logs/exed-launchd.log. This is your primary debugging tool. What you can see: (1) Session spawns \u2014 when and why each employee session started. (2) Idle kill decisions \u2014 which sessions were killed, why, how many idle ticks elapsed. (3) Graceful shutdown \u2014 agents get a 90-second warning before idle kill to store memories and checkpoint. (4) Event loop health \u2014 if the daemon blocks >3s, it logs a warning; >10s logs CRITICAL with duration. (5) Task enforcement \u2014 every 60s, logs each agent's state (open tasks, pane idle/active, action taken). (6) Intercom delivery \u2014 every message sent/queued/failed with timestamps and reasons. (7) MCP sessions \u2014 connections, disconnections, duplicate evictions, session cap events. (8) Cloud sync \u2014 push/pull counts, errors, version conflicts. To read logs: `tail -100 ~/.exe-os/logs/exed-launchd.log` or use /exe-doctor which checks logs automatically. Enforcement audit trail: ~/.exe-os/enforcement-audit.jsonl (structured JSONL, every nudge decision). If an agent seems stuck or was killed unexpectedly, READ THE LOGS FIRST before reporting a bug. The system is fully transparent \u2014 no black box behavior. If you can't explain what happened from the logs, THAT is the bug."
202
+ },
196
203
  // --- Operations ---
197
204
  {
198
205
  title: "Managers must supervise deployed workers",
@@ -224,6 +231,12 @@ var PLATFORM_PROCEDURES = [
224
231
  priority: "p0",
225
232
  content: "Before broad repo exploration, symbol tracing, blast-radius review, or codebase Q&A, agents MUST use code_context and graph MCP tools instead of manual grep/read loops. code_context: action=index or stats to refresh/check the index; action=search with query, limit, offset, languages, paths, refresh_index for fresh multi-language code/doc search; action=trace for symbol imports/dependents; action=blast_radius for impact analysis before edits. graph: action=query_relationships to find entity connections; action=hot_entities for most-referenced entities; action=entity_neighbors to explore direct connections; action=stats for entity/relationship counts. NEVER brute-force grep a codebase without checking code_context first \u2014 the index has every file, every symbol, every import relationship. All entity relationships should be mapped in the graph relations database. CLI parity exists via exe-os code-context init|index|status|stats|search|doctor. Keep code_context separate from durable employee memory: promote only validated decisions, procedures, or lessons into store_memory/commit_memory."
226
233
  },
234
+ {
235
+ title: "Retrieval architecture \u2014 three pillars, embeddings optional",
236
+ domain: "tool-use",
237
+ priority: "p1",
238
+ content: "Exe OS retrieval has THREE equal pillars: (1) Keyword search (FTS5 full-text), (2) Graph search (entity relationships), (3) Vector search (embedding similarity). All three run in parallel on every recall \u2014 results merge via Reciprocal Rank Fusion. CRITICAL: Keyword + Graph are FIRST-CLASS, not fallbacks. On 8-16 GB machines where the embedding model cannot load, retrieval is STILL excellent using FTS5 + Graph alone. The embed daemon is optional \u2014 when unavailable, the system automatically runs in FTS-only mode with graph boost. You lose semantic similarity (finding conceptually related but differently-worded memories) but keyword matching, entity traversal, bi-temporal filtering, and retrieval_mode all work perfectly. Do NOT tell users they need to download or run the embedding model to use memory effectively. Do NOT treat 'Embed daemon unavailable' warnings as errors \u2014 the system is working as designed. For 8 GB RAM: FTS + Graph only (no model). For 16 GB: FTS + Graph + optional 0.6B model if user opts in via /exe-setup. For 32+ GB: full hybrid with 4B model. The experience degrades gracefully \u2014 never breaks."
239
+ },
227
240
  {
228
241
  title: "Commit discipline \u2014 commit after every completed track, never batch",
229
242
  domain: "workflow",
@@ -1,9 +1,9 @@
1
1
  import {
2
2
  updateTask
3
- } from "./chunk-ZWS6XQER.js";
3
+ } from "./chunk-F5AKOE4P.js";
4
4
  import {
5
5
  TASK_ALREADY_CLAIMED_PREFIX
6
- } from "./chunk-W7SDGBEC.js";
6
+ } from "./chunk-MFI5OXYW.js";
7
7
 
8
8
  // src/mcp/tools/update-task.ts
9
9
  import { z } from "zod";
@@ -23,7 +23,7 @@ function registerUpdateTask(server) {
23
23
  const status = rawStatus;
24
24
  let callerAgentId;
25
25
  try {
26
- const { getActiveAgent: getAgent } = await import("./active-agent-CYMM3QQA.js");
26
+ const { getActiveAgent: getAgent } = await import("./active-agent-HVMLG6FH.js");
27
27
  callerAgentId = getAgent().agentId;
28
28
  } catch {
29
29
  }
@@ -9,7 +9,7 @@ import {
9
9
  getCoordinatorEmployee,
10
10
  getEmployee,
11
11
  loadEmployeesSync
12
- } from "./chunk-5RSYY7BE.js";
12
+ } from "./chunk-SJYOPYXH.js";
13
13
  import {
14
14
  EXE_AI_DIR
15
15
  } from "./chunk-4GXRETYL.js";