synabun 2026.3.307 → 2026.3.310

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 (214) hide show
  1. package/CLAUDE.md +150 -0
  2. package/hooks/claude-code/post-plan.mjs +1 -1
  3. package/hooks/claude-code/session-start.mjs +2 -0
  4. package/mcp-server/dist/config.d.ts +13 -0
  5. package/mcp-server/dist/config.d.ts.map +1 -0
  6. package/mcp-server/dist/config.js +59 -0
  7. package/mcp-server/dist/config.js.map +1 -0
  8. package/mcp-server/dist/http.d.ts +13 -0
  9. package/mcp-server/dist/http.d.ts.map +1 -0
  10. package/mcp-server/dist/http.js +86 -0
  11. package/mcp-server/dist/http.js.map +1 -0
  12. package/mcp-server/dist/index.d.ts +10 -0
  13. package/mcp-server/dist/index.d.ts.map +1 -0
  14. package/mcp-server/dist/index.js +189 -0
  15. package/mcp-server/dist/index.js.map +1 -0
  16. package/mcp-server/dist/preload-http.d.ts +3 -0
  17. package/mcp-server/dist/preload-http.d.ts.map +1 -0
  18. package/mcp-server/dist/preload-http.js +26 -0
  19. package/mcp-server/dist/preload-http.js.map +1 -0
  20. package/mcp-server/dist/preload.d.ts +3 -0
  21. package/mcp-server/dist/preload.d.ts.map +1 -0
  22. package/mcp-server/dist/preload.js +30 -0
  23. package/mcp-server/dist/preload.js.map +1 -0
  24. package/mcp-server/dist/scripts/migrate-qdrant-to-sqlite.d.ts +19 -0
  25. package/mcp-server/dist/scripts/migrate-qdrant-to-sqlite.d.ts.map +1 -0
  26. package/mcp-server/dist/scripts/migrate-qdrant-to-sqlite.js +403 -0
  27. package/mcp-server/dist/scripts/migrate-qdrant-to-sqlite.js.map +1 -0
  28. package/mcp-server/dist/services/categories.d.ts +61 -0
  29. package/mcp-server/dist/services/categories.d.ts.map +1 -0
  30. package/mcp-server/dist/services/categories.js +356 -0
  31. package/mcp-server/dist/services/categories.js.map +1 -0
  32. package/mcp-server/dist/services/discord.d.ts +112 -0
  33. package/mcp-server/dist/services/discord.d.ts.map +1 -0
  34. package/mcp-server/dist/services/discord.js +477 -0
  35. package/mcp-server/dist/services/discord.js.map +1 -0
  36. package/mcp-server/dist/services/file-checksums.d.ts +14 -0
  37. package/mcp-server/dist/services/file-checksums.d.ts.map +1 -0
  38. package/mcp-server/dist/services/file-checksums.js +34 -0
  39. package/mcp-server/dist/services/file-checksums.js.map +1 -0
  40. package/mcp-server/dist/services/local-embeddings.d.ts +23 -0
  41. package/mcp-server/dist/services/local-embeddings.d.ts.map +1 -0
  42. package/mcp-server/dist/services/local-embeddings.js +71 -0
  43. package/mcp-server/dist/services/local-embeddings.js.map +1 -0
  44. package/mcp-server/dist/services/neural-interface.d.ts +92 -0
  45. package/mcp-server/dist/services/neural-interface.d.ts.map +1 -0
  46. package/mcp-server/dist/services/neural-interface.js +238 -0
  47. package/mcp-server/dist/services/neural-interface.js.map +1 -0
  48. package/mcp-server/dist/services/sqlite.d.ts +85 -0
  49. package/mcp-server/dist/services/sqlite.d.ts.map +1 -0
  50. package/mcp-server/dist/services/sqlite.js +660 -0
  51. package/mcp-server/dist/services/sqlite.js.map +1 -0
  52. package/mcp-server/dist/tools/browser-advanced.d.ts +54 -0
  53. package/mcp-server/dist/tools/browser-advanced.d.ts.map +1 -0
  54. package/mcp-server/dist/tools/browser-advanced.js +97 -0
  55. package/mcp-server/dist/tools/browser-advanced.js.map +1 -0
  56. package/mcp-server/dist/tools/browser-interact.d.ts +138 -0
  57. package/mcp-server/dist/tools/browser-interact.d.ts.map +1 -0
  58. package/mcp-server/dist/tools/browser-interact.js +216 -0
  59. package/mcp-server/dist/tools/browser-interact.js.map +1 -0
  60. package/mcp-server/dist/tools/browser-navigate.d.ts +52 -0
  61. package/mcp-server/dist/tools/browser-navigate.d.ts.map +1 -0
  62. package/mcp-server/dist/tools/browser-navigate.js +61 -0
  63. package/mcp-server/dist/tools/browser-navigate.js.map +1 -0
  64. package/mcp-server/dist/tools/browser-observe.d.ts +298 -0
  65. package/mcp-server/dist/tools/browser-observe.d.ts.map +1 -0
  66. package/mcp-server/dist/tools/browser-observe.js +1154 -0
  67. package/mcp-server/dist/tools/browser-observe.js.map +1 -0
  68. package/mcp-server/dist/tools/browser.d.ts +7 -0
  69. package/mcp-server/dist/tools/browser.d.ts.map +1 -0
  70. package/mcp-server/dist/tools/browser.js +55 -0
  71. package/mcp-server/dist/tools/browser.js.map +1 -0
  72. package/mcp-server/dist/tools/card-tools.d.ts +82 -0
  73. package/mcp-server/dist/tools/card-tools.d.ts.map +1 -0
  74. package/mcp-server/dist/tools/card-tools.js +137 -0
  75. package/mcp-server/dist/tools/card-tools.js.map +1 -0
  76. package/mcp-server/dist/tools/card.d.ts +8 -0
  77. package/mcp-server/dist/tools/card.d.ts.map +1 -0
  78. package/mcp-server/dist/tools/card.js +14 -0
  79. package/mcp-server/dist/tools/card.js.map +1 -0
  80. package/mcp-server/dist/tools/category.d.ts +32 -0
  81. package/mcp-server/dist/tools/category.d.ts.map +1 -0
  82. package/mcp-server/dist/tools/category.js +290 -0
  83. package/mcp-server/dist/tools/category.js.map +1 -0
  84. package/mcp-server/dist/tools/discord-channel.d.ts +44 -0
  85. package/mcp-server/dist/tools/discord-channel.d.ts.map +1 -0
  86. package/mcp-server/dist/tools/discord-channel.js +236 -0
  87. package/mcp-server/dist/tools/discord-channel.js.map +1 -0
  88. package/mcp-server/dist/tools/discord-guild.d.ts +20 -0
  89. package/mcp-server/dist/tools/discord-guild.d.ts.map +1 -0
  90. package/mcp-server/dist/tools/discord-guild.js +138 -0
  91. package/mcp-server/dist/tools/discord-guild.js.map +1 -0
  92. package/mcp-server/dist/tools/discord-member.d.ts +26 -0
  93. package/mcp-server/dist/tools/discord-member.d.ts.map +1 -0
  94. package/mcp-server/dist/tools/discord-member.js +122 -0
  95. package/mcp-server/dist/tools/discord-member.js.map +1 -0
  96. package/mcp-server/dist/tools/discord-message.d.ts +36 -0
  97. package/mcp-server/dist/tools/discord-message.d.ts.map +1 -0
  98. package/mcp-server/dist/tools/discord-message.js +184 -0
  99. package/mcp-server/dist/tools/discord-message.js.map +1 -0
  100. package/mcp-server/dist/tools/discord-onboarding.d.ts +32 -0
  101. package/mcp-server/dist/tools/discord-onboarding.d.ts.map +1 -0
  102. package/mcp-server/dist/tools/discord-onboarding.js +179 -0
  103. package/mcp-server/dist/tools/discord-onboarding.js.map +1 -0
  104. package/mcp-server/dist/tools/discord-role.d.ts +34 -0
  105. package/mcp-server/dist/tools/discord-role.d.ts.map +1 -0
  106. package/mcp-server/dist/tools/discord-role.js +178 -0
  107. package/mcp-server/dist/tools/discord-role.js.map +1 -0
  108. package/mcp-server/dist/tools/discord-thread.d.ts +28 -0
  109. package/mcp-server/dist/tools/discord-thread.d.ts.map +1 -0
  110. package/mcp-server/dist/tools/discord-thread.js +88 -0
  111. package/mcp-server/dist/tools/discord-thread.js.map +1 -0
  112. package/mcp-server/dist/tools/discord-webhook.d.ts +32 -0
  113. package/mcp-server/dist/tools/discord-webhook.d.ts.map +1 -0
  114. package/mcp-server/dist/tools/discord-webhook.js +154 -0
  115. package/mcp-server/dist/tools/discord-webhook.js.map +1 -0
  116. package/mcp-server/dist/tools/discord.d.ts +7 -0
  117. package/mcp-server/dist/tools/discord.d.ts.map +1 -0
  118. package/mcp-server/dist/tools/discord.js +31 -0
  119. package/mcp-server/dist/tools/discord.js.map +1 -0
  120. package/mcp-server/dist/tools/forget.d.ts +14 -0
  121. package/mcp-server/dist/tools/forget.d.ts.map +1 -0
  122. package/mcp-server/dist/tools/forget.js +26 -0
  123. package/mcp-server/dist/tools/forget.js.map +1 -0
  124. package/mcp-server/dist/tools/git-tools.d.ts +24 -0
  125. package/mcp-server/dist/tools/git-tools.d.ts.map +1 -0
  126. package/mcp-server/dist/tools/git-tools.js +107 -0
  127. package/mcp-server/dist/tools/git-tools.js.map +1 -0
  128. package/mcp-server/dist/tools/git.d.ts +7 -0
  129. package/mcp-server/dist/tools/git.d.ts.map +1 -0
  130. package/mcp-server/dist/tools/git.js +9 -0
  131. package/mcp-server/dist/tools/git.js.map +1 -0
  132. package/mcp-server/dist/tools/image-tools.d.ts +24 -0
  133. package/mcp-server/dist/tools/image-tools.d.ts.map +1 -0
  134. package/mcp-server/dist/tools/image-tools.js +80 -0
  135. package/mcp-server/dist/tools/image-tools.js.map +1 -0
  136. package/mcp-server/dist/tools/image.d.ts +10 -0
  137. package/mcp-server/dist/tools/image.d.ts.map +1 -0
  138. package/mcp-server/dist/tools/image.js +12 -0
  139. package/mcp-server/dist/tools/image.js.map +1 -0
  140. package/mcp-server/dist/tools/leonardo-browser-tools.d.ts +77 -0
  141. package/mcp-server/dist/tools/leonardo-browser-tools.d.ts.map +1 -0
  142. package/mcp-server/dist/tools/leonardo-browser-tools.js +223 -0
  143. package/mcp-server/dist/tools/leonardo-browser-tools.js.map +1 -0
  144. package/mcp-server/dist/tools/leonardo.d.ts +13 -0
  145. package/mcp-server/dist/tools/leonardo.d.ts.map +1 -0
  146. package/mcp-server/dist/tools/leonardo.js +19 -0
  147. package/mcp-server/dist/tools/leonardo.js.map +1 -0
  148. package/mcp-server/dist/tools/loop.d.ts +30 -0
  149. package/mcp-server/dist/tools/loop.d.ts.map +1 -0
  150. package/mcp-server/dist/tools/loop.js +302 -0
  151. package/mcp-server/dist/tools/loop.js.map +1 -0
  152. package/mcp-server/dist/tools/memories.d.ts +26 -0
  153. package/mcp-server/dist/tools/memories.d.ts.map +1 -0
  154. package/mcp-server/dist/tools/memories.js +96 -0
  155. package/mcp-server/dist/tools/memories.js.map +1 -0
  156. package/mcp-server/dist/tools/recall.d.ts +41 -0
  157. package/mcp-server/dist/tools/recall.d.ts.map +1 -0
  158. package/mcp-server/dist/tools/recall.js +275 -0
  159. package/mcp-server/dist/tools/recall.js.map +1 -0
  160. package/mcp-server/dist/tools/reflect.d.ts +44 -0
  161. package/mcp-server/dist/tools/reflect.d.ts.map +1 -0
  162. package/mcp-server/dist/tools/reflect.js +118 -0
  163. package/mcp-server/dist/tools/reflect.js.map +1 -0
  164. package/mcp-server/dist/tools/remember.d.ts +38 -0
  165. package/mcp-server/dist/tools/remember.d.ts.map +1 -0
  166. package/mcp-server/dist/tools/remember.js +88 -0
  167. package/mcp-server/dist/tools/remember.js.map +1 -0
  168. package/mcp-server/dist/tools/response.d.ts +23 -0
  169. package/mcp-server/dist/tools/response.d.ts.map +1 -0
  170. package/mcp-server/dist/tools/response.js +24 -0
  171. package/mcp-server/dist/tools/response.js.map +1 -0
  172. package/mcp-server/dist/tools/restore.d.ts +14 -0
  173. package/mcp-server/dist/tools/restore.d.ts.map +1 -0
  174. package/mcp-server/dist/tools/restore.js +23 -0
  175. package/mcp-server/dist/tools/restore.js.map +1 -0
  176. package/mcp-server/dist/tools/sync.d.ts +18 -0
  177. package/mcp-server/dist/tools/sync.d.ts.map +1 -0
  178. package/mcp-server/dist/tools/sync.js +93 -0
  179. package/mcp-server/dist/tools/sync.js.map +1 -0
  180. package/mcp-server/dist/tools/tictactoe-tools.d.ts +18 -0
  181. package/mcp-server/dist/tools/tictactoe-tools.d.ts.map +1 -0
  182. package/mcp-server/dist/tools/tictactoe-tools.js +78 -0
  183. package/mcp-server/dist/tools/tictactoe-tools.js.map +1 -0
  184. package/mcp-server/dist/tools/tictactoe.d.ts +7 -0
  185. package/mcp-server/dist/tools/tictactoe.d.ts.map +1 -0
  186. package/mcp-server/dist/tools/tictactoe.js +9 -0
  187. package/mcp-server/dist/tools/tictactoe.js.map +1 -0
  188. package/mcp-server/dist/tools/utils.d.ts +10 -0
  189. package/mcp-server/dist/tools/utils.d.ts.map +1 -0
  190. package/mcp-server/dist/tools/utils.js +30 -0
  191. package/mcp-server/dist/tools/utils.js.map +1 -0
  192. package/mcp-server/dist/tools/whiteboard-tools.d.ts +194 -0
  193. package/mcp-server/dist/tools/whiteboard-tools.d.ts.map +1 -0
  194. package/mcp-server/dist/tools/whiteboard-tools.js +198 -0
  195. package/mcp-server/dist/tools/whiteboard-tools.js.map +1 -0
  196. package/mcp-server/dist/tools/whiteboard.d.ts +8 -0
  197. package/mcp-server/dist/tools/whiteboard.d.ts.map +1 -0
  198. package/mcp-server/dist/tools/whiteboard.js +14 -0
  199. package/mcp-server/dist/tools/whiteboard.js.map +1 -0
  200. package/mcp-server/dist/tui.d.ts +3 -0
  201. package/mcp-server/dist/tui.d.ts.map +1 -0
  202. package/mcp-server/dist/tui.js +807 -0
  203. package/mcp-server/dist/tui.js.map +1 -0
  204. package/mcp-server/dist/types.d.ts +77 -0
  205. package/mcp-server/dist/types.d.ts.map +1 -0
  206. package/mcp-server/dist/types.js +2 -0
  207. package/mcp-server/dist/types.js.map +1 -0
  208. package/neural-interface/public/shared/styles.css +2 -2
  209. package/neural-interface/public/shared/ui-settings.js +2 -2
  210. package/neural-interface/server.js +82 -8
  211. package/neural-interface/templates/CLAUDE-template.md +9 -1
  212. package/package.json +4 -2
  213. package/preuninstall.js +28 -0
  214. package/setup.js +86 -1
package/CLAUDE.md ADDED
@@ -0,0 +1,150 @@
1
+ # CLAUDE.md
2
+
3
+ ====================================END SYNBUN
4
+
5
+ This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
6
+
7
+ ## What is SynaBun
8
+
9
+ Persistent vector memory for AI assistants — SQLite + local Transformers.js embeddings (all-MiniLM-L6-v2, 384 dims). No external services, no API keys, no Docker. Installed via `npm install -g synabun` or cloned from GitHub.
10
+
11
+ ## Commands
12
+
13
+ ```bash
14
+ # Start everything (installs deps, builds MCP, launches Neural Interface)
15
+ npm start # runs setup.js
16
+
17
+ # Neural Interface only (Express server on :3344)
18
+ node neural-interface/server.js
19
+
20
+ # Build MCP server (required after any TypeScript change)
21
+ cd mcp-server && npm run build # ALWAYS use npm run build, never npx tsc
22
+
23
+ # Dev mode (auto-rebuild on change)
24
+ cd mcp-server && npm run dev # tsx src/index.ts
25
+
26
+ # Tests
27
+ cd mcp-server && npm test # vitest run
28
+ cd mcp-server && npm run test:watch # vitest watch mode
29
+
30
+ # Register MCP with Claude Code
31
+ claude mcp add SynaBun -s user -- node "/path/to/Synabun/mcp-server/run.mjs"
32
+ ```
33
+
34
+ ## Architecture
35
+
36
+ Two independently running processes that share one SQLite database:
37
+
38
+ ### MCP Server (`mcp-server/`)
39
+ TypeScript, compiles to `dist/`. Entry point: `run.mjs` → `dist/preload.js` → `dist/index.js`. Communicates with AI tools via MCP protocol (stdio or HTTP). 72 tools across 9 groups: Memory (8), Browser (39), Whiteboard (5), Cards (5), Discord (8), Leonardo (4), Git (1), Loop (1), TicTacToe (1).
40
+
41
+ - `src/index.ts` — tool registration, schema refresh, server creation
42
+ - `src/config.ts` — env config, project detection from `claude-code-projects.json`
43
+ - `src/types.ts` — `MemoryPayload` interface
44
+ - `src/http.ts` — HTTP MCP transport (stateless, fresh server per request)
45
+ - `src/services/sqlite.ts` — storage layer, vectors as Float32Array BLOBs, cosine similarity in JS
46
+ - `src/services/local-embeddings.ts` — Transformers.js embedding generation
47
+ - `src/services/categories.ts` — category CRUD, hierarchy, dynamic schema refresh
48
+ - `src/tools/` — one file per tool (or per tool group with a registration function)
49
+
50
+ ### Neural Interface (`neural-interface/`)
51
+ Express server (`server.js`, ~15K lines) serving a vanilla JS + Three.js frontend. 55+ REST API endpoints. Runs on port 3344.
52
+
53
+ - `server.js` — monolithic Express server with all API routes, WebSocket, terminal (node-pty), Playwright browser management, session registry, loop orchestration
54
+ - `public/index.html` — 3D force-directed graph (Three.js)
55
+ - `public/index2d.html` — 2D canvas variant
56
+ - `public/onboarding.html` — first-time setup wizard
57
+ - `public/claude-chat.html` — standalone Claude Code chat page
58
+ - `public/shared/` — modular JS/CSS (~50 files): `ui-*.js` modules, `storage.js` (server-synced state), `styles.css`, `utils.js`
59
+ - `lib/db.js` — shared SQLite access (same DB as MCP server)
60
+ - `lib/session-indexer.js` — conversation session indexing
61
+ - `skins/` — theme system (CSS + JSON per skin)
62
+ - `i18n/` — internationalization (en.json)
63
+ - `templates/CLAUDE-template.md` — source of truth for memory rulesets injected into project CLAUDE.md files
64
+
65
+ ### Hooks (`hooks/claude-code/`)
66
+ 7 ESM (.mjs) lifecycle hooks for Claude Code, registered in `.claude/settings.json`:
67
+
68
+ | Hook | Event | Purpose |
69
+ |------|-------|---------|
70
+ | `session-start.mjs` | SessionStart | Greeting, boot sequence, compaction recovery, loop detection |
71
+ | `prompt-submit.mjs` | UserPromptSubmit | Tiered recall nudges, loop iteration injection |
72
+ | `pre-compact.mjs` | PreCompact | Transcript capture before context compaction |
73
+ | `stop.mjs` | Stop | Combined obligations: compaction, loops, task memory, user learning |
74
+ | `post-remember.mjs` | PostToolUse | Edit tracking, flag clearing, user learning |
75
+ | `pre-websearch.mjs` | PreToolUse | Blocks WebSearch/WebFetch during active browser sessions |
76
+ | `post-plan.mjs` | PostToolUse | Auto-stores plans as memories on ExitPlanMode |
77
+
78
+ `shared.mjs` contains utilities used across hooks.
79
+
80
+ ### Skills (`skills/`)
81
+ Claude Code slash commands with `SKILL.md` entry points and `modules/` subdirectories:
82
+ - `synabun/` — `/synabun` command hub (brainstorm, audit, health, search)
83
+ - `leonardo/` — `/leonardo` master media prompter (video, image, model advisor, prompt library)
84
+
85
+ ### Data Flow
86
+ ```
87
+ AI tool calls remember → MCP server embeds content → SQLite stores vector + payload
88
+ AI tool calls recall → MCP server embeds query → cosine similarity search → re-ranked results
89
+ Neural Interface → reads same SQLite DB → renders 3D graph, REST API, WebSocket
90
+ Hooks → fire on Claude Code events → inject context, enforce memory obligations
91
+ ```
92
+
93
+ ### Shared State
94
+ - `data/memory.db` — single SQLite database (memories, session chunks, trash)
95
+ - `data/ui-state.json` — Neural Interface UI state (synced via `storage.js`)
96
+ - `data/pending-compact/` — per-session compaction flags
97
+ - `data/pending-remember/` — per-session edit tracking flags
98
+ - `mcp-server/data/custom-categories-{connId}.json` — per-connection category definitions
99
+
100
+ ## Key Patterns
101
+
102
+ - **Category descriptions are routing instructions**: Claude reads all category descriptions from the MCP tool schema to decide where to store memories. Descriptions must be prescriptive rules, not vague labels.
103
+ - **Dynamic schema refresh**: Category changes trigger `refreshCategorySchemas()` → `notifications/tools/list_changed` → Claude re-fetches tool list. No restart needed.
104
+ - **Per-tab session isolation**: Project/model/effort state stored per-tab in sidepanel (`ui-claude-panel.js`) and per-tab via `sessionStorage` in standalone (`claude-chat.js`). Global `ui-state.json` keys are "last used" defaults only.
105
+ - **Browser sessions**: Playwright with persistent Chromium profiles. Multi-session isolation via dedicated browser session per automation. Leonardo tools are 100% browser-based (no API key).
106
+ - **Compaction chain**: PreCompact → flag → SessionStart injects → Claude remembers(conversations) → PostToolUse clears → Stop allows.
107
+ - **MCP calls must be sequential**: Parallel MCP tool calls can cascade failures. Always call memory tools one at a time.
108
+
109
+ ## Environment
110
+
111
+ - Node.js 22.5+ required (for built-in `node:sqlite`)
112
+ - `.env` at project root — `SQLITE_DB_PATH`, `NEURAL_PORT` (default 3344), `DISCORD_BOT_TOKEN`, `DISCORD_GUILD_ID`
113
+ - CLAUDE.md is gitignored (user-local)
114
+
115
+ ## Persistent Memory
116
+
117
+ You have persistent vector memory via the `SynaBun` MCP server (72 tools).
118
+ Core memory tools: remember, recall, forget, restore, reflect, memories, sync, category.
119
+
120
+ ### Auto-Recall
121
+ - Session start: recall current project context
122
+ - Topic mentioned: recall what you know
123
+ - Before architecture decisions: recall past decisions
124
+ - Debugging: recall similar bugs
125
+
126
+ ### Auto-Remember (MANDATORY)
127
+ After ANY task (bug fix, feature, refactor, config change, investigation, architecture decision), MUST `remember` BEFORE responding.
128
+
129
+ Steps:
130
+ 1. `remember` — what + why + how, appropriate category, set project, related_files, importance (5=routine, 6-7=significant, 8+=critical), and 3-5 tags
131
+
132
+ `remember` returns the full UUID and accepts all fields (tags, importance) directly. No need to recall+reflect afterward.
133
+
134
+ **NOT triggered by:** Simple Q&A, file reads with no findings, trivial typos.
135
+
136
+ **Importance scale:** 1-2=trivial, 3-4=low, 5=normal, 6-7=significant, 8-9=critical, 10=foundational. User says "remember this" → 8+. Architecture decisions → 8+.
137
+
138
+ ### Response Ordering
139
+ When finishing a task: call `remember` (and any other memory tools) **FIRST**, then write your completion summary **LAST**. Never summary-then-tools — the stop hook will block you.
140
+
141
+ ### Tool Quirks
142
+ - `remember` returns the full UUID and accepts tags + importance directly.
143
+ - `reflect` requires FULL UUID — use the one from `remember`, or `recall` to find existing memories.
144
+ - Sequential MCP calls only — never parallel.
145
+
146
+ ### Plan Mode
147
+ When in plan mode and you need clarification:
148
+ - ALWAYS use `AskUserQuestion` to present options — never plain text questions
149
+ - Use `ExitPlanMode` for final plan approval
150
+ - Use `multiSelect: true` in AskUserQuestion when options aren't mutually exclusive
@@ -309,7 +309,7 @@ async function main() {
309
309
  if (toolName === 'EnterPlanMode') {
310
310
  debugLog('EnterPlanMode fired — injecting AskUserQuestion reminder');
311
311
  process.stdout.write(JSON.stringify({
312
- additionalContext: `SynaBun: You are now in plan mode. When you have questions or need clarification from the user, you MUST use the \`AskUserQuestion\` tool — do NOT write questions as plain text. Load it via \`ToolSearch\` if its schema is not yet available. Use \`ExitPlanMode\` for final plan approval.\n\n**Plan file location**: Write plan files to \`${PLANS_DIR}/\` — NOT \`~/.claude/plans/\`. This avoids sensitive-file permission prompts that stall the session.`,
312
+ additionalContext: `SynaBun: You are now in plan mode.\n\n**CRITICAL CONSTRAINT**: Do NOT make code changes (Edit, Write, NotebookEdit). Plan mode is RESEARCH AND PLANNING ONLY. Investigate, read files, search code — then present your plan. Do NOT implement anything until the user explicitly approves the plan and you exit plan mode.\n\nWhen you have questions or need clarification, you MUST use the \`AskUserQuestion\` tool — do NOT write questions as plain text. Load it via \`ToolSearch\` if its schema is not yet available. Use \`ExitPlanMode\` for final plan approval.\n\n**Plan file location**: Write plan files to \`${PLANS_DIR}/\` — NOT \`~/.claude/plans/\`. This avoids sensitive-file permission prompts.`,
313
313
  }));
314
314
  return;
315
315
  }
@@ -464,6 +464,8 @@ async function main() {
464
464
  ``,
465
465
  `If an autonomous loop was active before compaction, the Stop hook will resume it automatically. Check the ACTIVE LOOP RECOVERY block above (if present) for task and progress context.`,
466
466
  ``,
467
+ `**Plan files**: Write plan files to the project's \`data/plans/\` directory — NOT \`~/.claude/plans/\`. This avoids sensitive-file permission prompts that don't persist across compactions.`,
468
+ ``,
467
469
  `---`,
468
470
  ``,
469
471
  );
@@ -0,0 +1,13 @@
1
+ export declare const config: {
2
+ readonly dataDir: string;
3
+ readonly sqlite: {
4
+ readonly dbPath: string;
5
+ };
6
+ readonly embedding: {
7
+ readonly model: "Xenova/all-MiniLM-L6-v2";
8
+ readonly dimensions: 384;
9
+ };
10
+ };
11
+ export declare function getEnvPath(): string;
12
+ export declare function detectProject(cwd?: string): string;
13
+ //# sourceMappingURL=config.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"AAKA,eAAO,MAAM,MAAM;;;;;;;;;CAST,CAAC;AAIX,wBAAgB,UAAU,IAAI,MAAM,CAEnC;AAsBD,wBAAgB,aAAa,CAAC,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,CA2BlD"}
@@ -0,0 +1,59 @@
1
+ import path from 'path';
2
+ import fs from 'fs';
3
+ // --- Static config ---
4
+ export const config = {
5
+ dataDir: process.env.MEMORY_DATA_DIR || path.resolve(import.meta.dirname || process.cwd(), '..', 'data'),
6
+ sqlite: {
7
+ dbPath: process.env.SQLITE_DB_PATH || '', // resolved lazily from dataDir
8
+ },
9
+ embedding: {
10
+ model: 'Xenova/all-MiniLM-L6-v2',
11
+ dimensions: 384,
12
+ },
13
+ };
14
+ // --- .env path resolution (for file watching) ---
15
+ export function getEnvPath() {
16
+ return process.env.DOTENV_PATH || path.resolve(import.meta.dirname || process.cwd(), '..', '..', '.env');
17
+ }
18
+ // --- Project Detection (reads from claude-code-projects.json) ---
19
+ const PROJECTS_PATH = path.join(config.dataDir, 'claude-code-projects.json');
20
+ function loadRegisteredProjects() {
21
+ try {
22
+ if (!fs.existsSync(PROJECTS_PATH))
23
+ return [];
24
+ return JSON.parse(fs.readFileSync(PROJECTS_PATH, 'utf-8'));
25
+ }
26
+ catch {
27
+ return [];
28
+ }
29
+ }
30
+ function normalizeLabel(label) {
31
+ return label.toLowerCase().replace(/[^a-z0-9]+/g, '-').replace(/^-|-$/g, '');
32
+ }
33
+ export function detectProject(cwd) {
34
+ const dir = cwd || process.cwd();
35
+ const lower = dir.toLowerCase().replace(/\\/g, '/');
36
+ const projects = loadRegisteredProjects();
37
+ // Sort by path length descending — most specific match wins
38
+ const sorted = projects
39
+ .map((p) => ({
40
+ path: p.path.toLowerCase().replace(/\\/g, '/'),
41
+ label: normalizeLabel(p.label),
42
+ }))
43
+ .sort((a, b) => b.path.length - a.path.length);
44
+ // 1. Exact path prefix match (cwd is inside a registered project)
45
+ for (const p of sorted) {
46
+ if (lower.startsWith(p.path + '/') || lower === p.path)
47
+ return p.label;
48
+ }
49
+ // 2. Substring match — cwd folder name contains a registered project's folder name
50
+ for (const p of sorted) {
51
+ const projFolder = path.basename(p.path).toLowerCase();
52
+ if (lower.includes(projFolder))
53
+ return p.label;
54
+ }
55
+ // 3. Fallback to directory basename
56
+ const base = path.basename(dir).toLowerCase().replace(/[^a-z0-9-]/g, '-');
57
+ return base || 'global';
58
+ }
59
+ //# sourceMappingURL=config.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.js","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,13 @@
1
+ #!/usr/bin/env node
2
+ /**
3
+ * HTTP transport for SynaBun MCP server.
4
+ * Stateless — creates a fresh McpServer per request (same tools, no session state).
5
+ * Mount on any Express app or run standalone.
6
+ */
7
+ /**
8
+ * Create Express routes for the MCP HTTP endpoint.
9
+ * Auth is handled externally (URL-embedded key in server.js).
10
+ * Can be mounted on an existing Express app: app.use('/mcp', createMcpRoutes());
11
+ */
12
+ export declare function createMcpRoutes(): import("express-serve-static-core").Router;
13
+ //# sourceMappingURL=http.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"http.d.ts","sourceRoot":"","sources":["../src/http.ts"],"names":[],"mappings":";AAEA;;;;GAIG;AAiBH;;;;GAIG;AACH,wBAAgB,eAAe,+CA6C9B"}
@@ -0,0 +1,86 @@
1
+ #!/usr/bin/env node
2
+ /**
3
+ * HTTP transport for SynaBun MCP server.
4
+ * Stateless — creates a fresh McpServer per request (same tools, no session state).
5
+ * Mount on any Express app or run standalone.
6
+ */
7
+ import express from 'express';
8
+ import { StreamableHTTPServerTransport } from '@modelcontextprotocol/sdk/server/streamableHttp.js';
9
+ import { ensureDatabase } from './services/sqlite.js';
10
+ import { initCategoryCache } from './services/categories.js';
11
+ import { createMcpServer } from './index.js';
12
+ let initialized = false;
13
+ async function ensureInit() {
14
+ if (initialized)
15
+ return;
16
+ try {
17
+ await ensureDatabase();
18
+ }
19
+ catch { }
20
+ await initCategoryCache();
21
+ initialized = true;
22
+ }
23
+ /**
24
+ * Create Express routes for the MCP HTTP endpoint.
25
+ * Auth is handled externally (URL-embedded key in server.js).
26
+ * Can be mounted on an existing Express app: app.use('/mcp', createMcpRoutes());
27
+ */
28
+ export function createMcpRoutes() {
29
+ const router = express.Router();
30
+ router.use(express.json());
31
+ router.post('/', async (req, res) => {
32
+ await ensureInit();
33
+ const server = createMcpServer();
34
+ try {
35
+ const transport = new StreamableHTTPServerTransport({ sessionIdGenerator: undefined });
36
+ await server.connect(transport);
37
+ await transport.handleRequest(req, res, req.body);
38
+ res.on('close', () => {
39
+ transport.close();
40
+ server.close();
41
+ });
42
+ }
43
+ catch (error) {
44
+ console.error('MCP HTTP error:', error);
45
+ if (!res.headersSent) {
46
+ res.status(500).json({
47
+ jsonrpc: '2.0',
48
+ error: { code: -32603, message: 'Internal server error' },
49
+ id: null,
50
+ });
51
+ }
52
+ }
53
+ });
54
+ // Stateless — no GET (SSE) or DELETE (session close) needed
55
+ router.get('/', (_req, res) => {
56
+ res.writeHead(405).end(JSON.stringify({
57
+ jsonrpc: '2.0',
58
+ error: { code: -32000, message: 'Method not allowed.' },
59
+ id: null,
60
+ }));
61
+ });
62
+ router.delete('/', (_req, res) => {
63
+ res.writeHead(405).end(JSON.stringify({
64
+ jsonrpc: '2.0',
65
+ error: { code: -32000, message: 'Method not allowed.' },
66
+ id: null,
67
+ }));
68
+ });
69
+ return router;
70
+ }
71
+ // If run directly, start a standalone HTTP server
72
+ const isMain = process.argv[1]?.replace(/\\/g, '/').endsWith('/http.js')
73
+ || process.argv[1]?.replace(/\\/g, '/').endsWith('/http.ts');
74
+ if (isMain) {
75
+ const PORT = parseInt(process.env.MCP_HTTP_PORT || '3345', 10);
76
+ const app = express();
77
+ app.use('/mcp', createMcpRoutes());
78
+ app.get('/', (_req, res) => {
79
+ res.json({ name: 'SynaBun MCP (HTTP)', status: 'ok', endpoint: '/mcp' });
80
+ });
81
+ app.listen(PORT, () => {
82
+ console.log(`SynaBun MCP HTTP server listening on port ${PORT}`);
83
+ console.log(`Endpoint: http://localhost:${PORT}/mcp`);
84
+ });
85
+ }
86
+ //# sourceMappingURL=http.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"http.js","sourceRoot":"","sources":["../src/http.ts"],"names":[],"mappings":";AAEA;;;;GAIG;AAEH,OAAO,OAAO,MAAM,SAAS,CAAC;AAC9B,OAAO,EAAE,6BAA6B,EAAE,MAAM,oDAAoD,CAAC;AACnG,OAAO,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AACtD,OAAO,EAAE,iBAAiB,EAAE,MAAM,0BAA0B,CAAC;AAC7D,OAAO,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAE7C,IAAI,WAAW,GAAG,KAAK,CAAC;AAExB,KAAK,UAAU,UAAU;IACvB,IAAI,WAAW;QAAE,OAAO;IACxB,IAAI,CAAC;QAAC,MAAM,cAAc,EAAE,CAAC;IAAC,CAAC;IAAC,MAAM,CAAC,CAAA,CAAC;IACxC,MAAM,iBAAiB,EAAE,CAAC;IAC1B,WAAW,GAAG,IAAI,CAAC;AACrB,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,eAAe;IAC7B,MAAM,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC;IAChC,MAAM,CAAC,GAAG,CAAC,OAAO,CAAC,IAAI,EAAE,CAAC,CAAC;IAE3B,MAAM,CAAC,IAAI,CAAC,GAAG,EAAE,KAAK,EAAE,GAAG,EAAE,GAAG,EAAE,EAAE;QAClC,MAAM,UAAU,EAAE,CAAC;QACnB,MAAM,MAAM,GAAG,eAAe,EAAE,CAAC;QACjC,IAAI,CAAC;YACH,MAAM,SAAS,GAAG,IAAI,6BAA6B,CAAC,EAAE,kBAAkB,EAAE,SAAS,EAAE,CAAC,CAAC;YACvF,MAAM,MAAM,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;YAChC,MAAM,SAAS,CAAC,aAAa,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,IAAI,CAAC,CAAC;YAClD,GAAG,CAAC,EAAE,CAAC,OAAO,EAAE,GAAG,EAAE;gBACnB,SAAS,CAAC,KAAK,EAAE,CAAC;gBAClB,MAAM,CAAC,KAAK,EAAE,CAAC;YACjB,CAAC,CAAC,CAAC;QACL,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,CAAC,KAAK,CAAC,iBAAiB,EAAE,KAAK,CAAC,CAAC;YACxC,IAAI,CAAC,GAAG,CAAC,WAAW,EAAE,CAAC;gBACrB,GAAG,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC;oBACnB,OAAO,EAAE,KAAK;oBACd,KAAK,EAAE,EAAE,IAAI,EAAE,CAAC,KAAK,EAAE,OAAO,EAAE,uBAAuB,EAAE;oBACzD,EAAE,EAAE,IAAI;iBACT,CAAC,CAAC;YACL,CAAC;QACH,CAAC;IACH,CAAC,CAAC,CAAC;IAEH,4DAA4D;IAC5D,MAAM,CAAC,GAAG,CAAC,GAAG,EAAE,CAAC,IAAI,EAAE,GAAG,EAAE,EAAE;QAC5B,GAAG,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,IAAI,CAAC,SAAS,CAAC;YACpC,OAAO,EAAE,KAAK;YACd,KAAK,EAAE,EAAE,IAAI,EAAE,CAAC,KAAK,EAAE,OAAO,EAAE,qBAAqB,EAAE;YACvD,EAAE,EAAE,IAAI;SACT,CAAC,CAAC,CAAC;IACN,CAAC,CAAC,CAAC;IAEH,MAAM,CAAC,MAAM,CAAC,GAAG,EAAE,CAAC,IAAI,EAAE,GAAG,EAAE,EAAE;QAC/B,GAAG,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,IAAI,CAAC,SAAS,CAAC;YACpC,OAAO,EAAE,KAAK;YACd,KAAK,EAAE,EAAE,IAAI,EAAE,CAAC,KAAK,EAAE,OAAO,EAAE,qBAAqB,EAAE;YACvD,EAAE,EAAE,IAAI;SACT,CAAC,CAAC,CAAC;IACN,CAAC,CAAC,CAAC;IAEH,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,kDAAkD;AAClD,MAAM,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC,QAAQ,CAAC,UAAU,CAAC;OACnE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC,QAAQ,CAAC,UAAU,CAAC,CAAC;AAE/D,IAAI,MAAM,EAAE,CAAC;IACX,MAAM,IAAI,GAAG,QAAQ,CAAC,OAAO,CAAC,GAAG,CAAC,aAAa,IAAI,MAAM,EAAE,EAAE,CAAC,CAAC;IAC/D,MAAM,GAAG,GAAG,OAAO,EAAE,CAAC;IACtB,GAAG,CAAC,GAAG,CAAC,MAAM,EAAE,eAAe,EAAE,CAAC,CAAC;IAEnC,GAAG,CAAC,GAAG,CAAC,GAAG,EAAE,CAAC,IAAI,EAAE,GAAG,EAAE,EAAE;QACzB,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,oBAAoB,EAAE,MAAM,EAAE,IAAI,EAAE,QAAQ,EAAE,MAAM,EAAE,CAAC,CAAC;IAC3E,CAAC,CAAC,CAAC;IAEH,GAAG,CAAC,MAAM,CAAC,IAAI,EAAE,GAAG,EAAE;QACpB,OAAO,CAAC,GAAG,CAAC,6CAA6C,IAAI,EAAE,CAAC,CAAC;QACjE,OAAO,CAAC,GAAG,CAAC,8BAA8B,IAAI,MAAM,CAAC,CAAC;IACxD,CAAC,CAAC,CAAC;AACL,CAAC"}
@@ -0,0 +1,10 @@
1
+ import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
2
+ export declare function registerTools(server: McpServer): {
3
+ rememberTool: import("@modelcontextprotocol/sdk/server/mcp.js").RegisteredTool;
4
+ recallTool: import("@modelcontextprotocol/sdk/server/mcp.js").RegisteredTool;
5
+ reflectTool: import("@modelcontextprotocol/sdk/server/mcp.js").RegisteredTool;
6
+ memoriesTool: import("@modelcontextprotocol/sdk/server/mcp.js").RegisteredTool;
7
+ };
8
+ export declare function createMcpServer(): McpServer;
9
+ export declare function refreshCategorySchemas(): void;
10
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAmDpE,wBAAgB,aAAa,CAAC,MAAM,EAAE,SAAS;;;;;EAmB9C;AAGD,wBAAgB,eAAe,cAO9B;AAWD,wBAAgB,sBAAsB,SAMrC"}
@@ -0,0 +1,189 @@
1
+ import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
2
+ import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
3
+ import { ensureDatabase, closeDatabase, reopenDatabase } from './services/sqlite.js';
4
+ import { rememberSchema, rememberDescription, handleRemember, buildRememberSchema } from './tools/remember.js';
5
+ import { recallSchema, recallDescription, handleRecall, buildRecallSchema } from './tools/recall.js';
6
+ import { forgetSchema, forgetDescription, handleForget } from './tools/forget.js';
7
+ import { restoreSchema, restoreDescription, handleRestore } from './tools/restore.js';
8
+ import { reflectSchema, reflectDescription, handleReflect, buildReflectSchema } from './tools/reflect.js';
9
+ import { memoriesSchema, memoriesDescription, handleMemories, buildMemoriesSchema } from './tools/memories.js';
10
+ import { categorySchema, categoryDescription, handleCategory } from './tools/category.js';
11
+ import { syncSchema, syncDescription, handleSync } from './tools/sync.js';
12
+ import { loopSchema, loopDescription, handleLoop } from './tools/loop.js';
13
+ import { registerBrowserTools } from './tools/browser.js';
14
+ import { registerWhiteboardTools } from './tools/whiteboard.js';
15
+ import { registerCardTools } from './tools/card.js';
16
+ import { registerTicTacToeTools } from './tools/tictactoe.js';
17
+ import { registerDiscordTools } from './tools/discord.js';
18
+ import { registerGitTools } from './tools/git.js';
19
+ import { registerLeonardoTools } from './tools/leonardo.js';
20
+ import { registerImageTools } from './tools/image.js';
21
+ import { invalidateCategoryCache, setOnExternalChange, startWatchingCategories, stopWatchingCategories, initCategoryCache } from './services/categories.js';
22
+ import { getEnvPath } from './config.js';
23
+ import { readFileSync, watch, existsSync } from 'fs';
24
+ function buildServerInstructions() {
25
+ return `SynaBun — persistent vector memory system for Claude Code sessions.
26
+
27
+ Tool groups:
28
+ - Memory: remember, recall, reflect, forget, restore, memories
29
+ - Categories: category (action: create/update/delete/list)
30
+ - Browser: browser_navigate, browser_click, browser_type, browser_fill, browser_hover, browser_select, browser_press, browser_scroll, browser_upload, browser_go_back, browser_go_forward, browser_reload, browser_snapshot, browser_content, browser_screenshot, browser_evaluate, browser_wait, browser_session, browser_extract_tweets, browser_extract_fb_posts, browser_extract_tiktok_videos, browser_extract_tiktok_search, browser_extract_tiktok_studio, browser_extract_tiktok_profile, browser_extract_wa_chats, browser_extract_wa_messages, browser_extract_ig_feed, browser_extract_ig_profile, browser_extract_ig_post, browser_extract_ig_reels, browser_extract_ig_search, browser_extract_li_feed, browser_extract_li_profile, browser_extract_li_post, browser_extract_li_notifications, browser_extract_li_messages, browser_extract_li_search_people, browser_extract_li_network, browser_extract_li_jobs
31
+ - Whiteboard: whiteboard_read, whiteboard_add, whiteboard_update, whiteboard_remove, whiteboard_screenshot
32
+ - Cards: card_list, card_open, card_close, card_update, card_screenshot
33
+ - TicTacToe: tictactoe (action: start/move/state/end)
34
+ - Sync: sync
35
+ - Loop: loop (action: start/stop/status)
36
+ - Git: git (action: status/diff/commit/log/branches)
37
+ - Discord: discord_guild, discord_channel, discord_role, discord_message, discord_member, discord_onboarding, discord_webhook, discord_thread
38
+ - Images: image_staged (action: list/clear/remove)
39
+ - Leonardo (browser-based): leonardo_browser_navigate, leonardo_browser_generate, leonardo_browser_library, leonardo_browser_download, leonardo_browser_reference
40
+
41
+ Use "category" with action "list" to see valid category names before using remember/recall/reflect.
42
+
43
+ Discord tools require DISCORD_BOT_TOKEN in .env. Set DISCORD_GUILD_ID for default guild. Each tool uses an "action" parameter to select the operation.
44
+
45
+ Leonardo tools are 100% browser-based — no API key needed. Use leonardo_browser_navigate to go to the right page, then use generic browser tools (browser_click, browser_fill, browser_snapshot) to configure settings (model, style, dimensions, motion controls), and leonardo_browser_generate to fill the prompt and click Generate. Use the /leonardo skill for the full guided creation experience.`;
46
+ }
47
+ // Register all tools on a given McpServer instance.
48
+ // Returns references needed for dynamic schema refresh.
49
+ export function registerTools(server) {
50
+ const rememberTool = server.tool('remember', rememberDescription, rememberSchema, handleRemember);
51
+ const recallTool = server.tool('recall', recallDescription, recallSchema, handleRecall);
52
+ server.tool('forget', forgetDescription, forgetSchema, handleForget);
53
+ server.tool('restore', restoreDescription, restoreSchema, handleRestore);
54
+ const reflectTool = server.tool('reflect', reflectDescription, reflectSchema, handleReflect);
55
+ const memoriesTool = server.tool('memories', memoriesDescription, memoriesSchema, handleMemories);
56
+ server.tool('category', categoryDescription, categorySchema, handleCategory);
57
+ server.tool('sync', syncDescription, syncSchema, handleSync);
58
+ server.tool('loop', loopDescription, loopSchema, handleLoop);
59
+ registerBrowserTools(server);
60
+ registerWhiteboardTools(server);
61
+ registerCardTools(server);
62
+ registerTicTacToeTools(server);
63
+ registerDiscordTools(server);
64
+ registerGitTools(server);
65
+ registerLeonardoTools(server);
66
+ registerImageTools(server);
67
+ return { rememberTool, recallTool, reflectTool, memoriesTool };
68
+ }
69
+ // Create a fully configured McpServer with all tools registered.
70
+ export function createMcpServer() {
71
+ const server = new McpServer({ name: 'claude-memory', version: '1.1.0' }, { instructions: buildServerInstructions() });
72
+ registerTools(server);
73
+ return server;
74
+ }
75
+ const server = new McpServer({ name: 'claude-memory', version: '1.1.0' }, { instructions: buildServerInstructions() });
76
+ const { rememberTool, recallTool, reflectTool, memoriesTool } = registerTools(server);
77
+ // Refresh all tool schemas that reference category descriptions.
78
+ // Called after any category change so Claude sees updated guidelines.
79
+ export function refreshCategorySchemas() {
80
+ invalidateCategoryCache();
81
+ rememberTool.update({ paramsSchema: buildRememberSchema() });
82
+ recallTool.update({ paramsSchema: buildRecallSchema() });
83
+ reflectTool.update({ paramsSchema: buildReflectSchema() });
84
+ memoriesTool.update({ paramsSchema: buildMemoriesSchema() });
85
+ }
86
+ async function main() {
87
+ try {
88
+ await ensureDatabase();
89
+ }
90
+ catch (err) {
91
+ console.error('Warning: Could not initialize SQLite database on startup.', err instanceof Error ? err.message : err);
92
+ }
93
+ // Initialize category cache (loads from SQLite or starts empty)
94
+ await initCategoryCache();
95
+ // Set up file watcher for external category changes
96
+ setOnExternalChange(() => {
97
+ console.error('Categories changed externally, refreshing schemas...');
98
+ refreshCategorySchemas();
99
+ // Notify Claude Code that tool schemas have changed
100
+ server.server.notification({
101
+ method: 'notifications/tools/list_changed',
102
+ }).catch((err) => {
103
+ console.error('Failed to send tools/list_changed notification:', err);
104
+ });
105
+ });
106
+ startWatchingCategories();
107
+ // Watch .env for SQLITE_DB_PATH changes (e.g. from onboarding or settings)
108
+ const envPath = getEnvPath();
109
+ let envWatcher = null;
110
+ if (existsSync(envPath)) {
111
+ startEnvWatcher();
112
+ }
113
+ else {
114
+ // .env doesn't exist yet — poll until it appears, then start watching
115
+ const envPollInterval = setInterval(() => {
116
+ if (existsSync(envPath)) {
117
+ clearInterval(envPollInterval);
118
+ startEnvWatcher();
119
+ }
120
+ }, 5000);
121
+ envPollInterval.unref();
122
+ }
123
+ function startEnvWatcher() {
124
+ try {
125
+ let debounce = null;
126
+ envWatcher = watch(envPath, () => {
127
+ if (debounce)
128
+ clearTimeout(debounce);
129
+ debounce = setTimeout(() => {
130
+ try {
131
+ const content = readFileSync(envPath, 'utf-8');
132
+ const vars = {};
133
+ for (const line of content.split('\n')) {
134
+ const trimmed = line.trim();
135
+ if (!trimmed || trimmed.startsWith('#'))
136
+ continue;
137
+ const eq = trimmed.indexOf('=');
138
+ if (eq === -1)
139
+ continue;
140
+ vars[trimmed.slice(0, eq)] = trimmed.slice(eq + 1);
141
+ }
142
+ const newDbPath = vars['SQLITE_DB_PATH'];
143
+ const currentDbPath = process.env.SQLITE_DB_PATH || '';
144
+ if (newDbPath && newDbPath !== currentDbPath) {
145
+ console.error(`SQLITE_DB_PATH changed: ${currentDbPath || '(default)'} → ${newDbPath}`);
146
+ process.env.SQLITE_DB_PATH = newDbPath;
147
+ reopenDatabase().catch((err) => {
148
+ console.error('Failed to reopen database at new path:', err);
149
+ });
150
+ }
151
+ }
152
+ catch (err) {
153
+ console.error('.env reload error:', err);
154
+ }
155
+ }, 500);
156
+ });
157
+ }
158
+ catch (err) {
159
+ console.error('Failed to watch .env:', err);
160
+ }
161
+ }
162
+ // Clean up on exit
163
+ process.on('SIGINT', () => {
164
+ if (envWatcher)
165
+ envWatcher.close();
166
+ stopWatchingCategories();
167
+ closeDatabase();
168
+ process.exit(0);
169
+ });
170
+ process.on('SIGTERM', () => {
171
+ if (envWatcher)
172
+ envWatcher.close();
173
+ stopWatchingCategories();
174
+ closeDatabase();
175
+ process.exit(0);
176
+ });
177
+ const transport = new StdioServerTransport();
178
+ await server.connect(transport);
179
+ }
180
+ // Only start stdio transport when run directly (not when imported by http.ts)
181
+ const isMain = process.argv[1]?.replace(/\\/g, '/').endsWith('/index.js')
182
+ || process.argv[1]?.replace(/\\/g, '/').endsWith('/preload.js');
183
+ if (isMain) {
184
+ main().catch((err) => {
185
+ console.error('Fatal error starting memory server:', err);
186
+ process.exit(1);
187
+ });
188
+ }
189
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AACpE,OAAO,EAAE,oBAAoB,EAAE,MAAM,2CAA2C,CAAC;AACjF,OAAO,EAAE,cAAc,EAAE,aAAa,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAErF,OAAO,EAAE,cAAc,EAAE,mBAAmB,EAAE,cAAc,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC;AAC/G,OAAO,EAAE,YAAY,EAAE,iBAAiB,EAAE,YAAY,EAAE,iBAAiB,EAAE,MAAM,mBAAmB,CAAC;AACrG,OAAO,EAAE,YAAY,EAAE,iBAAiB,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AAClF,OAAO,EAAE,aAAa,EAAE,kBAAkB,EAAE,aAAa,EAAE,MAAM,oBAAoB,CAAC;AACtF,OAAO,EAAE,aAAa,EAAE,kBAAkB,EAAE,aAAa,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AAC1G,OAAO,EAAE,cAAc,EAAE,mBAAmB,EAAE,cAAc,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC;AAC/G,OAAO,EAAE,cAAc,EAAE,mBAAmB,EAAE,cAAc,EAAE,MAAM,qBAAqB,CAAC;AAC1F,OAAO,EAAE,UAAU,EAAE,eAAe,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;AAC1E,OAAO,EAAE,UAAU,EAAE,eAAe,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;AAC1E,OAAO,EAAE,oBAAoB,EAAE,MAAM,oBAAoB,CAAC;AAC1D,OAAO,EAAE,uBAAuB,EAAE,MAAM,uBAAuB,CAAC;AAChE,OAAO,EAAE,iBAAiB,EAAE,MAAM,iBAAiB,CAAC;AACpD,OAAO,EAAE,sBAAsB,EAAE,MAAM,sBAAsB,CAAC;AAC9D,OAAO,EAAE,oBAAoB,EAAE,MAAM,oBAAoB,CAAC;AAC1D,OAAO,EAAE,gBAAgB,EAAE,MAAM,gBAAgB,CAAC;AAClD,OAAO,EAAE,qBAAqB,EAAE,MAAM,qBAAqB,CAAC;AAC5D,OAAO,EAAE,kBAAkB,EAAE,MAAM,kBAAkB,CAAC;AACtD,OAAO,EAAE,uBAAuB,EAAE,mBAAmB,EAAE,uBAAuB,EAAE,sBAAsB,EAAE,iBAAiB,EAAE,MAAM,0BAA0B,CAAC;AAC5J,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AACzC,OAAO,EAAE,YAAY,EAAE,KAAK,EAAE,UAAU,EAAE,MAAM,IAAI,CAAC;AAErD,SAAS,uBAAuB;IAC9B,OAAO;;;;;;;;;;;;;;;;;;;;0YAoBiY,CAAC;AAC3Y,CAAC;AAED,oDAAoD;AACpD,wDAAwD;AACxD,MAAM,UAAU,aAAa,CAAC,MAAiB;IAC7C,MAAM,YAAY,GAAG,MAAM,CAAC,IAAI,CAAC,UAAU,EAAE,mBAAmB,EAAE,cAAc,EAAE,cAAc,CAAC,CAAC;IAClG,MAAM,UAAU,GAAG,MAAM,CAAC,IAAI,CAAC,QAAQ,EAAE,iBAAiB,EAAE,YAAY,EAAE,YAAY,CAAC,CAAC;IACxF,MAAM,CAAC,IAAI,CAAC,QAAQ,EAAE,iBAAiB,EAAE,YAAY,EAAE,YAAY,CAAC,CAAC;IACrE,MAAM,CAAC,IAAI,CAAC,SAAS,EAAE,kBAAkB,EAAE,aAAa,EAAE,aAAa,CAAC,CAAC;IACzE,MAAM,WAAW,GAAG,MAAM,CAAC,IAAI,CAAC,SAAS,EAAE,kBAAkB,EAAE,aAAa,EAAE,aAAa,CAAC,CAAC;IAC7F,MAAM,YAAY,GAAG,MAAM,CAAC,IAAI,CAAC,UAAU,EAAE,mBAAmB,EAAE,cAAc,EAAE,cAAc,CAAC,CAAC;IAClG,MAAM,CAAC,IAAI,CAAC,UAAU,EAAE,mBAAmB,EAAE,cAAc,EAAE,cAAc,CAAC,CAAC;IAC7E,MAAM,CAAC,IAAI,CAAC,MAAM,EAAE,eAAe,EAAE,UAAU,EAAE,UAAU,CAAC,CAAC;IAC7D,MAAM,CAAC,IAAI,CAAC,MAAM,EAAE,eAAe,EAAE,UAAU,EAAE,UAAU,CAAC,CAAC;IAC7D,oBAAoB,CAAC,MAAM,CAAC,CAAC;IAC7B,uBAAuB,CAAC,MAAM,CAAC,CAAC;IAChC,iBAAiB,CAAC,MAAM,CAAC,CAAC;IAC1B,sBAAsB,CAAC,MAAM,CAAC,CAAC;IAC/B,oBAAoB,CAAC,MAAM,CAAC,CAAC;IAC7B,gBAAgB,CAAC,MAAM,CAAC,CAAC;IACzB,qBAAqB,CAAC,MAAM,CAAC,CAAC;IAC9B,kBAAkB,CAAC,MAAM,CAAC,CAAC;IAC3B,OAAO,EAAE,YAAY,EAAE,UAAU,EAAE,WAAW,EAAE,YAAY,EAAE,CAAC;AACjE,CAAC;AAED,iEAAiE;AACjE,MAAM,UAAU,eAAe;IAC7B,MAAM,MAAM,GAAG,IAAI,SAAS,CAC1B,EAAE,IAAI,EAAE,eAAe,EAAE,OAAO,EAAE,OAAO,EAAE,EAC3C,EAAE,YAAY,EAAE,uBAAuB,EAAE,EAAE,CAC5C,CAAC;IACF,aAAa,CAAC,MAAM,CAAC,CAAC;IACtB,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,MAAM,MAAM,GAAG,IAAI,SAAS,CAC1B,EAAE,IAAI,EAAE,eAAe,EAAE,OAAO,EAAE,OAAO,EAAE,EAC3C,EAAE,YAAY,EAAE,uBAAuB,EAAE,EAAE,CAC5C,CAAC;AAEF,MAAM,EAAE,YAAY,EAAE,UAAU,EAAE,WAAW,EAAE,YAAY,EAAE,GAAG,aAAa,CAAC,MAAM,CAAC,CAAC;AAEtF,iEAAiE;AACjE,sEAAsE;AACtE,MAAM,UAAU,sBAAsB;IACpC,uBAAuB,EAAE,CAAC;IAC1B,YAAY,CAAC,MAAM,CAAC,EAAE,YAAY,EAAE,mBAAmB,EAAE,EAAE,CAAC,CAAC;IAC7D,UAAU,CAAC,MAAM,CAAC,EAAE,YAAY,EAAE,iBAAiB,EAAE,EAAE,CAAC,CAAC;IACzD,WAAW,CAAC,MAAM,CAAC,EAAE,YAAY,EAAE,kBAAkB,EAAE,EAAE,CAAC,CAAC;IAC3D,YAAY,CAAC,MAAM,CAAC,EAAE,YAAY,EAAE,mBAAmB,EAAE,EAAE,CAAC,CAAC;AAC/D,CAAC;AAED,KAAK,UAAU,IAAI;IACjB,IAAI,CAAC;QACH,MAAM,cAAc,EAAE,CAAC;IACzB,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,OAAO,CAAC,KAAK,CACX,2DAA2D,EAC3D,GAAG,YAAY,KAAK,CAAC,CAAC,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,GAAG,CACzC,CAAC;IACJ,CAAC;IAED,gEAAgE;IAChE,MAAM,iBAAiB,EAAE,CAAC;IAE1B,oDAAoD;IACpD,mBAAmB,CAAC,GAAG,EAAE;QACvB,OAAO,CAAC,KAAK,CAAC,sDAAsD,CAAC,CAAC;QACtE,sBAAsB,EAAE,CAAC;QACzB,oDAAoD;QACpD,MAAM,CAAC,MAAM,CAAC,YAAY,CAAC;YACzB,MAAM,EAAE,kCAAkC;SAC3C,CAAC,CAAC,KAAK,CAAC,CAAC,GAAG,EAAE,EAAE;YACf,OAAO,CAAC,KAAK,CAAC,iDAAiD,EAAE,GAAG,CAAC,CAAC;QACxE,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IACH,uBAAuB,EAAE,CAAC;IAE1B,2EAA2E;IAC3E,MAAM,OAAO,GAAG,UAAU,EAAE,CAAC;IAC7B,IAAI,UAAU,GAAoC,IAAI,CAAC;IACvD,IAAI,UAAU,CAAC,OAAO,CAAC,EAAE,CAAC;QACxB,eAAe,EAAE,CAAC;IACpB,CAAC;SAAM,CAAC;QACN,sEAAsE;QACtE,MAAM,eAAe,GAAG,WAAW,CAAC,GAAG,EAAE;YACvC,IAAI,UAAU,CAAC,OAAO,CAAC,EAAE,CAAC;gBACxB,aAAa,CAAC,eAAe,CAAC,CAAC;gBAC/B,eAAe,EAAE,CAAC;YACpB,CAAC;QACH,CAAC,EAAE,IAAI,CAAC,CAAC;QACT,eAAe,CAAC,KAAK,EAAE,CAAC;IAC1B,CAAC;IAED,SAAS,eAAe;QACtB,IAAI,CAAC;YACH,IAAI,QAAQ,GAAyC,IAAI,CAAC;YAC1D,UAAU,GAAG,KAAK,CAAC,OAAO,EAAE,GAAG,EAAE;gBAC/B,IAAI,QAAQ;oBAAE,YAAY,CAAC,QAAQ,CAAC,CAAC;gBACrC,QAAQ,GAAG,UAAU,CAAC,GAAG,EAAE;oBACzB,IAAI,CAAC;wBACH,MAAM,OAAO,GAAG,YAAY,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;wBAC/C,MAAM,IAAI,GAA2B,EAAE,CAAC;wBACxC,KAAK,MAAM,IAAI,IAAI,OAAO,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC;4BACvC,MAAM,OAAO,GAAG,IAAI,CAAC,IAAI,EAAE,CAAC;4BAC5B,IAAI,CAAC,OAAO,IAAI,OAAO,CAAC,UAAU,CAAC,GAAG,CAAC;gCAAE,SAAS;4BAClD,MAAM,EAAE,GAAG,OAAO,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;4BAChC,IAAI,EAAE,KAAK,CAAC,CAAC;gCAAE,SAAS;4BACxB,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,GAAG,OAAO,CAAC,KAAK,CAAC,EAAE,GAAG,CAAC,CAAC,CAAC;wBACrD,CAAC;wBACD,MAAM,SAAS,GAAG,IAAI,CAAC,gBAAgB,CAAC,CAAC;wBACzC,MAAM,aAAa,GAAG,OAAO,CAAC,GAAG,CAAC,cAAc,IAAI,EAAE,CAAC;wBACvD,IAAI,SAAS,IAAI,SAAS,KAAK,aAAa,EAAE,CAAC;4BAC7C,OAAO,CAAC,KAAK,CAAC,2BAA2B,aAAa,IAAI,WAAW,MAAM,SAAS,EAAE,CAAC,CAAC;4BACxF,OAAO,CAAC,GAAG,CAAC,cAAc,GAAG,SAAS,CAAC;4BACvC,cAAc,EAAE,CAAC,KAAK,CAAC,CAAC,GAAG,EAAE,EAAE;gCAC7B,OAAO,CAAC,KAAK,CAAC,wCAAwC,EAAE,GAAG,CAAC,CAAC;4BAC/D,CAAC,CAAC,CAAC;wBACL,CAAC;oBACH,CAAC;oBAAC,OAAO,GAAG,EAAE,CAAC;wBACb,OAAO,CAAC,KAAK,CAAC,oBAAoB,EAAE,GAAG,CAAC,CAAC;oBAC3C,CAAC;gBACH,CAAC,EAAE,GAAG,CAAC,CAAC;YACV,CAAC,CAAC,CAAC;QACL,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,OAAO,CAAC,KAAK,CAAC,uBAAuB,EAAE,GAAG,CAAC,CAAC;QAC9C,CAAC;IACH,CAAC;IAED,mBAAmB;IACnB,OAAO,CAAC,EAAE,CAAC,QAAQ,EAAE,GAAG,EAAE;QACxB,IAAI,UAAU;YAAE,UAAU,CAAC,KAAK,EAAE,CAAC;QACnC,sBAAsB,EAAE,CAAC;QACzB,aAAa,EAAE,CAAC;QAChB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC,CAAC,CAAC;IACH,OAAO,CAAC,EAAE,CAAC,SAAS,EAAE,GAAG,EAAE;QACzB,IAAI,UAAU;YAAE,UAAU,CAAC,KAAK,EAAE,CAAC;QACnC,sBAAsB,EAAE,CAAC;QACzB,aAAa,EAAE,CAAC;QAChB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC,CAAC,CAAC;IAEH,MAAM,SAAS,GAAG,IAAI,oBAAoB,EAAE,CAAC;IAC7C,MAAM,MAAM,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;AAClC,CAAC;AAED,8EAA8E;AAC9E,MAAM,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC,QAAQ,CAAC,WAAW,CAAC;OACpE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC,QAAQ,CAAC,aAAa,CAAC,CAAC;AAClE,IAAI,MAAM,EAAE,CAAC;IACX,IAAI,EAAE,CAAC,KAAK,CAAC,CAAC,GAAG,EAAE,EAAE;QACnB,OAAO,CAAC,KAAK,CAAC,qCAAqC,EAAE,GAAG,CAAC,CAAC;QAC1D,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC,CAAC,CAAC;AACL,CAAC"}
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=preload-http.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"preload-http.d.ts","sourceRoot":"","sources":["../src/preload-http.ts"],"names":[],"mappings":""}
@@ -0,0 +1,26 @@
1
+ #!/usr/bin/env node
2
+ /**
3
+ * Preload script for HTTP transport — loads .env then starts the HTTP server.
4
+ */
5
+ import { readFileSync } from 'fs';
6
+ import { resolve, dirname } from 'path';
7
+ import { fileURLToPath } from 'url';
8
+ const __dirname = dirname(fileURLToPath(import.meta.url));
9
+ const envPath = process.env.DOTENV_PATH || resolve(__dirname, '..', '..', '.env');
10
+ try {
11
+ const content = readFileSync(envPath, 'utf-8');
12
+ for (const line of content.split('\n')) {
13
+ const trimmed = line.trim();
14
+ if (!trimmed || trimmed.startsWith('#'))
15
+ continue;
16
+ const eq = trimmed.indexOf('=');
17
+ if (eq === -1)
18
+ continue;
19
+ const key = trimmed.slice(0, eq);
20
+ const val = trimmed.slice(eq + 1);
21
+ process.env[key] = val;
22
+ }
23
+ }
24
+ catch { /* .env not found, rely on existing env vars */ }
25
+ await import('./http.js');
26
+ //# sourceMappingURL=preload-http.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"preload-http.js","sourceRoot":"","sources":["../src/preload-http.ts"],"names":[],"mappings":";AAEA;;GAEG;AACH,OAAO,EAAE,YAAY,EAAE,MAAM,IAAI,CAAC;AAClC,OAAO,EAAE,OAAO,EAAE,OAAO,EAAE,MAAM,MAAM,CAAC;AACxC,OAAO,EAAE,aAAa,EAAE,MAAM,KAAK,CAAC;AAEpC,MAAM,SAAS,GAAG,OAAO,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC;AAC1D,MAAM,OAAO,GAAG,OAAO,CAAC,GAAG,CAAC,WAAW,IAAI,OAAO,CAAC,SAAS,EAAE,IAAI,EAAE,IAAI,EAAE,MAAM,CAAC,CAAC;AAClF,IAAI,CAAC;IACH,MAAM,OAAO,GAAG,YAAY,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;IAC/C,KAAK,MAAM,IAAI,IAAI,OAAO,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC;QACvC,MAAM,OAAO,GAAG,IAAI,CAAC,IAAI,EAAE,CAAC;QAC5B,IAAI,CAAC,OAAO,IAAI,OAAO,CAAC,UAAU,CAAC,GAAG,CAAC;YAAE,SAAS;QAClD,MAAM,EAAE,GAAG,OAAO,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;QAChC,IAAI,EAAE,KAAK,CAAC,CAAC;YAAE,SAAS;QACxB,MAAM,GAAG,GAAG,OAAO,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;QACjC,MAAM,GAAG,GAAG,OAAO,CAAC,KAAK,CAAC,EAAE,GAAG,CAAC,CAAC,CAAC;QAClC,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,GAAG,CAAC;IACzB,CAAC;AACH,CAAC;AAAC,MAAM,CAAC,CAAC,+CAA+C,CAAC,CAAC;AAE3D,MAAM,MAAM,CAAC,WAAW,CAAC,CAAC"}
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=preload.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"preload.d.ts","sourceRoot":"","sources":["../src/preload.ts"],"names":[],"mappings":""}