myaiforone 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (315) hide show
  1. package/README.md +113 -0
  2. package/agents/_template/CLAUDE.md +18 -0
  3. package/agents/_template/agent.json +7 -0
  4. package/agents/platform/agentcreator/CLAUDE.md +300 -0
  5. package/agents/platform/appcreator/CLAUDE.md +158 -0
  6. package/agents/platform/gym/CLAUDE.md +486 -0
  7. package/agents/platform/gym/agent.json +40 -0
  8. package/agents/platform/gym/programs/agent-building/program.json +160 -0
  9. package/agents/platform/gym/programs/automations-mastery/program.json +129 -0
  10. package/agents/platform/gym/programs/getting-started/program.json +124 -0
  11. package/agents/platform/gym/programs/mcp-integrations/program.json +116 -0
  12. package/agents/platform/gym/programs/multi-model-strategy/program.json +115 -0
  13. package/agents/platform/gym/programs/prompt-engineering/program.json +136 -0
  14. package/agents/platform/gym/souls/alex.md +12 -0
  15. package/agents/platform/gym/souls/jordan.md +12 -0
  16. package/agents/platform/gym/souls/morgan.md +12 -0
  17. package/agents/platform/gym/souls/riley.md +12 -0
  18. package/agents/platform/gym/souls/sam.md +12 -0
  19. package/agents/platform/hub/CLAUDE.md +372 -0
  20. package/agents/platform/promptcreator/CLAUDE.md +130 -0
  21. package/agents/platform/skillcreator/CLAUDE.md +163 -0
  22. package/bin/cli.js +566 -0
  23. package/config.example.json +310 -0
  24. package/dist/agent-registry.d.ts +32 -0
  25. package/dist/agent-registry.d.ts.map +1 -0
  26. package/dist/agent-registry.js +144 -0
  27. package/dist/agent-registry.js.map +1 -0
  28. package/dist/channels/discord.d.ts +17 -0
  29. package/dist/channels/discord.d.ts.map +1 -0
  30. package/dist/channels/discord.js +114 -0
  31. package/dist/channels/discord.js.map +1 -0
  32. package/dist/channels/imessage.d.ts +23 -0
  33. package/dist/channels/imessage.d.ts.map +1 -0
  34. package/dist/channels/imessage.js +214 -0
  35. package/dist/channels/imessage.js.map +1 -0
  36. package/dist/channels/slack.d.ts +19 -0
  37. package/dist/channels/slack.d.ts.map +1 -0
  38. package/dist/channels/slack.js +167 -0
  39. package/dist/channels/slack.js.map +1 -0
  40. package/dist/channels/telegram.d.ts +19 -0
  41. package/dist/channels/telegram.d.ts.map +1 -0
  42. package/dist/channels/telegram.js +274 -0
  43. package/dist/channels/telegram.js.map +1 -0
  44. package/dist/channels/types.d.ts +44 -0
  45. package/dist/channels/types.d.ts.map +1 -0
  46. package/dist/channels/types.js +18 -0
  47. package/dist/channels/types.js.map +1 -0
  48. package/dist/channels/whatsapp.d.ts +23 -0
  49. package/dist/channels/whatsapp.d.ts.map +1 -0
  50. package/dist/channels/whatsapp.js +189 -0
  51. package/dist/channels/whatsapp.js.map +1 -0
  52. package/dist/config.d.ts +134 -0
  53. package/dist/config.d.ts.map +1 -0
  54. package/dist/config.js +127 -0
  55. package/dist/config.js.map +1 -0
  56. package/dist/cron.d.ts +8 -0
  57. package/dist/cron.d.ts.map +1 -0
  58. package/dist/cron.js +35 -0
  59. package/dist/cron.js.map +1 -0
  60. package/dist/decrypt-keys.d.ts +7 -0
  61. package/dist/decrypt-keys.d.ts.map +1 -0
  62. package/dist/decrypt-keys.js +53 -0
  63. package/dist/decrypt-keys.js.map +1 -0
  64. package/dist/encrypt-keys.d.ts +8 -0
  65. package/dist/encrypt-keys.d.ts.map +1 -0
  66. package/dist/encrypt-keys.js +62 -0
  67. package/dist/encrypt-keys.js.map +1 -0
  68. package/dist/executor.d.ts +31 -0
  69. package/dist/executor.d.ts.map +1 -0
  70. package/dist/executor.js +2009 -0
  71. package/dist/executor.js.map +1 -0
  72. package/dist/gemini-executor.d.ts +27 -0
  73. package/dist/gemini-executor.d.ts.map +1 -0
  74. package/dist/gemini-executor.js +160 -0
  75. package/dist/gemini-executor.js.map +1 -0
  76. package/dist/goals.d.ts +24 -0
  77. package/dist/goals.d.ts.map +1 -0
  78. package/dist/goals.js +189 -0
  79. package/dist/goals.js.map +1 -0
  80. package/dist/gym/activity-digest.d.ts +30 -0
  81. package/dist/gym/activity-digest.d.ts.map +1 -0
  82. package/dist/gym/activity-digest.js +506 -0
  83. package/dist/gym/activity-digest.js.map +1 -0
  84. package/dist/gym/dimension-scorer.d.ts +76 -0
  85. package/dist/gym/dimension-scorer.d.ts.map +1 -0
  86. package/dist/gym/dimension-scorer.js +236 -0
  87. package/dist/gym/dimension-scorer.js.map +1 -0
  88. package/dist/gym/gym-router.d.ts +7 -0
  89. package/dist/gym/gym-router.d.ts.map +1 -0
  90. package/dist/gym/gym-router.js +718 -0
  91. package/dist/gym/gym-router.js.map +1 -0
  92. package/dist/gym/index.d.ts +11 -0
  93. package/dist/gym/index.d.ts.map +1 -0
  94. package/dist/gym/index.js +11 -0
  95. package/dist/gym/index.js.map +1 -0
  96. package/dist/heartbeat.d.ts +21 -0
  97. package/dist/heartbeat.d.ts.map +1 -0
  98. package/dist/heartbeat.js +163 -0
  99. package/dist/heartbeat.js.map +1 -0
  100. package/dist/index.d.ts +2 -0
  101. package/dist/index.d.ts.map +1 -0
  102. package/dist/index.js +254 -0
  103. package/dist/index.js.map +1 -0
  104. package/dist/keystore.d.ts +22 -0
  105. package/dist/keystore.d.ts.map +1 -0
  106. package/dist/keystore.js +178 -0
  107. package/dist/keystore.js.map +1 -0
  108. package/dist/logger.d.ts +9 -0
  109. package/dist/logger.d.ts.map +1 -0
  110. package/dist/logger.js +45 -0
  111. package/dist/logger.js.map +1 -0
  112. package/dist/memory/daily.d.ts +22 -0
  113. package/dist/memory/daily.d.ts.map +1 -0
  114. package/dist/memory/daily.js +82 -0
  115. package/dist/memory/daily.js.map +1 -0
  116. package/dist/memory/embeddings.d.ts +15 -0
  117. package/dist/memory/embeddings.d.ts.map +1 -0
  118. package/dist/memory/embeddings.js +154 -0
  119. package/dist/memory/embeddings.js.map +1 -0
  120. package/dist/memory/index.d.ts +32 -0
  121. package/dist/memory/index.d.ts.map +1 -0
  122. package/dist/memory/index.js +159 -0
  123. package/dist/memory/index.js.map +1 -0
  124. package/dist/memory/search.d.ts +21 -0
  125. package/dist/memory/search.d.ts.map +1 -0
  126. package/dist/memory/search.js +77 -0
  127. package/dist/memory/search.js.map +1 -0
  128. package/dist/memory/store.d.ts +23 -0
  129. package/dist/memory/store.d.ts.map +1 -0
  130. package/dist/memory/store.js +144 -0
  131. package/dist/memory/store.js.map +1 -0
  132. package/dist/ollama-executor.d.ts +17 -0
  133. package/dist/ollama-executor.d.ts.map +1 -0
  134. package/dist/ollama-executor.js +112 -0
  135. package/dist/ollama-executor.js.map +1 -0
  136. package/dist/openai-executor.d.ts +38 -0
  137. package/dist/openai-executor.d.ts.map +1 -0
  138. package/dist/openai-executor.js +197 -0
  139. package/dist/openai-executor.js.map +1 -0
  140. package/dist/router.d.ts +11 -0
  141. package/dist/router.d.ts.map +1 -0
  142. package/dist/router.js +185 -0
  143. package/dist/router.js.map +1 -0
  144. package/dist/test-message.d.ts +2 -0
  145. package/dist/test-message.d.ts.map +1 -0
  146. package/dist/test-message.js +60 -0
  147. package/dist/test-message.js.map +1 -0
  148. package/dist/utils/imsg-db-reader.d.ts +24 -0
  149. package/dist/utils/imsg-db-reader.d.ts.map +1 -0
  150. package/dist/utils/imsg-db-reader.js +92 -0
  151. package/dist/utils/imsg-db-reader.js.map +1 -0
  152. package/dist/utils/imsg-rpc.d.ts +25 -0
  153. package/dist/utils/imsg-rpc.d.ts.map +1 -0
  154. package/dist/utils/imsg-rpc.js +149 -0
  155. package/dist/utils/imsg-rpc.js.map +1 -0
  156. package/dist/utils/message-formatter.d.ts +3 -0
  157. package/dist/utils/message-formatter.d.ts.map +1 -0
  158. package/dist/utils/message-formatter.js +69 -0
  159. package/dist/utils/message-formatter.js.map +1 -0
  160. package/dist/web-ui.d.ts +12 -0
  161. package/dist/web-ui.d.ts.map +1 -0
  162. package/dist/web-ui.js +5784 -0
  163. package/dist/web-ui.js.map +1 -0
  164. package/dist/whatsapp-chats.d.ts +2 -0
  165. package/dist/whatsapp-chats.d.ts.map +1 -0
  166. package/dist/whatsapp-chats.js +76 -0
  167. package/dist/whatsapp-chats.js.map +1 -0
  168. package/dist/whatsapp-login.d.ts +2 -0
  169. package/dist/whatsapp-login.d.ts.map +1 -0
  170. package/dist/whatsapp-login.js +90 -0
  171. package/dist/whatsapp-login.js.map +1 -0
  172. package/dist/wiki-sync.d.ts +21 -0
  173. package/dist/wiki-sync.d.ts.map +1 -0
  174. package/dist/wiki-sync.js +147 -0
  175. package/dist/wiki-sync.js.map +1 -0
  176. package/docs/AddNewAgentGuide.md +100 -0
  177. package/docs/AddNewMcpGuide.md +72 -0
  178. package/docs/Architecture.md +795 -0
  179. package/docs/CLAUDE-AI-SETUP.md +166 -0
  180. package/docs/Setup.md +297 -0
  181. package/docs/ai-gym-architecture.md +1040 -0
  182. package/docs/ai-gym-build-plan.md +343 -0
  183. package/docs/ai-gym-onboarding.md +122 -0
  184. package/docs/appcreator_plan.md +348 -0
  185. package/docs/platform-mcp-audit.md +320 -0
  186. package/docs/server-deployment-plan.md +503 -0
  187. package/docs/superpowers/plans/2026-03-25-marketplace.md +1281 -0
  188. package/docs/superpowers/specs/2026-03-25-marketplace-design.md +287 -0
  189. package/docs/user-guide.md +2016 -0
  190. package/mcp-catalog.json +628 -0
  191. package/package.json +63 -0
  192. package/public/MyAIforOne-logomark-512.svg +16 -0
  193. package/public/MyAIforOne-logomark-transparent.svg +15 -0
  194. package/public/activity.html +314 -0
  195. package/public/admin.html +1674 -0
  196. package/public/agent-dashboard.html +670 -0
  197. package/public/api-docs.html +1106 -0
  198. package/public/automations.html +722 -0
  199. package/public/canvas.css +223 -0
  200. package/public/canvas.js +588 -0
  201. package/public/changelog.html +231 -0
  202. package/public/gym.html +2766 -0
  203. package/public/home.html +1930 -0
  204. package/public/index.html +2809 -0
  205. package/public/lab.html +1643 -0
  206. package/public/library.html +1442 -0
  207. package/public/marketplace.html +1101 -0
  208. package/public/mcp-docs.html +441 -0
  209. package/public/mini.html +390 -0
  210. package/public/monitor.html +584 -0
  211. package/public/org.html +4304 -0
  212. package/public/projects.html +734 -0
  213. package/public/settings.html +645 -0
  214. package/public/tasks.html +932 -0
  215. package/public/trainers/alex.svg +12 -0
  216. package/public/trainers/jordan.svg +12 -0
  217. package/public/trainers/morgan.svg +12 -0
  218. package/public/trainers/riley.svg +12 -0
  219. package/public/trainers/sam.svg +12 -0
  220. package/public/user-guide.html +218 -0
  221. package/registry/agents.json +3 -0
  222. package/registry/apps.json +20 -0
  223. package/registry/installed-drafts.json +3 -0
  224. package/registry/mcps.json +1084 -0
  225. package/registry/prompts/personal/mcp-test-prompt.md +6 -0
  226. package/registry/prompts/personal/memory-recall.md +6 -0
  227. package/registry/prompts/platform/brainstorm.md +15 -0
  228. package/registry/prompts/platform/code-review.md +16 -0
  229. package/registry/prompts/platform/explain.md +16 -0
  230. package/registry/prompts.json +58 -0
  231. package/registry/skills/external/brainstorming.md +5 -0
  232. package/registry/skills/external/code-review.md +40 -0
  233. package/registry/skills/external/frontend-patterns.md +642 -0
  234. package/registry/skills/external/frontend-slides.md +184 -0
  235. package/registry/skills/external/systematic-debugging.md +5 -0
  236. package/registry/skills/external/tdd.md +328 -0
  237. package/registry/skills/external/verification-before-completion.md +5 -0
  238. package/registry/skills/external/writing-plans.md +5 -0
  239. package/registry/skills/platform/ai41_app_build.md +930 -0
  240. package/registry/skills/platform/ai41_app_deploy.md +168 -0
  241. package/registry/skills/platform/ai41_app_orchestrator.md +239 -0
  242. package/registry/skills/platform/ai41_app_patterns.md +359 -0
  243. package/registry/skills/platform/ai41_app_register.md +85 -0
  244. package/registry/skills/platform/ai41_app_scaffold.md +421 -0
  245. package/registry/skills/platform/ai41_app_verify.md +107 -0
  246. package/registry/skills/platform/opProjectCreate.md +239 -0
  247. package/registry/skills/platform/op_devbrowser.md +136 -0
  248. package/registry/skills/platform/sop_brandguidelines.md +103 -0
  249. package/registry/skills/platform/sop_docx.md +117 -0
  250. package/registry/skills/platform/sop_frontenddesign.md +44 -0
  251. package/registry/skills/platform/sop_frontenddesign_v2.md +659 -0
  252. package/registry/skills/platform/sop_mcpbuilder.md +133 -0
  253. package/registry/skills/platform/sop_pdf.md +172 -0
  254. package/registry/skills/platform/sop_pptx.md +133 -0
  255. package/registry/skills/platform/sop_skillcreator.md +104 -0
  256. package/registry/skills/platform/sop_themefactory.md +128 -0
  257. package/registry/skills/platform/sop_webapptesting.md +75 -0
  258. package/registry/skills/platform/sop_webartifactsbuilder.md +97 -0
  259. package/registry/skills/platform/sop_xlsx.md +134 -0
  260. package/registry/skills.json +1055 -0
  261. package/scripts/discover-chats.sh +11 -0
  262. package/scripts/install-service-windows.ps1 +87 -0
  263. package/scripts/install-service.sh +52 -0
  264. package/scripts/seed-registry.ts +195 -0
  265. package/scripts/test-send.sh +5 -0
  266. package/scripts/tray-indicator.ps1 +35 -0
  267. package/scripts/uninstall-service-windows.ps1 +23 -0
  268. package/scripts/uninstall-service.sh +15 -0
  269. package/scripts/xbar-myagent.5s.sh +32 -0
  270. package/server/mcp-server/dist/index.d.ts +11 -0
  271. package/server/mcp-server/dist/index.js +1332 -0
  272. package/server/mcp-server/dist/lib/api-client.d.ts +165 -0
  273. package/server/mcp-server/dist/lib/api-client.js +241 -0
  274. package/server/mcp-server/index.ts +1545 -0
  275. package/server/mcp-server/lib/api-client.ts +366 -0
  276. package/server/mcp-server/tsconfig.json +14 -0
  277. package/src/agent-registry.ts +180 -0
  278. package/src/channels/discord.ts +129 -0
  279. package/src/channels/imessage.ts +261 -0
  280. package/src/channels/slack.ts +208 -0
  281. package/src/channels/telegram.ts +307 -0
  282. package/src/channels/types.ts +62 -0
  283. package/src/channels/whatsapp.ts +227 -0
  284. package/src/config.ts +281 -0
  285. package/src/cron.ts +43 -0
  286. package/src/decrypt-keys.ts +60 -0
  287. package/src/encrypt-keys.ts +70 -0
  288. package/src/executor.ts +2190 -0
  289. package/src/gemini-executor.ts +212 -0
  290. package/src/goals.ts +240 -0
  291. package/src/gym/activity-digest.ts +546 -0
  292. package/src/gym/dimension-scorer.ts +297 -0
  293. package/src/gym/gym-router.ts +801 -0
  294. package/src/gym/index.ts +19 -0
  295. package/src/heartbeat.ts +220 -0
  296. package/src/index.ts +275 -0
  297. package/src/keystore.ts +190 -0
  298. package/src/logger.ts +51 -0
  299. package/src/memory/daily.ts +101 -0
  300. package/src/memory/embeddings.ts +185 -0
  301. package/src/memory/index.ts +218 -0
  302. package/src/memory/search.ts +124 -0
  303. package/src/memory/store.ts +189 -0
  304. package/src/ollama-executor.ts +126 -0
  305. package/src/openai-executor.ts +259 -0
  306. package/src/router.ts +230 -0
  307. package/src/test-message.ts +72 -0
  308. package/src/utils/imsg-db-reader.ts +109 -0
  309. package/src/utils/imsg-rpc.ts +178 -0
  310. package/src/utils/message-formatter.ts +90 -0
  311. package/src/web-ui.ts +5778 -0
  312. package/src/whatsapp-chats.ts +91 -0
  313. package/src/whatsapp-login.ts +110 -0
  314. package/src/wiki-sync.ts +199 -0
  315. package/tsconfig.json +19 -0
@@ -0,0 +1,795 @@
1
+ # MyAgent — Architecture
2
+
3
+ ## What This Is
4
+
5
+ A gateway that lets you communicate with Claude Code sessions from your phone via Slack, iMessage, Telegram, Discord, and WhatsApp. Each "agent" is a persistent Claude Code session with a defined purpose, scoped tools, MCPs, and skills — accessed by @mentioning an alias in a chat.
6
+
7
+ Everything runs as a single Node.js process on your Mac, managed by launchd.
8
+
9
+ ## How It Works
10
+
11
+ ```
12
+ Phone → Slack/iMessage/Telegram/Discord → internet → your Mac (gateway) → claude -p → response → back to phone
13
+ ```
14
+
15
+ 1. You send a message from your phone (e.g., `@agentmgr what's in my Bobby project?`)
16
+ 2. The gateway service running on your Mac detects the message
17
+ 3. The router checks pairing (if enabled), then matches channel + chat ID + @mention alias to an agent
18
+ 4. The executor spawns `claude -p` with the agent's system prompt, workspace, MCPs, and tools
19
+ 5. For streaming agents, real-time status updates and text stream back via SSE
20
+ 6. Long responses are automatically chunked to fit channel limits
21
+ 7. The response is sent back to the originating channel
22
+ 8. The process exits, but the **session persists** — next message resumes where you left off
23
+
24
+ ## Channels
25
+
26
+ | Channel | Library | Auth | How it connects |
27
+ |---------|---------|------|-----------------|
28
+ | **Slack** | @slack/socket-mode | Bot + App tokens | Outbound WebSocket (no public URL needed) |
29
+ | **Telegram** | grammY | Bot token from @BotFather | Long polling (no public URL needed) |
30
+ | **iMessage** | imsg CLI | Local macOS access | Watches Messages database via JSON-RPC subprocess |
31
+ | **Discord** | discord.js | Bot token | Outbound WebSocket (no public URL needed) |
32
+ | **WhatsApp** | @whiskeysockets/baileys | QR code pairing | WhatsApp Web protocol (unofficial) |
33
+
34
+ All channels connect outbound from your Mac — no inbound ports need to be exposed to the internet.
35
+
36
+ ## Agents = Scoped Sessions
37
+
38
+ An agent is not a different AI. It's the **same Claude** with different guardrails per session:
39
+
40
+ | What the agent defines | Example |
41
+ |------------------------|---------|
42
+ | **Purpose** (system prompt) | "You manage the financeiscooked show content" |
43
+ | **Workspace** (file access) | `~/Desktop/APPs/financeiscooked` |
44
+ | **MCPs** (API integrations) | financeiscooked platform API, context7 |
45
+ | **Tools** (what Claude can do) | Read, Edit, Write, Bash — or read-only |
46
+ | **Skills** (indexed instructions) | opcodereview, sop_pdf, etc. |
47
+ | **Session** (conversation memory) | Persistent UUID-based session with full history |
48
+ | **Streaming** (real-time output) | Tool status updates + live text in Web UI |
49
+ | **Org** (team structure) | Organization, department, title, reporting chain |
50
+
51
+ Multiple agents can share the same Slack channel, Telegram group, or iMessage thread — they're differentiated by their @mention alias (e.g., `@producer` vs `@oldproducer` vs `@agentmgr`).
52
+
53
+ ### Sticky Routing
54
+
55
+ After you @mention an agent, follow-up messages without a mention automatically route to the same agent for 5 minutes. This lets you have a natural conversation without typing the alias every message.
56
+
57
+ - `@bobby check the build` → routes to bobby, starts 5-min timer
58
+ - "what about the tests?" → still bobby (within 5 min)
59
+ - "looks good" → still bobby
60
+ - (5 minutes of silence) → timer expires, next message needs a mention
61
+
62
+ Each sender has their own sticky — Alice talking to `@bobby` doesn't affect Bob's messages.
63
+
64
+ Configure per channel:
65
+ ```json
66
+ "telegram": {
67
+ "config": {
68
+ "stickyRouting": true,
69
+ "stickyTimeoutMs": 300000
70
+ }
71
+ }
72
+ ```
73
+
74
+ Defaults: `stickyRouting: true`, `stickyTimeoutMs: 300000` (5 min). Set `stickyRouting: false` to require @mention on every message.
75
+
76
+ ## Session Persistence
77
+
78
+ Agents can be **persistent**, **streaming**, or **single-shot**:
79
+
80
+ ### Persistent (`"persistent": true`)
81
+ - First message generates a UUID and creates a Claude Code session via `--session-id`
82
+ - Every subsequent message resumes the session via `--resume <uuid>`
83
+ - Claude maintains full conversation history — it remembers everything you've discussed
84
+ - Session state stored by Claude Code in `~/.claude/projects/` (not configurable)
85
+ - A pointer (UUID) stored in the agent's `memory/session.json`
86
+ - Claude Code handles context compression automatically as sessions grow
87
+
88
+ ### Streaming (`"streaming": true`)
89
+ - Uses `--output-format stream-json --verbose` to get real-time output
90
+ - **Web UI**: Streams text live via SSE as Claude writes. Shows tool status ("Using Read...", "Using Bash...") in the thinking indicator
91
+ - **Phone channels**: Sends typing indicators while processing. Final response sent when done
92
+ - Session management works the same as persistent (sessions are maintained)
93
+ - If `persistent` is also true, sessions resume across messages with streaming output
94
+
95
+ ### Per-Sender Sessions (`"perSenderSessions": true`)
96
+ - Each sender gets their own isolated session file (`session-<senderId>.json`)
97
+ - Useful when multiple people talk to the same agent — each gets a private conversation thread
98
+ - Requires `persistent: true` to have any effect
99
+
100
+ ### Single-shot (`"persistent": false`, the default)
101
+ - Every message is a fresh Claude invocation
102
+ - Last 5 messages from `conversation_log.jsonl` injected as text context
103
+ - No session continuity beyond that
104
+
105
+ ### Session Lifecycle Commands
106
+ - **`/opcompact <what to save>`** — Tell the agent to save important information to `context.md`. This context survives session resets and is injected into the system prompt of new sessions.
107
+ - **`/opreset`** — Clear the session. Deletes session file, next message starts fresh. The agent's identity (CLAUDE.md) and saved context (context.md) remain.
108
+
109
+ ## Advanced Memory
110
+
111
+ When `"advancedMemory": true` is set on an agent, it gets a semantic long-term memory system that goes beyond basic session persistence and `context.md`. This is the recommended default for general-purpose agents.
112
+
113
+ ### How It Differs from Basic Memory
114
+
115
+ | Feature | Basic (persistent session) | Advanced Memory |
116
+ |---------|---------------------------|-----------------|
117
+ | **Short-term** | Claude session history | Same — session history |
118
+ | **Long-term** | Manual `/opcompact` → `context.md` | Automatic daily journals + semantic recall |
119
+ | **Recall** | Full `context.md` injected every time | Relevant memories retrieved by similarity search |
120
+ | **Scaling** | `context.md` grows until you edit it | Old entries auto-compact; vector search stays fast |
121
+
122
+ ### Daily Memory
123
+
124
+ Memories are stored as markdown files in `memory/daily/YYYY-MM-DD.md` inside the agent's memory directory. Each day gets its own file with timestamped entries.
125
+
126
+ At the start of every conversation turn, the system automatically loads **today's** and **yesterday's** daily files as immediate context, so the agent always knows what happened recently.
127
+
128
+ ### Semantic Search
129
+
130
+ When the agent needs to recall something older than yesterday, it searches the memory store using a **hybrid retrieval** strategy:
131
+
132
+ 1. **Cosine similarity** — vector dot-product against stored embeddings
133
+ 2. **BM25 keyword scoring** — term-frequency weighting for exact-match recall
134
+ 3. **Temporal decay** — recent memories get a relevance boost over older ones
135
+
136
+ The three scores are combined into a single ranking. Top results are injected into the prompt as recalled context.
137
+
138
+ ### Embedding Providers
139
+
140
+ - **OpenAI** (default when `OPENAI_API_KEY` is set) — uses `text-embedding-3-small` for high-quality vectors
141
+ - **TF-IDF fallback** — if no OpenAI key is available, a local TF-IDF vectorizer generates embeddings with no external calls
142
+
143
+ ### Vector Store
144
+
145
+ - **JSON** (default) — stores embeddings in a JSON file in the memory directory. Zero dependencies.
146
+ - **SQLite** (auto-upgrade) — when the JSON store grows past a threshold, it automatically migrates to SQLite for faster lookups.
147
+
148
+ ### Auto-Compaction
149
+
150
+ To prevent unbounded context growth, advanced memory monitors conversation length:
151
+
152
+ - **Warning at 20 messages** — the agent is nudged to summarize and save important context to daily memory
153
+ - **Forced compaction at 40 messages** — the system automatically triggers a compaction, writing a summary to daily memory and resetting the conversation
154
+
155
+ ### Config Flag
156
+
157
+ Enable on any agent:
158
+ ```json
159
+ "advancedMemory": true
160
+ ```
161
+
162
+ No additional configuration needed. The embedding provider and vector store are auto-detected based on available environment variables and data size.
163
+
164
+ ## Organization & Team Structure
165
+
166
+ Agents can be placed in an organizational hierarchy for the Org Chart dashboard:
167
+
168
+ ```json
169
+ "org": [
170
+ { "organization": "Finance Is Cooked", "function": "Content Production", "title": "Show Producer", "reportsTo": "@agentmgr" },
171
+ { "organization": "Personal", "function": "Operations", "title": "General Manager" }
172
+ ]
173
+ ```
174
+
175
+ - **organization** — Which org this agent belongs to (agents can be in multiple orgs)
176
+ - **function** — Department/team label (shown as a tag on the agent card)
177
+ - **title** — Role title (shown above the agent name)
178
+ - **reportsTo** — Alias of the agent this one reports to (drives the hierarchy tree)
179
+
180
+ The Org Chart page (`/org`) visualizes this:
181
+ - Dropdown to select an organization
182
+ - Tree hierarchy driven by `reportsTo` — agents without a `reportsTo` sit at the top
183
+ - Department shown as a purple tag on each card
184
+ - Heartbeat animation on active agents (green ❤ pulsing top-right)
185
+ - "All Agents" view groups agents by organization with section headers
186
+ - Click any agent to Chat or view Config
187
+
188
+ ## Multi-Account Support
189
+
190
+ Multiple Anthropic accounts — each with their own Claude Code subscription — can be assigned to different agents. This lets you spread usage across subscriptions, isolate billing, or use different plan tiers per agent type.
191
+
192
+ ### How It Works
193
+
194
+ Each account is a separate Claude Code login, isolated by pointing `CLAUDE_CONFIG_DIR` to a dedicated config directory. When the gateway spawns `claude -p` for an agent, it sets `CLAUDE_CONFIG_DIR` to the directory for that agent's assigned account so Claude authenticates as the correct subscription.
195
+
196
+ ### Setup
197
+
198
+ One-time login per account:
199
+
200
+ ```bash
201
+ CLAUDE_CONFIG_DIR=~/.claude-account-X claude
202
+ # then run /login inside the session to authenticate
203
+ ```
204
+
205
+ Repeat for each account (`~/.claude-account-1`, `~/.claude-account-2`, etc.). Each directory holds its own credentials independently.
206
+
207
+ ### Config
208
+
209
+ Register accounts in the service block, then assign them to agents:
210
+
211
+ ```json
212
+ "service": {
213
+ "claudeAccounts": {
214
+ "main": { "configDir": "~/.claude" },
215
+ "account2": { "configDir": "~/.claude-account-2" },
216
+ "account3": { "configDir": "~/.claude-account-3" }
217
+ }
218
+ }
219
+ ```
220
+
221
+ Per agent, set the default account:
222
+
223
+ ```json
224
+ "claudeAccount": "account2"
225
+ ```
226
+
227
+ If omitted, the agent uses the default Claude config directory (no `CLAUDE_CONFIG_DIR` override).
228
+
229
+ ### UI
230
+
231
+ - **Chat header dropdown** — switch the active account for an agent on the fly (in-memory override, does not persist to config)
232
+ - **Agent edit modal dropdown** — set the default account for an agent (persisted to config)
233
+
234
+ ### The `/relogin` Command
235
+
236
+ If an account's session expires mid-conversation, send `/relogin` in chat. The gateway will prompt you through re-authentication for the agent's assigned account without leaving the chat interface.
237
+
238
+ ### Use Cases
239
+
240
+ | Scenario | How |
241
+ |----------|-----|
242
+ | **Spread usage** | Assign high-traffic agents to separate subscriptions to avoid rate limits |
243
+ | **Isolate billing** | Give each team or project its own account for clean cost attribution |
244
+ | **Different plan tiers** | Use a Pro account for lightweight agents, Max for heavy autonomous ones |
245
+
246
+ ## Multi-Model Executor
247
+
248
+ When `multiModelEnabled: true` is set in the service config, agents can use open-source models via Ollama instead of Claude Code.
249
+
250
+ ### Executor Dispatch
251
+
252
+ The executor resolves which backend to use via a four-step fallback chain:
253
+
254
+ 1. **`multiModelEnabled`** — if `false` (default), all agents use Claude. Full stop.
255
+ 2. **Per-agent `executor` field** — e.g., `"executor": "ollama:gemma2"` overrides everything for that agent.
256
+ 3. **`platformDefaultExecutor`** — service-level default (e.g., `"ollama:llama3"`) applied when an agent has no `executor` field.
257
+ 4. **Hard default** — if none of the above are set, the agent uses `claude -p`.
258
+
259
+ ### Two Executor Paths
260
+
261
+ | | Claude | Ollama |
262
+ |--|--------|--------|
263
+ | **Trigger** | `executor` is unset or `"claude"` | `executor` starts with `"ollama:"` |
264
+ | **How it runs** | Spawns `claude -p` with system prompt, workspace, allowed tools, MCP config, and session flags | HTTP POST to Ollama API (`/api/chat`) at `service.ollamaBaseUrl` (default `http://localhost:11434`) |
265
+ | **Tool use** | Full — Read, Write, Bash, Glob, Grep, etc. | None |
266
+ | **MCP access** | Yes — temp `.mcp.json` generated and passed via `--mcp-config` | None |
267
+ | **Sessions** | Persistent via `--session-id` / `--resume` | None — each message is stateless |
268
+ | **Streaming** | Yes — `--output-format stream-json` | Text response only |
269
+
270
+ ### Ollama Limitations
271
+
272
+ Ollama-backed agents are **text-in / text-out only**. They cannot use tools (Read, Write, Bash), MCP servers, persistent sessions, or streaming. This makes them suitable for Q&A, content generation, and advisory roles — not for agents that need to read files, run commands, or call APIs.
273
+
274
+ ### Health Check
275
+
276
+ Before dispatching to Ollama, the executor calls `checkOllamaHealth()` which:
277
+
278
+ 1. Hits `GET /api/tags` on the Ollama server to confirm it is reachable
279
+ 2. Checks that the requested model (e.g., `gemma2`) is in the list of locally available models
280
+ 3. Returns an error message to the user if either check fails, rather than silently failing
281
+
282
+ ### Model Override API
283
+
284
+ Agents can have their executor model changed at runtime without editing `config.json`:
285
+
286
+ | Endpoint | Method | Description |
287
+ |----------|--------|-------------|
288
+ | `/api/agents/:agentId/model` | GET | Returns the agent's current executor model |
289
+ | `/api/agents/:agentId/model` | PUT | Sets the executor model (e.g., `{ "executor": "ollama:gemma2" }`) |
290
+ | `/api/agents/:agentId/model` | DELETE | Clears the per-agent override, reverting to platform default |
291
+
292
+ MCP tools provide the same functionality for agent-to-agent use:
293
+
294
+ | Tool | Description |
295
+ |------|-------------|
296
+ | `get_model` | Read the current executor for an agent |
297
+ | `set_model` | Set an agent's executor (e.g., `"ollama:gemma2"` or `"claude"`) |
298
+ | `clear_model` | Remove the per-agent override |
299
+
300
+ ### Config
301
+
302
+ Service-level settings:
303
+ ```json
304
+ "service": {
305
+ "multiModelEnabled": true,
306
+ "platformDefaultExecutor": "claude",
307
+ "ollamaBaseUrl": "http://localhost:11434"
308
+ }
309
+ ```
310
+
311
+ Per-agent override:
312
+ ```json
313
+ "executor": "ollama:gemma2"
314
+ ```
315
+
316
+ When `multiModelEnabled` is `false` (the default), the entire Ollama path is disabled. All agents use `claude -p` regardless of their `executor` field.
317
+
318
+ ## Skills
319
+
320
+ Skills are markdown instruction files in `~/.claude/commands/`. In an interactive terminal session, Claude loads these via the `Skill` tool. Since `claude -p` doesn't have the `Skill` tool, the gateway uses a workaround:
321
+
322
+ 1. A **skill index** (name + description + file path) is appended to the agent's system prompt
323
+ 2. The skills directory is added via `--add-dir ~/.claude/commands/`
324
+ 3. When a task matches a skill, the agent uses the `Read` tool to load the full skill file and follows its instructions
325
+
326
+ Configure per agent: `"skills": ["opcodereview", "sop_pdf", "opAgents_AddNew"]`
327
+
328
+ ## MCPs (Model Context Protocol)
329
+
330
+ MCP servers are registered once in the top-level `mcps` block of `config.json`, then referenced by name in each agent's config. The gateway:
331
+
332
+ 1. Reads the agent's MCP list
333
+ 2. Generates a temporary `.mcp.json` file with the server configs
334
+ 3. Passes `--mcp-config <path> --strict-mcp-config` to `claude -p`
335
+ 4. Adds `mcp__<name>__*` to the allowed tools list
336
+ 5. Cleans up the temp file after execution
337
+
338
+ Since everything runs locally on your Mac, stdio MCPs (local processes like context7, playwright) and HTTP/SSE MCPs (remote servers like granola) both work.
339
+
340
+ ## Web UI — MyAgent
341
+
342
+ Two pages served by the built-in Express server:
343
+
344
+ ### Chat Page (`/ui`)
345
+ - Left sidebar: agent cards with org/department filter dropdowns
346
+ - Right panel: live chat with any agent
347
+ - Streaming agents show real-time text + tool status as Claude works
348
+ - Non-streaming agents show "Thinking..." then full response
349
+ - Session reset button for persistent agents
350
+ - Dashboard link to org page
351
+
352
+ ### Org Chart Page (`/org`)
353
+ - Organization dropdown to filter by org
354
+ - Tree hierarchy visualization driven by `reportsTo`
355
+ - Animated connector lines between hierarchy levels (flowing cyan pulse)
356
+ - Agent cards show title, name, alias, department tag, message count
357
+ - Heartbeat ❤ animation on active agents
358
+ - "All Agents" view groups by organization with section headers
359
+ - **+ New Agent** button opens create form
360
+ - **Config** button opens edit modal (same form, pre-filled)
361
+ - Create/edit modals with: name, alias, workspace, persistent/streaming toggles, tool pills, MCP pills, org entries (with datalist autocomplete), routes with @mention toggle
362
+ - Light/dark mode toggle (respects system preference)
363
+
364
+ ### API Endpoints
365
+ | Endpoint | Method | Description |
366
+ |----------|--------|-------------|
367
+ | `/ui` | GET | Chat page |
368
+ | `/org` | GET | Org chart page |
369
+ | `/api/dashboard` | GET | All agents, channels, status, uptime |
370
+ | `/api/agents/:id` | GET | Agent detail + last 50 messages |
371
+ | `/api/agents` | POST | Create new agent (form data) |
372
+ | `/api/agents/:id` | PUT | Update existing agent |
373
+ | `/api/chat/:id` | POST | Send message, get response |
374
+ | `/api/chat/:id/stream` | POST | Send message, get SSE stream |
375
+ | `/api/mcps` | GET | List registered MCPs |
376
+ | `/webhook/:id` | POST | External webhook trigger |
377
+ | `/health` | GET | Health check |
378
+
379
+ ## Features
380
+
381
+ ### Response Chunking
382
+ Long responses automatically split to fit channel limits:
383
+ - Slack: 3900 chars
384
+ - Telegram: 4096 chars
385
+ - iMessage: 3000 chars
386
+ - Discord: 2000 chars
387
+
388
+ Splits prefer newline boundaries to avoid breaking mid-sentence.
389
+
390
+ ### Typing Indicators
391
+ When a message is being processed:
392
+ - **Telegram**: Sends native `typing` chat action
393
+ - **Discord**: Sends native typing indicator
394
+ - **Slack/iMessage**: Sends "On it..." text message (no native bot typing API)
395
+
396
+ ### DM Pairing / Approval Codes
397
+ Optional security gate for new senders. Set in config:
398
+ ```json
399
+ "service": {
400
+ "pairingCode": "mysecretcode"
401
+ }
402
+ ```
403
+ First-time senders must send the pairing code before agents respond. Paired senders persisted in `data/paired-senders.json`.
404
+
405
+ ### Cron / Scheduled Messages
406
+ Agents can receive scheduled messages:
407
+ ```json
408
+ "cron": [
409
+ {
410
+ "schedule": "0 9 * * 1-5",
411
+ "message": "Give me a status update on the current episode",
412
+ "channel": "slack",
413
+ "chatId": "C0AFJMHKZDG"
414
+ }
415
+ ]
416
+ ```
417
+ Uses standard cron expressions. The agent processes the message and replies on the specified channel.
418
+
419
+ ### Autonomous Goals
420
+
421
+ Agents with `"autonomousCapable": true` can be assigned goals — ongoing responsibilities that the agent checks on a recurring heartbeat schedule, with optional budget limits and channel reporting.
422
+
423
+ #### The `autonomousCapable` Flag
424
+
425
+ Set on the agent config to indicate whether this agent can accept goal assignments:
426
+ ```json
427
+ "autonomousCapable": true
428
+ ```
429
+
430
+ When `false`, the Goals tab in the Org UI is still visible but serves as documentation only — no heartbeats will fire.
431
+
432
+ #### Goal Config Fields
433
+
434
+ Each goal in the `goals` array has:
435
+
436
+ | Field | Required | Description |
437
+ |-------|----------|-------------|
438
+ | `id` | YES | Kebab-case identifier, auto-generated from description (editable) |
439
+ | `enabled` | YES | Whether the goal is active (`true`/`false`) |
440
+ | `description` | YES | What the agent is responsible for |
441
+ | `successCriteria` | no | How to determine the goal is complete |
442
+ | `instructions` | no | Step-by-step guidance for the agent |
443
+ | `heartbeat` | YES | Cron expression for check-in frequency |
444
+ | `budget` | no | `{ "maxDailyUsd": 5.00 }` — max daily spend |
445
+ | `reportTo` | no | `"channel:chatId"` — where to send results (e.g., `"telegram:-5274444946"`) |
446
+
447
+ Example:
448
+ ```json
449
+ "goals": [
450
+ {
451
+ "id": "monitor-deploy-health",
452
+ "enabled": true,
453
+ "description": "Monitor production deployment health",
454
+ "successCriteria": "All services returning 200 on health checks",
455
+ "instructions": "1. Check /health on each service\n2. If any fail, report immediately\n3. If all pass, log success silently",
456
+ "heartbeat": "0 9 * * 1-5",
457
+ "budget": { "maxDailyUsd": 2.00 },
458
+ "reportTo": "slack:C0AFJMHKZDG"
459
+ }
460
+ ]
461
+ ```
462
+
463
+ #### Heartbeat System
464
+
465
+ The `heartbeat` field uses the same cron expression format as scheduled messages. The Org UI provides a human-friendly picker (Every Day/Weekday/Week/Hour at HH:MM AM/PM) that converts to cron syntax.
466
+
467
+ When a heartbeat fires, the agent receives the goal description + instructions as a message and processes it like any other task. Results are sent to the `reportTo` channel if configured.
468
+
469
+ #### Budget Tracking
470
+
471
+ When `budget.maxDailyUsd` is set, the agent tracks spending in `agentHome/goals/budget/`. If the daily limit is reached, the goal pauses until the next day. Budget files are stored per-goal per-day.
472
+
473
+ #### Channel Reporting
474
+
475
+ The `reportTo` field follows the format `"channel:chatId"` (e.g., `"telegram:-5274444946"` or `"slack:C0AFJMHKZDG"`). When set, goal execution results are sent to that channel/chat instead of (or in addition to) the agent's default routes.
476
+
477
+ #### Three States
478
+
479
+ An autonomous-capable agent with goals can be in one of three states:
480
+
481
+ | State | Condition | Behavior |
482
+ |-------|-----------|----------|
483
+ | **Not Capable** | `autonomousCapable: false` | Goals are config-only, no heartbeats fire |
484
+ | **Idle** | `autonomousCapable: true`, no enabled goals | Agent responds to messages only, no autonomous activity |
485
+ | **Active** | `autonomousCapable: true`, 1+ enabled goals | Agent responds to messages AND executes goals on heartbeat schedules |
486
+
487
+ ### Task System
488
+
489
+ Agents have per-agent kanban task boards stored in `tasks.json` in the agent's home directory. Tasks are **deliberate** — they are explicitly created, not generated automatically.
490
+
491
+ #### Board Structure
492
+
493
+ Each board has 5 columns representing the task lifecycle:
494
+
495
+ ```
496
+ Proposed → Approved → In Progress → Review → Done
497
+ ```
498
+
499
+ Tasks start in **Proposed** or **Approved** depending on who creates them, and move through the pipeline as work progresses.
500
+
501
+ #### Creating Tasks
502
+
503
+ There are three ways to create a task:
504
+
505
+ | Method | How | Starting Column |
506
+ |--------|-----|-----------------|
507
+ | **Web UI** | Drag-and-drop board at `/tasks` | User chooses |
508
+ | **Chat command** | `/task add <description>` | Depends on hierarchy |
509
+ | **Agent-to-agent** | One agent assigns a task to another | Depends on hierarchy |
510
+
511
+ #### Hierarchy-Based Assignment
512
+
513
+ Task approval follows the org hierarchy:
514
+
515
+ - **Superior → subordinate**: Task is **auto-approved** (lands in Approved)
516
+ - **Peer → peer**: Task is a **proposal** (lands in Proposed, needs approval)
517
+
518
+ #### Task Commands
519
+
520
+ | Command | Description |
521
+ |---------|-------------|
522
+ | `/task list` | Show active tasks for the current agent |
523
+ | `/task add <description>` | Create a new task |
524
+ | `/task done <id>` | Mark a task as complete (moves to Done) |
525
+
526
+ #### Active Task Context
527
+
528
+ Active tasks (Approved + In Progress) are injected as **read-only context** into the agent's system prompt at the start of each conversation turn. This lets the agent be aware of its current responsibilities without needing to be told.
529
+
530
+ #### Projects
531
+
532
+ Task boards support **projects** — logical groupings within a board. Each project has an `id`, `name`, and `color`. Every board starts with a default "General" project. Tasks are tagged with a project ID for filtering.
533
+
534
+ #### Web UI
535
+
536
+ The task board is available at `/tasks` with:
537
+ - Per-agent board view
538
+ - Drag-and-drop between columns
539
+ - Project filtering
540
+ - Task creation and editing
541
+
542
+ #### Config
543
+
544
+ Tasks are stored in `tasks.json` in the agent's home directory (`agentHome`):
545
+
546
+ ```json
547
+ {
548
+ "agentId": "myagent",
549
+ "projects": [{ "id": "general", "name": "General", "color": "#6b7280" }],
550
+ "tasks": []
551
+ }
552
+ ```
553
+
554
+ ### Webhook Triggers
555
+ External services can trigger agents via HTTP:
556
+ ```bash
557
+ curl -X POST http://localhost:4888/webhook/claudeManager \
558
+ -H "Content-Type: application/json" \
559
+ -H "x-webhook-secret: yoursecret" \
560
+ -d '{"text": "PR #42 was merged, update the tracker"}'
561
+ ```
562
+
563
+ ### Voice Note Transcription
564
+ Telegram voice messages and audio files automatically transcribed via OpenAI Whisper API. Requires `OPENAI_API_KEY` environment variable. If not set, voice messages are silently ignored.
565
+
566
+ ### Media Output (File Sending)
567
+ All channel drivers support sending files back:
568
+ - **Telegram**: Photos as photos, other files as documents
569
+ - **Slack**: Files uploaded via Slack API
570
+ - **Discord**: Files as message attachments
571
+
572
+ ## Infrastructure
573
+
574
+ **Everything runs on your Mac as a single Node.js process.**
575
+
576
+ | Component | Where | Port | Notes |
577
+ |-----------|-------|------|-------|
578
+ | Gateway service | launchd | — | Main process: channels, router, executor |
579
+ | Slack connection | Outbound WSS | — | Socket Mode to Slack servers |
580
+ | Telegram connection | Outbound HTTPS | — | Long polling to Telegram API |
581
+ | iMessage watcher | Local subprocess | — | `imsg` CLI watches Messages.db |
582
+ | Discord connection | Outbound WSS | — | discord.js gateway |
583
+ | WhatsApp connection | Outbound WSS | — | Baileys protocol |
584
+ | Web UI + API + Webhooks | localhost | 4888 | Express server (not exposed to internet) |
585
+ | Cron scheduler | In-memory | — | node-cron timers |
586
+ | `claude -p` | Spawned per message | — | Claude Code CLI in print mode |
587
+ | MCP servers | Spawned per message | — | stdio subprocesses or HTTP calls |
588
+
589
+ **Your Mac must be on and awake** for agents to be reachable.
590
+
591
+ ## File Structure
592
+
593
+ ```
594
+ channelToAgentToClaude/ # The gateway project
595
+ ├── config.json # Channels, MCPs, agents, routes, web UI, cron (gitignored)
596
+ ├── config.example.json # Template for new installs
597
+ ├── src/
598
+ │ ├── index.ts # Entry point — wires everything together
599
+ │ ├── config.ts # Config loader + validation + interfaces
600
+ │ ├── router.ts # Routes messages + DM pairing
601
+ │ ├── executor.ts # Spawns claude -p, sessions, streaming, skills, commands
602
+ │ ├── web-ui.ts # Express server: UI pages, API, chat, webhooks
603
+ │ ├── cron.ts # Scheduled message triggers
604
+ │ ├── channels/
605
+ │ │ ├── types.ts # ChannelDriver interface + splitText utility
606
+ │ │ ├── imessage.ts # iMessage driver (imsg CLI)
607
+ │ │ ├── slack.ts # Slack driver (Socket Mode)
608
+ │ │ ├── telegram.ts # Telegram driver (grammY + voice transcription)
609
+ │ │ ├── discord.ts # Discord driver (discord.js)
610
+ │ │ └── whatsapp.ts # WhatsApp driver (Baileys)
611
+ │ └── utils/
612
+ │ ├── imsg-rpc.ts # JSON-RPC client for imsg
613
+ │ └── message-formatter.ts # Message formatting with context + history
614
+ ├── public/
615
+ │ ├── index.html # Chat UI page
616
+ │ └── org.html # Org chart page
617
+ ├── agents/ # Agent identity files (project-scoped agents)
618
+ │ ├── _template/
619
+ │ ├── fic-show/
620
+ │ └── fic-platform/
621
+ ├── Comprehensive Test Suite/ # 7 test files, 43 tests
622
+ │ ├── run-all-tests.js
623
+ │ ├── config/
624
+ │ ├── router/
625
+ │ ├── executor/
626
+ │ ├── web-ui/
627
+ │ ├── cron/
628
+ │ ├── types/
629
+ │ └── message-formatter/
630
+ ├── data/
631
+ │ ├── whatsapp-auth/ # WhatsApp session credentials
632
+ │ └── paired-senders.json # DM pairing store
633
+ ├── docs/
634
+ │ ├── Architecture.md # This file
635
+ │ ├── Setup.md # Setup guide for new installs
636
+ │ ├── AddNewAgentGuide.md
637
+ │ └── AddNewMcpGuide.md
638
+ └── logs/
639
+ └── service.log
640
+
641
+ ~/Desktop/MyAIforOne Drive/PersonalAgents/ # Agent homes (personal agents)
642
+ └── claudeManager/
643
+ ├── CLAUDE.md # System prompt
644
+ ├── memory/
645
+ │ ├── context.md # Persistent context (survives resets)
646
+ │ ├── session.json # Session UUID pointer
647
+ │ └── conversation_log.jsonl # Audit trail
648
+ └── goals/ # Budget tracking and goal execution logs
649
+ ├── budget/ # Daily budget usage per goal
650
+ └── logs/ # Execution logs from goal heartbeats
651
+ ```
652
+
653
+ ## Config Reference
654
+
655
+ ### Service
656
+ ```json
657
+ "service": {
658
+ "logLevel": "debug",
659
+ "logFile": "./logs/service.log",
660
+ "pairingCode": "optional-secret",
661
+ "webUI": {
662
+ "enabled": true,
663
+ "port": 4888,
664
+ "webhookSecret": "optional-secret"
665
+ }
666
+ }
667
+ ```
668
+
669
+ ### Channels
670
+ ```json
671
+ "telegram": {
672
+ "enabled": true,
673
+ "driver": "telegram",
674
+ "config": { "botToken": "123:ABC..." }
675
+ },
676
+ "slack": {
677
+ "enabled": true,
678
+ "driver": "slack",
679
+ "config": { "botToken": "xoxb-...", "appToken": "xapp-...", "mode": "socket" }
680
+ },
681
+ "discord": {
682
+ "enabled": false,
683
+ "driver": "discord",
684
+ "config": { "botToken": "..." }
685
+ },
686
+ "imessage": {
687
+ "enabled": true,
688
+ "driver": "imessage",
689
+ "config": { "cliPath": "imsg", "debounceMs": 2000 }
690
+ },
691
+ "whatsapp": {
692
+ "enabled": false,
693
+ "driver": "whatsapp",
694
+ "config": { "authDir": "./data/whatsapp-auth" }
695
+ }
696
+ ```
697
+
698
+ ### MCP Registry
699
+ ```json
700
+ "mcps": {
701
+ "context7": { "type": "stdio", "command": "npx", "args": ["-y", "@upstash/context7-mcp"] },
702
+ "playwright": { "type": "stdio", "command": "npx", "args": ["@playwright/mcp@latest"] },
703
+ "granola": { "type": "sse", "url": "https://mcp.granola.ai/mcp" }
704
+ }
705
+ ```
706
+
707
+ ### Agent (full example)
708
+ ```json
709
+ "claudeManager": {
710
+ "name": "Claude Manager Agent",
711
+ "description": "General-purpose Claude agent",
712
+ "workspace": "~",
713
+ "claudeMd": "~/Desktop/MyAIforOne Drive/PersonalAgents/claudeManager/CLAUDE.md",
714
+ "memoryDir": "~/Desktop/MyAIforOne Drive/PersonalAgents/claudeManager/memory",
715
+ "claudeAccount": "main",
716
+ "mcps": ["context7", "playwright", "granola"],
717
+ "persistent": true,
718
+ "streaming": true,
719
+ "advancedMemory": true,
720
+ "perSenderSessions": false,
721
+ "skills": ["opcodereview", "sop_pdf"],
722
+ "mentionAliases": ["@agentmgr"],
723
+ "autoCommit": false,
724
+ "allowedTools": ["Read", "Edit", "Write", "Glob", "Grep", "Bash", "WebFetch", "WebSearch"],
725
+ "timeout": 120000,
726
+ "org": [
727
+ { "organization": "Finance Is Cooked", "function": "Operations", "title": "Chief of Staff" },
728
+ { "organization": "Personal", "function": "Operations", "title": "General Manager" }
729
+ ],
730
+ "cron": [
731
+ {
732
+ "schedule": "0 9 * * 1-5",
733
+ "message": "Good morning. Any tasks pending?",
734
+ "channel": "telegram",
735
+ "chatId": "-5274444946"
736
+ }
737
+ ],
738
+ "routes": [
739
+ {
740
+ "channel": "telegram",
741
+ "match": { "type": "chat_id", "value": "-5274444946" },
742
+ "permissions": { "allowFrom": ["*"], "requireMention": true }
743
+ }
744
+ ]
745
+ }
746
+ ```
747
+
748
+ ## Adding a New Agent
749
+
750
+ Three ways:
751
+
752
+ 1. **Web UI**: Go to `/org` → click **"+ New Agent"** → fill out the form
753
+ 2. **Chat**: Message `@agentmgr` with "create a new agent" (uses the `/opAgents_AddNew` skill)
754
+ 3. **Manual**: See `docs/AddNewAgentGuide.md` or `docs/Setup.md`
755
+
756
+ ## Running
757
+
758
+ ```bash
759
+ npm run build # Compile TypeScript
760
+ npm start # Run directly
761
+ npm run dev # Dev mode with auto-reload
762
+ npm test # Run test suite (43 tests)
763
+ ```
764
+
765
+ ### As a launchd service (auto-start on login)
766
+ ```bash
767
+ # Start
768
+ launchctl load ~/Library/LaunchAgents/com.agenticledger.channelToAgentToClaude.plist
769
+
770
+ # Stop
771
+ launchctl unload ~/Library/LaunchAgents/com.agenticledger.channelToAgentToClaude.plist
772
+
773
+ # Restart
774
+ launchctl unload ~/Library/LaunchAgents/com.agenticledger.channelToAgentToClaude.plist && \
775
+ sleep 1 && \
776
+ launchctl load ~/Library/LaunchAgents/com.agenticledger.channelToAgentToClaude.plist
777
+ ```
778
+
779
+ ## Tech Stack
780
+
781
+ | Layer | Technology |
782
+ |-------|------------|
783
+ | **Language** | TypeScript 5.7 |
784
+ | **Runtime** | Node.js 22+ |
785
+ | **iMessage** | `imsg` CLI (JSON-RPC) |
786
+ | **Slack** | @slack/socket-mode, @slack/web-api |
787
+ | **Telegram** | grammY |
788
+ | **Discord** | discord.js |
789
+ | **WhatsApp** | @whiskeysockets/baileys |
790
+ | **Web UI** | Express + vanilla HTML/CSS/JS (no framework) |
791
+ | **Voice** | OpenAI Whisper API |
792
+ | **Scheduling** | node-cron |
793
+ | **AI Engine** | `claude -p` (Claude Code CLI) |
794
+ | **Service** | launchd (macOS native) |
795
+ | **Tests** | Node.js built-in test runner |