very-happy-cli 0.2.159 → 0.2.160

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 (258) hide show
  1. package/dist/{AcpBackend-DUYFlyfN.cjs → AcpBackend-Bm2rdke8.cjs} +78 -76
  2. package/dist/{AcpBackend-VsfkZiVF.mjs → AcpBackend-mzv8Dhba.mjs} +4 -2
  3. package/dist/{AcpSessionManager-Bdv8LWXh.cjs → AcpSessionManager-BAY1Pggx.cjs} +9 -9
  4. package/dist/{AcpSessionManager-rYtVb0kN.mjs → AcpSessionManager-CoMWFVw3.mjs} +1 -1
  5. package/dist/BasePermissionHandler-CFHAxumV.cjs +157 -0
  6. package/dist/BasePermissionHandler-m3WVholL.mjs +155 -0
  7. package/dist/BaseReasoningProcessor-BFa9_rZA.cjs +200 -0
  8. package/dist/BaseReasoningProcessor-CYrKBXGm.mjs +198 -0
  9. package/dist/RemoteModeDisplay-D-HewyXg.mjs +150 -0
  10. package/dist/RemoteModeDisplay-NC1gPHtj.cjs +153 -0
  11. package/dist/agentAttachments-Dbw8iMCZ.cjs +20 -0
  12. package/dist/agentAttachments-M_B5qEF2.mjs +18 -0
  13. package/dist/agentGuidance-B5NATuFa.cjs +28 -0
  14. package/dist/agentGuidance-CQuNlNx8.mjs +20 -0
  15. package/dist/{agentHome-CHh4lmjM.cjs → agentHome-CboCeKWq.cjs} +14 -28
  16. package/dist/{agentHome-CvsJyeQB.mjs → agentHome-Dj1C43aJ.mjs} +8 -22
  17. package/dist/api-CLMUr-SX.mjs +3339 -0
  18. package/dist/api-CgundNNX.cjs +3346 -0
  19. package/dist/{types-Dh-s4Lqs.mjs → apiMachine-B9dLW_p5.mjs} +9116 -16205
  20. package/dist/{types-BbvK1Tr_.cjs → apiMachine-Bn8482VM.cjs} +9104 -16247
  21. package/dist/assistantTools-BTqPnlFl.cjs +380 -0
  22. package/dist/assistantTools-D6tuc6o4.mjs +376 -0
  23. package/dist/attachmentContent-DpiTJZb4.cjs +88 -0
  24. package/dist/attachmentContent-_kxRznNf.mjs +82 -0
  25. package/dist/attachmentLimits-CzVrqgLR.cjs +354 -0
  26. package/dist/attachmentLimits-yba1uHFO.mjs +348 -0
  27. package/dist/auth-BDOVh5h5.cjs +220 -0
  28. package/dist/auth-Cwutmdsa.mjs +225 -0
  29. package/dist/auth-PYHZQNPp.mjs +218 -0
  30. package/dist/auth-ba4WMYrN.cjs +227 -0
  31. package/dist/authRelay-BdYkC1Po.cjs +156 -0
  32. package/dist/authRelay-DSAvg1uv.mjs +143 -0
  33. package/dist/{auto-DKmEls8Z.cjs → auto-BOX_fgmR.cjs} +70 -79
  34. package/dist/{auto-nb8GhRRy.mjs → auto-BXu14yP_.mjs} +27 -36
  35. package/dist/backgroundTaskActivity-8PdPxrvy.mjs +149 -0
  36. package/dist/backgroundTaskActivity-CBvUdj39.cjs +157 -0
  37. package/dist/bootstrap-B5G1TijC.cjs +116 -0
  38. package/dist/bootstrap-hxXPCFMx.mjs +112 -0
  39. package/dist/browser-Y6Bl8L_O.cjs +22 -0
  40. package/dist/browser-jh2P0UVZ.mjs +20 -0
  41. package/dist/claudeCliPath-BqkaH2oR.mjs +8 -0
  42. package/dist/claudeCliPath-U4HHmV4r.cjs +10 -0
  43. package/dist/claudeLocal-BaY4fZKi.mjs +339 -0
  44. package/dist/claudeLocal-CRGG4Pea.cjs +343 -0
  45. package/dist/claudeLocalLauncher-D4T7MTqd.mjs +152 -0
  46. package/dist/claudeLocalLauncher-DyEbVzUN.cjs +154 -0
  47. package/dist/cliUpdate-DsKXPFYp.cjs +120 -0
  48. package/dist/cliUpdate-Y34VGe9Y.mjs +112 -0
  49. package/dist/client-3Ac-O4pw.cjs +104 -0
  50. package/dist/client-BPNbmtvO.cjs +119 -0
  51. package/dist/client-CeGKqqcJ.mjs +100 -0
  52. package/dist/client-ClR0K8zX.mjs +112 -0
  53. package/dist/codex/happyMcpStdioBridge.cjs +33 -14
  54. package/dist/codex/happyMcpStdioBridge.mjs +26 -7
  55. package/dist/codexAppServerClient-I3teiV-N.mjs +1088 -0
  56. package/dist/codexAppServerClient-q2FjnRcK.cjs +1090 -0
  57. package/dist/codexCommand-4zcccIoq.cjs +2088 -0
  58. package/dist/codexCommand-Cc9gcbdX.mjs +2086 -0
  59. package/dist/codexThreadFork-BH9IZPqD.cjs +350 -0
  60. package/dist/codexThreadFork-slzAseLx.mjs +338 -0
  61. package/dist/{config-ClLtM6F3.mjs → config-CTx_jb-C.mjs} +7 -40
  62. package/dist/{config-DLx-vW3I.cjs → config-Ci9Kpgwa.cjs} +26 -59
  63. package/dist/configuration-BSYpcPwE.cjs +181 -0
  64. package/dist/configuration-RfeNjFmd.mjs +170 -0
  65. package/dist/connect-BpOdzNbE.mjs +682 -0
  66. package/dist/connect-C2CiOUFs.cjs +684 -0
  67. package/dist/constants-BC4St0xd.mjs +11 -0
  68. package/dist/constants-VJ0N6WuG.cjs +17 -0
  69. package/dist/contentLogMetadata-BlWI0egu.mjs +51 -0
  70. package/dist/contentLogMetadata-ZSFk_NjQ.cjs +54 -0
  71. package/dist/context-DsDr6E2t.cjs +69 -0
  72. package/dist/context-H0Bcb9S_.mjs +65 -0
  73. package/dist/controlClient-BGbDcgWS.mjs +260 -0
  74. package/dist/controlClient-Bcwv3D21.cjs +279 -0
  75. package/dist/createSessionMetadata-BJxEnM-o.cjs +58 -0
  76. package/dist/createSessionMetadata-CVVkGjxV.mjs +54 -0
  77. package/dist/defaultPermissionMode-BnxJPVHT.mjs +4 -0
  78. package/dist/defaultPermissionMode-CxmTXUQR.cjs +7 -0
  79. package/dist/detectCLI-CSGMlV51.mjs +58 -0
  80. package/dist/detectCLI-DR9ZaN6B.cjs +61 -0
  81. package/dist/deterministicJson-C5CYTVpm.cjs +507 -0
  82. package/dist/deterministicJson-CzkFJWw1.mjs +502 -0
  83. package/dist/doctor-BPkYWSuq.mjs +75 -0
  84. package/dist/doctor-D2YJ-Yn2.cjs +395 -0
  85. package/dist/doctor-DOvByjbk.mjs +391 -0
  86. package/dist/doctor-u46qYYKX.cjs +79 -0
  87. package/dist/doctorReadiness-BCZGcN0a.cjs +151 -0
  88. package/dist/doctorReadiness-C208SMN9.mjs +142 -0
  89. package/dist/editPaths-BVfS_FFL.mjs +68 -0
  90. package/dist/editPaths-Bqp4OFPw.cjs +73 -0
  91. package/dist/ensureDaemonRunning-BCwNrMyv.cjs +64 -0
  92. package/dist/ensureDaemonRunning-Dqa2pOjY.mjs +61 -0
  93. package/dist/handleResumeCommand-BvXYf5El.mjs +240 -0
  94. package/dist/handleResumeCommand-C2cKchpX.cjs +245 -0
  95. package/dist/ids-B6ZC0HGt.cjs +13 -0
  96. package/dist/ids-DU6sLx4C.mjs +10 -0
  97. package/dist/index-B6UGRQ7h.mjs +102 -0
  98. package/dist/{index-BEOMECtE.cjs → index-B6pAdvJx.cjs} +121 -91
  99. package/dist/index-Bu5Zi_a9.cjs +182 -0
  100. package/dist/index-D3kI0hDR.cjs +107 -0
  101. package/dist/index-DA7yINuk.cjs +994 -0
  102. package/dist/index-DDeHXrIX.cjs +71 -0
  103. package/dist/index-DKLU_fD0.mjs +158 -0
  104. package/dist/{index-2mCaeKyf.mjs → index-DMZqWwsP.mjs} +68 -38
  105. package/dist/index-DVkMGPyS.mjs +68 -0
  106. package/dist/index-qdS1friN.mjs +949 -0
  107. package/dist/index.cjs +5 -46
  108. package/dist/index.mjs +5 -46
  109. package/dist/{install-BPhJppvd.mjs → install-BO_W7VhL.mjs} +37 -37
  110. package/dist/install-BgoC2e_2.cjs +88 -0
  111. package/dist/install-CFY3tYtJ.mjs +86 -0
  112. package/dist/{install-BOHrUaFM.cjs → install-Cs5qAPrB.cjs} +38 -38
  113. package/dist/{installPiTools-DuZ6jZvX.cjs → installPiTools-BKnXjrVu.cjs} +2 -3
  114. package/dist/{installPiTools-Cj7yU9Fc.mjs → installPiTools-B_CdM5_2.mjs} +1 -2
  115. package/dist/{installTerminalHooks-Cou3WUf3.cjs → installTerminalHooks-BQZbvxsZ.cjs} +5 -40
  116. package/dist/{installTerminalHooks-WeznjkuC.mjs → installTerminalHooks-By7gBMEF.mjs} +3 -38
  117. package/dist/lib.cjs +28 -19
  118. package/dist/lib.d.cts +12 -2
  119. package/dist/lib.d.mts +12 -2
  120. package/dist/lib.mjs +23 -14
  121. package/dist/lidState-BeDfxxEX.cjs +305 -0
  122. package/dist/lidState-CeEt442o.mjs +297 -0
  123. package/dist/limits-C-a7gr04.cjs +43 -0
  124. package/dist/limits-DIo7rEBR.mjs +36 -0
  125. package/dist/localHappyAgentAuth-C-HQyiv6.mjs +82 -0
  126. package/dist/localHappyAgentAuth-D6rFhaoc.cjs +86 -0
  127. package/dist/logger-6HYUEXNk.mjs +271 -0
  128. package/dist/logger-CS0mw3fa.cjs +275 -0
  129. package/dist/loginShellEnv-BkuYtExZ.cjs +182 -0
  130. package/dist/loginShellEnv-Dw8M7tkI.mjs +167 -0
  131. package/dist/machineMetadata-DyDbODYd.cjs +41 -0
  132. package/dist/machineMetadata-oOzBfDfs.mjs +38 -0
  133. package/dist/main-BkxJP6JQ.cjs +941 -0
  134. package/dist/main-BwNIAI1A.mjs +939 -0
  135. package/dist/manager-BQ4flvQZ.mjs +101 -0
  136. package/dist/manager-Cly8xVIR.cjs +105 -0
  137. package/dist/{mcp-Dy3f_K0h.mjs → mcp-B1A4I3TK.mjs} +27 -33
  138. package/dist/{mcp-CPYbtsYG.cjs → mcp-Hszd7qpS.cjs} +42 -48
  139. package/dist/messageBuffer-BWlGgR3A.mjs +71 -0
  140. package/dist/messageBuffer-fJMH6uY8.cjs +73 -0
  141. package/dist/mirrorProtocol-BNLtoWjO.mjs +170 -0
  142. package/dist/mirrorProtocol-BUtmg1ws.cjs +186 -0
  143. package/dist/oneShotPrompts-CL0dip9C.cjs +16 -0
  144. package/dist/oneShotPrompts-DT4p6RNd.mjs +12 -0
  145. package/dist/package-BhaKlnxz.mjs +171 -0
  146. package/dist/package-BwMrPwqH.cjs +173 -0
  147. package/dist/path-B7zW-WwE.cjs +18 -0
  148. package/dist/path-D2wdaNSk.mjs +15 -0
  149. package/dist/peerTools-BTqw97Gb.mjs +272 -0
  150. package/dist/peerTools-BvKtHXj8.cjs +283 -0
  151. package/dist/permissionMode-Cr5JCbB7.mjs +80 -0
  152. package/dist/permissionMode-CrV-XuMs.cjs +87 -0
  153. package/dist/persistence-HGW_ZVs9.mjs +372 -0
  154. package/dist/persistence-yKTH3-5X.cjs +414 -0
  155. package/dist/piExtension.mjs +2 -1
  156. package/dist/piRunnerArgs-BNloJCCg.cjs +66 -0
  157. package/dist/piRunnerArgs-BuX1UFWy.mjs +59 -0
  158. package/dist/{piRuntime-kLZNpAAl.mjs → piRuntime-CSGkwCKQ.mjs} +2 -2
  159. package/dist/{piRuntime-NtF0YqjH.cjs → piRuntime-C_H7MJCM.cjs} +4 -4
  160. package/dist/{piTerminal-B0fEOV_2.mjs → piTerminal-C8a1OrNQ.mjs} +32 -35
  161. package/dist/{piTerminal-9J0GAKzb.cjs → piTerminal-DNCZ6yTM.cjs} +32 -35
  162. package/dist/previewPath-B0rBdhy1.cjs +83 -0
  163. package/dist/previewPath-CXN4Vag0.mjs +81 -0
  164. package/dist/projectPath-BTBIMB57.mjs +10 -0
  165. package/dist/projectPath-ChLhdOyt.cjs +13 -0
  166. package/dist/registerCommonHandlers-Ccvsz7Ou.mjs +536 -0
  167. package/dist/registerCommonHandlers-DskirN-_.cjs +538 -0
  168. package/dist/registerKillSessionHandler-DZeLXWcB.cjs +361 -0
  169. package/dist/registerKillSessionHandler-GYvHdipX.mjs +358 -0
  170. package/dist/remoteSessionClient-B0LraSB9.cjs +634 -0
  171. package/dist/remoteSessionClient-CYnXRynE.mjs +612 -0
  172. package/dist/resources-BdFBQi8r.mjs +117 -0
  173. package/dist/resources-JDPugcDq.cjs +120 -0
  174. package/dist/run-CJzxoHVh.cjs +5762 -0
  175. package/dist/run-D3ifupU3.mjs +5739 -0
  176. package/dist/runClaude-Ba01qT-u.mjs +848 -0
  177. package/dist/runClaude-Da3RirzE.cjs +850 -0
  178. package/dist/runClaudeDeps-DOt79DjU.mjs +3624 -0
  179. package/dist/runClaudeDeps-DOzEBMls.cjs +3649 -0
  180. package/dist/{runGemini-DV6Ouadt.mjs → runGemini-BGeTz57m.mjs} +58 -31
  181. package/dist/{runGemini-F-mqx3_K.cjs → runGemini-DSr9LIxL.cjs} +202 -175
  182. package/dist/{runOpenClaw-Qqo9j63M.cjs → runOpenClaw-B1mTxN35.cjs} +64 -65
  183. package/dist/{runOpenClaw-D7MlPS5n.mjs → runOpenClaw-CogSedIc.mjs} +31 -32
  184. package/dist/sandbox-CG7IyDTU.cjs +187 -0
  185. package/dist/sandbox-DTe6d54R.mjs +180 -0
  186. package/dist/selfCheck-C9mVrQwf.mjs +84 -0
  187. package/dist/selfCheck-Dc-mNSLb.cjs +87 -0
  188. package/dist/{send-4qJTCAYW.cjs → send-B7J_eaG3.cjs} +16 -9
  189. package/dist/{send-CLhYXNgy.mjs → send-CBXJKc6O.mjs} +12 -5
  190. package/dist/server-CZTP_iOn.cjs +407 -0
  191. package/dist/server-DcVBv04l.mjs +404 -0
  192. package/dist/sessionLock-Bys1PNSo.cjs +205 -0
  193. package/dist/sessionLock-D-EG2CfG.mjs +197 -0
  194. package/dist/sessionModeFile-DMl3dw3r.mjs +32 -0
  195. package/dist/sessionModeFile-RSm0NQkH.cjs +36 -0
  196. package/dist/sessionOps-Dn8z85h_.cjs +783 -0
  197. package/dist/sessionOps-SuHW8Dfe.mjs +760 -0
  198. package/dist/sessionScanner-BOrGjMXL.cjs +209 -0
  199. package/dist/sessionScanner-CX3onqXh.mjs +206 -0
  200. package/dist/{sessions-CzIH2rGp.mjs → sessions-BEG_HTSi.mjs} +17 -8
  201. package/dist/{sessions-Bh1pyddi.cjs → sessions-D74aJbhL.cjs} +37 -28
  202. package/dist/setupOfflineReconnection-ByElY60m.cjs +74 -0
  203. package/dist/setupOfflineReconnection-DpvWTt69.mjs +72 -0
  204. package/dist/smallFastModel-BLNgMrwR.mjs +18 -0
  205. package/dist/smallFastModel-D_uxGMo3.cjs +21 -0
  206. package/dist/{spawn-CPIWlPOM.mjs → spawn-B7yro0b2.mjs} +26 -38
  207. package/dist/{spawn-CmFOSVdW.cjs → spawn-DgR0RKRs.cjs} +52 -64
  208. package/dist/spawnAgents-BGQiEF-w.cjs +52 -0
  209. package/dist/spawnAgents-DZzZ9jMI.mjs +45 -0
  210. package/dist/spawnHappyCLI-B2H5s4B_.mjs +64 -0
  211. package/dist/spawnHappyCLI-DBhwZT7O.cjs +66 -0
  212. package/dist/specialCommands-BSqhYg5X.mjs +52 -0
  213. package/dist/specialCommands-DSsTeRej.cjs +54 -0
  214. package/dist/startFileWatcher-B4VsLgjD.cjs +71 -0
  215. package/dist/startFileWatcher-DErVWZE4.mjs +69 -0
  216. package/dist/startupPlan-BLMbfQIH.cjs +12 -0
  217. package/dist/startupPlan-DFMyNgAs.mjs +10 -0
  218. package/dist/streamRelay-BiKw59Cc.cjs +233 -0
  219. package/dist/streamRelay-FPVbHpbM.mjs +231 -0
  220. package/dist/sync-C8gyQFMc.mjs +69 -0
  221. package/dist/sync-DccIKZ5_.cjs +71 -0
  222. package/dist/systemPrompt-BwTPWfMu.cjs +97 -0
  223. package/dist/systemPrompt-DX521JJz.mjs +94 -0
  224. package/dist/{teams-CEahj4cm.mjs → teams-C32F1hqd.mjs} +9 -40
  225. package/dist/{teams-CB1R9-Z9.cjs → teams-Dl8g8kTI.cjs} +14 -45
  226. package/dist/template-BaHAmH2K.cjs +129 -0
  227. package/dist/template-CiOPa2rd.mjs +121 -0
  228. package/dist/{terminalTitleSuggest-DKgX3osW.mjs → terminalTitleSuggest-CeKsX_V6.mjs} +1 -9
  229. package/dist/{terminalTitleSuggest-Dji8I0Jy.cjs → terminalTitleSuggest-DhvRFX3H.cjs} +0 -10
  230. package/dist/terminals-B_bfC9c2.cjs +250 -0
  231. package/dist/terminals-Dlg0x3nY.mjs +235 -0
  232. package/dist/time-D0XyHOid.mjs +38 -0
  233. package/dist/time-DCuTyook.cjs +42 -0
  234. package/dist/titleGenerator-CQ8CoGhg.mjs +166 -0
  235. package/dist/titleGenerator-ChzMJsyg.cjs +172 -0
  236. package/dist/tmuxSocket-B8Yx20sT.mjs +19 -0
  237. package/dist/tmuxSocket-D-Xt6Vn-.cjs +24 -0
  238. package/dist/{todo-DqyRI4wP.cjs → todo-BvUOTa8G.cjs} +15 -12
  239. package/dist/{todo-Cknp5D4U.mjs → todo-CZ6cFrrn.mjs} +11 -8
  240. package/dist/tools-BZtHF_qQ.mjs +177 -0
  241. package/dist/tools-Be3AoAwu.cjs +63 -0
  242. package/dist/tools-DQj0AeLk.cjs +180 -0
  243. package/dist/tools-DkluDcG4.mjs +60 -0
  244. package/dist/trimIdent-4gvk9Wk6.cjs +22 -0
  245. package/dist/trimIdent-BAjmv_TG.mjs +20 -0
  246. package/dist/types-CRS-srZK.cjs +66 -0
  247. package/dist/types-CkqAACXx.mjs +64 -0
  248. package/dist/uninstall-BkLzaJ6I.mjs +47 -0
  249. package/dist/uninstall-x-TUtf5H.cjs +49 -0
  250. package/package.json +7 -7
  251. package/dist/agentGuidance-BRDN1NoZ.cjs +0 -2217
  252. package/dist/agentGuidance-KgvYuF3R.mjs +0 -2145
  253. package/dist/index-BF6WfgV5.mjs +0 -19624
  254. package/dist/index-C-JazrMB.mjs +0 -52
  255. package/dist/index-blDSadUR.cjs +0 -58
  256. package/dist/index-rH3DrQ5B.cjs +0 -19688
  257. package/dist/limits-BH5CV5vR.cjs +0 -2683
  258. package/dist/limits-CjRj8IX5.mjs +0 -2558
@@ -0,0 +1,101 @@
1
+ import { SandboxManager } from '@anthropic-ai/sandbox-runtime';
2
+ import { homedir } from 'node:os';
3
+ import { resolve, isAbsolute } from 'node:path';
4
+
5
+ function expandPath(pathValue, sessionPath) {
6
+ const expandedHome = pathValue.replace(/^~(?=\/|$)/, homedir());
7
+ if (isAbsolute(expandedHome)) {
8
+ return expandedHome;
9
+ }
10
+ return resolve(sessionPath, expandedHome);
11
+ }
12
+ function resolvePaths(paths, sessionPath) {
13
+ return paths.map((pathValue) => expandPath(pathValue, sessionPath));
14
+ }
15
+ function getSharedAgentStatePaths(sessionPath) {
16
+ const codexHome = process.env.CODEX_HOME || "~/.codex";
17
+ const claudeConfigDir = process.env.CLAUDE_CONFIG_DIR || "~/.claude";
18
+ return [
19
+ expandPath(codexHome, sessionPath),
20
+ expandPath(claudeConfigDir, sessionPath)
21
+ ];
22
+ }
23
+ function uniquePaths(paths) {
24
+ return [...new Set(paths)];
25
+ }
26
+ function buildSandboxRuntimeConfig(sandboxConfig, sessionPath) {
27
+ const extraWritePaths = resolvePaths(sandboxConfig.extraWritePaths, sessionPath);
28
+ const sharedAgentStatePaths = getSharedAgentStatePaths(sessionPath);
29
+ const allowWrite = (() => {
30
+ switch (sandboxConfig.sessionIsolation) {
31
+ case "strict":
32
+ return uniquePaths([resolve(sessionPath), ...extraWritePaths, ...sharedAgentStatePaths]);
33
+ case "workspace": {
34
+ const workspaceRoot = sandboxConfig.workspaceRoot ? expandPath(sandboxConfig.workspaceRoot, sessionPath) : resolve(sessionPath);
35
+ return uniquePaths([workspaceRoot, resolve(sessionPath), ...extraWritePaths, ...sharedAgentStatePaths]);
36
+ }
37
+ case "custom":
38
+ return uniquePaths([
39
+ ...resolvePaths(sandboxConfig.customWritePaths, sessionPath),
40
+ ...extraWritePaths,
41
+ ...sharedAgentStatePaths
42
+ ]);
43
+ }
44
+ })();
45
+ const network = (() => {
46
+ switch (sandboxConfig.networkMode) {
47
+ case "blocked":
48
+ return {
49
+ allowedDomains: [],
50
+ deniedDomains: [],
51
+ allowLocalBinding: sandboxConfig.allowLocalBinding,
52
+ allowUnixSockets: []
53
+ };
54
+ case "allowed":
55
+ return {
56
+ allowedDomains: void 0,
57
+ deniedDomains: [],
58
+ allowLocalBinding: sandboxConfig.allowLocalBinding,
59
+ allowUnixSockets: []
60
+ };
61
+ case "custom":
62
+ return {
63
+ allowedDomains: sandboxConfig.allowedDomains,
64
+ deniedDomains: sandboxConfig.deniedDomains,
65
+ allowLocalBinding: sandboxConfig.allowLocalBinding,
66
+ allowUnixSockets: []
67
+ };
68
+ }
69
+ })();
70
+ const enableWeakerNetworkIsolation = sandboxConfig.networkMode === "allowed" ? true : void 0;
71
+ return {
72
+ allowPty: true,
73
+ enableWeakerNetworkIsolation,
74
+ network,
75
+ filesystem: {
76
+ denyRead: resolvePaths(sandboxConfig.denyReadPaths, sessionPath),
77
+ allowWrite,
78
+ denyWrite: resolvePaths(sandboxConfig.denyWritePaths, sessionPath)
79
+ }
80
+ };
81
+ }
82
+
83
+ async function initializeSandbox(sandboxConfig, sessionPath) {
84
+ const runtimeConfig = buildSandboxRuntimeConfig(sandboxConfig, sessionPath);
85
+ await SandboxManager.initialize(runtimeConfig);
86
+ return async () => {
87
+ await SandboxManager.reset();
88
+ };
89
+ }
90
+ async function wrapCommand(command) {
91
+ return SandboxManager.wrapWithSandbox(command);
92
+ }
93
+ async function wrapForMcpTransport(command, args) {
94
+ const wrappedCommand = await wrapCommand(`${command} ${args.join(" ")}`.trim());
95
+ return {
96
+ command: "sh",
97
+ args: ["-c", wrappedCommand]
98
+ };
99
+ }
100
+
101
+ export { wrapCommand as a, initializeSandbox as i, wrapForMcpTransport as w };
@@ -0,0 +1,105 @@
1
+ 'use strict';
2
+
3
+ var sandboxRuntime = require('@anthropic-ai/sandbox-runtime');
4
+ var os = require('node:os');
5
+ var path = require('node:path');
6
+
7
+ function expandPath(pathValue, sessionPath) {
8
+ const expandedHome = pathValue.replace(/^~(?=\/|$)/, os.homedir());
9
+ if (path.isAbsolute(expandedHome)) {
10
+ return expandedHome;
11
+ }
12
+ return path.resolve(sessionPath, expandedHome);
13
+ }
14
+ function resolvePaths(paths, sessionPath) {
15
+ return paths.map((pathValue) => expandPath(pathValue, sessionPath));
16
+ }
17
+ function getSharedAgentStatePaths(sessionPath) {
18
+ const codexHome = process.env.CODEX_HOME || "~/.codex";
19
+ const claudeConfigDir = process.env.CLAUDE_CONFIG_DIR || "~/.claude";
20
+ return [
21
+ expandPath(codexHome, sessionPath),
22
+ expandPath(claudeConfigDir, sessionPath)
23
+ ];
24
+ }
25
+ function uniquePaths(paths) {
26
+ return [...new Set(paths)];
27
+ }
28
+ function buildSandboxRuntimeConfig(sandboxConfig, sessionPath) {
29
+ const extraWritePaths = resolvePaths(sandboxConfig.extraWritePaths, sessionPath);
30
+ const sharedAgentStatePaths = getSharedAgentStatePaths(sessionPath);
31
+ const allowWrite = (() => {
32
+ switch (sandboxConfig.sessionIsolation) {
33
+ case "strict":
34
+ return uniquePaths([path.resolve(sessionPath), ...extraWritePaths, ...sharedAgentStatePaths]);
35
+ case "workspace": {
36
+ const workspaceRoot = sandboxConfig.workspaceRoot ? expandPath(sandboxConfig.workspaceRoot, sessionPath) : path.resolve(sessionPath);
37
+ return uniquePaths([workspaceRoot, path.resolve(sessionPath), ...extraWritePaths, ...sharedAgentStatePaths]);
38
+ }
39
+ case "custom":
40
+ return uniquePaths([
41
+ ...resolvePaths(sandboxConfig.customWritePaths, sessionPath),
42
+ ...extraWritePaths,
43
+ ...sharedAgentStatePaths
44
+ ]);
45
+ }
46
+ })();
47
+ const network = (() => {
48
+ switch (sandboxConfig.networkMode) {
49
+ case "blocked":
50
+ return {
51
+ allowedDomains: [],
52
+ deniedDomains: [],
53
+ allowLocalBinding: sandboxConfig.allowLocalBinding,
54
+ allowUnixSockets: []
55
+ };
56
+ case "allowed":
57
+ return {
58
+ allowedDomains: void 0,
59
+ deniedDomains: [],
60
+ allowLocalBinding: sandboxConfig.allowLocalBinding,
61
+ allowUnixSockets: []
62
+ };
63
+ case "custom":
64
+ return {
65
+ allowedDomains: sandboxConfig.allowedDomains,
66
+ deniedDomains: sandboxConfig.deniedDomains,
67
+ allowLocalBinding: sandboxConfig.allowLocalBinding,
68
+ allowUnixSockets: []
69
+ };
70
+ }
71
+ })();
72
+ const enableWeakerNetworkIsolation = sandboxConfig.networkMode === "allowed" ? true : void 0;
73
+ return {
74
+ allowPty: true,
75
+ enableWeakerNetworkIsolation,
76
+ network,
77
+ filesystem: {
78
+ denyRead: resolvePaths(sandboxConfig.denyReadPaths, sessionPath),
79
+ allowWrite,
80
+ denyWrite: resolvePaths(sandboxConfig.denyWritePaths, sessionPath)
81
+ }
82
+ };
83
+ }
84
+
85
+ async function initializeSandbox(sandboxConfig, sessionPath) {
86
+ const runtimeConfig = buildSandboxRuntimeConfig(sandboxConfig, sessionPath);
87
+ await sandboxRuntime.SandboxManager.initialize(runtimeConfig);
88
+ return async () => {
89
+ await sandboxRuntime.SandboxManager.reset();
90
+ };
91
+ }
92
+ async function wrapCommand(command) {
93
+ return sandboxRuntime.SandboxManager.wrapWithSandbox(command);
94
+ }
95
+ async function wrapForMcpTransport(command, args) {
96
+ const wrappedCommand = await wrapCommand(`${command} ${args.join(" ")}`.trim());
97
+ return {
98
+ command: "sh",
99
+ args: ["-c", wrappedCommand]
100
+ };
101
+ }
102
+
103
+ exports.initializeSandbox = initializeSandbox;
104
+ exports.wrapCommand = wrapCommand;
105
+ exports.wrapForMcpTransport = wrapForMcpTransport;
@@ -1,52 +1,46 @@
1
- import { r as registerTeamsTools, P as PREVIEW_TOOL_NAME, a as PREVIEW_TOOL_TITLE, b as PREVIEW_TOOL_DESCRIPTION } from './agentGuidance-KgvYuF3R.mjs';
1
+ import { r as registerTeamsTools } from './tools-DkluDcG4.mjs';
2
2
  import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
3
3
  import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
4
4
  import { z } from 'zod';
5
- import { l as logger, C as CLIPBOARD_TOOL_NAME, a as CLIPBOARD_TOOL_TITLE, b as CLIPBOARD_TOOL_DESCRIPTION, p as pushClipboardViaDaemon, o as CLIPBOARD_MAX_BYTES, q as pushFilePreviewViaDaemon, t as setTerminalTitleViaDaemon } from './limits-CjRj8IX5.mjs';
6
- import { e as checkPreviewPath, f as registerAssistantSessionTools, g as suggestTitleForPrompt } from './index-BF6WfgV5.mjs';
5
+ import { p as pushClipboardViaDaemon, b as pushFilePreviewViaDaemon, d as setTerminalTitleViaDaemon } from './controlClient-BGbDcgWS.mjs';
6
+ import { C as CLIPBOARD_TOOL_NAME, a as CLIPBOARD_TOOL_TITLE, b as CLIPBOARD_TOOL_DESCRIPTION, c as CLIPBOARD_MAX_BYTES } from './limits-DIo7rEBR.mjs';
7
+ import { r as registerAssistantSessionTools } from './assistantTools-D6tuc6o4.mjs';
8
+ import { l as logger } from './logger-6HYUEXNk.mjs';
9
+ import { c as checkPreviewPath } from './previewPath-CXN4Vag0.mjs';
10
+ import { P as PREVIEW_TOOL_NAME, a as PREVIEW_TOOL_TITLE, b as PREVIEW_TOOL_DESCRIPTION } from './agentGuidance-CQuNlNx8.mjs';
7
11
  import 'node:fs/promises';
8
12
  import 'node:os';
13
+ import './persistence-HGW_ZVs9.mjs';
14
+ import './configuration-RfeNjFmd.mjs';
9
15
  import 'node:crypto';
10
16
  import 'axios';
11
17
  import 'tweetnacl';
12
18
  import 'socket.io-client';
13
19
  import 'node:child_process';
14
- import './types-Dh-s4Lqs.mjs';
20
+ import './terminals-Dlg0x3nY.mjs';
15
21
  import 'node:fs';
16
22
  import 'node:path';
17
- import { b as TerminalTitleSuggestRequestSchema } from './terminalTitleSuggest-DKgX3osW.mjs';
23
+ import { b as TerminalTitleSuggestRequestSchema } from './terminalTitleSuggest-CeKsX_V6.mjs';
24
+ import { s as suggestTitleForPrompt } from './titleGenerator-CQ8CoGhg.mjs';
18
25
  import { r as resolveMcpTerminalId } from './terminalToolContext-CFeGeaNm.mjs';
19
- import '@paralleldrive/cuid2';
26
+ import './client-CeGKqqcJ.mjs';
27
+ import './context-H0Bcb9S_.mjs';
28
+ import './sessionOps-SuHW8Dfe.mjs';
29
+ import './authRelay-DSAvg1uv.mjs';
30
+ import './time-D0XyHOid.mjs';
31
+ import './backgroundTaskActivity-8PdPxrvy.mjs';
32
+ import './remoteSessionClient-CYnXRynE.mjs';
33
+ import './ids-DU6sLx4C.mjs';
34
+ import './bootstrap-hxXPCFMx.mjs';
20
35
  import 'chalk';
21
36
  import 'node:util';
22
- import 'cross-spawn';
23
- import 'node:readline';
24
- import 'fs/promises';
25
- import 'ink';
26
- import 'react';
27
- import '@anthropic-ai/claude-agent-sdk';
28
- import 'node:events';
29
- import 'os';
30
- import 'child_process';
31
- import 'fs';
32
- import 'path';
33
- import '@anthropic-ai/sandbox-runtime';
34
- import 'expo-server-sdk';
35
- import 'crypto';
36
- import 'ps-list';
37
- import 'tmp';
38
- import 'open';
39
- import 'fastify';
40
- import 'fastify-type-provider-zod';
37
+ import './trimIdent-BAjmv_TG.mjs';
38
+ import './package-BhaKlnxz.mjs';
39
+ import './tmuxSocket-B8Yx20sT.mjs';
41
40
  import 'node:module';
42
- import 'node:http';
43
- import '@modelcontextprotocol/sdk/server/streamableHttp.js';
44
- import 'http';
45
- import 'util';
46
- import 'inquirer';
47
- import 'node:url';
48
- import 'node:readline/promises';
49
- import 'node-pty';
41
+ import './oneShotPrompts-DT4p6RNd.mjs';
42
+ import './projectPath-BTBIMB57.mjs';
43
+ import 'path';
50
44
  import 'url';
51
45
 
52
46
  const TERMINAL_TITLE_TOOL_NAME = "change_title";
@@ -1,54 +1,48 @@
1
1
  'use strict';
2
2
 
3
- var agentGuidance = require('./agentGuidance-BRDN1NoZ.cjs');
3
+ var tools = require('./tools-Be3AoAwu.cjs');
4
4
  var mcp_js = require('@modelcontextprotocol/sdk/server/mcp.js');
5
5
  var stdio_js = require('@modelcontextprotocol/sdk/server/stdio.js');
6
6
  var z = require('zod');
7
- var persistence = require('./limits-BH5CV5vR.cjs');
8
- var index = require('./index-rH3DrQ5B.cjs');
7
+ var controlClient = require('./controlClient-Bcwv3D21.cjs');
8
+ var limits = require('./limits-C-a7gr04.cjs');
9
+ var assistantTools = require('./assistantTools-BTqPnlFl.cjs');
10
+ var logger = require('./logger-CS0mw3fa.cjs');
11
+ var previewPath = require('./previewPath-B0rBdhy1.cjs');
12
+ var agentGuidance = require('./agentGuidance-B5NATuFa.cjs');
9
13
  require('node:fs/promises');
10
14
  require('node:os');
15
+ require('./persistence-yKTH3-5X.cjs');
16
+ require('./configuration-BSYpcPwE.cjs');
11
17
  require('node:crypto');
12
18
  require('axios');
13
19
  require('tweetnacl');
14
20
  require('socket.io-client');
15
21
  require('node:child_process');
16
- require('./types-BbvK1Tr_.cjs');
22
+ require('./terminals-B_bfC9c2.cjs');
17
23
  require('node:fs');
18
24
  require('node:path');
19
- var terminalTitleSuggest = require('./terminalTitleSuggest-Dji8I0Jy.cjs');
25
+ var terminalTitleSuggest = require('./terminalTitleSuggest-DhvRFX3H.cjs');
26
+ var titleGenerator = require('./titleGenerator-ChzMJsyg.cjs');
20
27
  var terminalToolContext = require('./terminalToolContext-DoV9Gs7K.cjs');
21
- require('@paralleldrive/cuid2');
28
+ require('./client-3Ac-O4pw.cjs');
29
+ require('./context-DsDr6E2t.cjs');
30
+ require('./sessionOps-Dn8z85h_.cjs');
31
+ require('./authRelay-BdYkC1Po.cjs');
32
+ require('./time-DCuTyook.cjs');
33
+ require('./backgroundTaskActivity-CBvUdj39.cjs');
34
+ require('./remoteSessionClient-B0LraSB9.cjs');
35
+ require('./ids-B6ZC0HGt.cjs');
36
+ require('./bootstrap-B5G1TijC.cjs');
22
37
  require('chalk');
23
38
  require('node:util');
24
- require('cross-spawn');
25
- require('node:readline');
26
- require('fs/promises');
27
- require('ink');
28
- require('react');
29
- require('@anthropic-ai/claude-agent-sdk');
30
- require('node:events');
31
- require('os');
32
- require('child_process');
33
- require('fs');
34
- require('path');
35
- require('@anthropic-ai/sandbox-runtime');
36
- require('expo-server-sdk');
37
- require('crypto');
38
- require('ps-list');
39
- require('tmp');
40
- require('open');
41
- require('fastify');
42
- require('fastify-type-provider-zod');
39
+ require('./trimIdent-4gvk9Wk6.cjs');
40
+ require('./package-BwMrPwqH.cjs');
41
+ require('./tmuxSocket-D-Xt6Vn-.cjs');
43
42
  require('node:module');
44
- require('node:http');
45
- require('@modelcontextprotocol/sdk/server/streamableHttp.js');
46
- require('http');
47
- require('util');
48
- require('inquirer');
49
- require('node:url');
50
- require('node:readline/promises');
51
- require('node-pty');
43
+ require('./oneShotPrompts-CL0dip9C.cjs');
44
+ require('./projectPath-ChLhdOyt.cjs');
45
+ require('path');
52
46
  require('url');
53
47
 
54
48
  const TERMINAL_TITLE_TOOL_NAME = "change_title";
@@ -60,22 +54,22 @@ function resolveMcpToolSurface(env) {
60
54
 
61
55
  function registerTerminalTitleSuggest(server) {
62
56
  server.server.setRequestHandler(terminalTitleSuggest.TerminalTitleSuggestRequestSchema, async (request) => {
63
- persistence.logger.debug("[MCP] terminal title suggestion requested");
64
- return { title: await index.suggestTitleForPrompt(request.params.prompt) };
57
+ logger.logger.debug("[MCP] terminal title suggestion requested");
58
+ return { title: await titleGenerator.suggestTitleForPrompt(request.params.prompt) };
65
59
  });
66
60
  }
67
61
  function registerMcpTools(server, surface, terminalId = null) {
68
- server.registerTool(persistence.CLIPBOARD_TOOL_NAME, {
69
- description: persistence.CLIPBOARD_TOOL_DESCRIPTION,
70
- title: persistence.CLIPBOARD_TOOL_TITLE,
62
+ server.registerTool(limits.CLIPBOARD_TOOL_NAME, {
63
+ description: limits.CLIPBOARD_TOOL_DESCRIPTION,
64
+ title: limits.CLIPBOARD_TOOL_TITLE,
71
65
  inputSchema: {
72
66
  text: z.z.string().describe("The text to copy to the user's clipboard")
73
67
  }
74
68
  }, async (args) => {
75
- persistence.logger.debug(`[MCP] copy_to_clipboard called (${args.text.length} chars)`);
76
- const result = await persistence.pushClipboardViaDaemon(args.text, terminalId ?? void 0);
69
+ logger.logger.debug(`[MCP] copy_to_clipboard called (${args.text.length} chars)`);
70
+ const result = await controlClient.pushClipboardViaDaemon(args.text, terminalId ?? void 0);
77
71
  if (result.delivered) {
78
- const note = result.truncated ? ` (truncated to ${persistence.CLIPBOARD_MAX_BYTES / 1024}KB \u2014 original was ${result.totalBytes} bytes)` : "";
72
+ const note = result.truncated ? ` (truncated to ${limits.CLIPBOARD_MAX_BYTES / 1024}KB \u2014 original was ${result.totalBytes} bytes)` : "";
79
73
  return {
80
74
  content: [{
81
75
  type: "text",
@@ -101,9 +95,9 @@ function registerMcpTools(server, surface, terminalId = null) {
101
95
  mode: z.z.enum(["file", "diff"]).optional().describe("'file' (default) previews the file; 'diff' is reserved and currently falls back to 'file'")
102
96
  }
103
97
  }, async (args) => {
104
- const verdict = index.checkPreviewPath(args.path);
98
+ const verdict = previewPath.checkPreviewPath(args.path);
105
99
  if (verdict.deniedReason) return { content: [{ type: "text", text: verdict.deniedReason }], isError: true };
106
- const result = await persistence.pushFilePreviewViaDaemon(terminalId, verdict.resolved, args.mode ?? "file");
100
+ const result = await controlClient.pushFilePreviewViaDaemon(terminalId, verdict.resolved, args.mode ?? "file");
107
101
  return {
108
102
  content: [{ type: "text", text: result.delivered ? `Queued a preview request for ${verdict.resolved}. This does not confirm that a browser opened it.` : `Failed to request preview: ${result.error || "unknown error"}` }],
109
103
  isError: !result.delivered
@@ -116,8 +110,8 @@ function registerMcpTools(server, surface, terminalId = null) {
116
110
  title: z.z.string().min(1).max(200).describe("The new title for this terminal")
117
111
  }
118
112
  }, async (args) => {
119
- persistence.logger.debug(`[MCP] change_title called for terminal ${terminalId}`);
120
- const result = await persistence.setTerminalTitleViaDaemon(terminalId, args.title);
113
+ logger.logger.debug(`[MCP] change_title called for terminal ${terminalId}`);
114
+ const result = await controlClient.setTerminalTitleViaDaemon(terminalId, args.title);
121
115
  if (result.ok) {
122
116
  return {
123
117
  content: [{ type: "text", text: `Successfully changed terminal title to: "${args.title}"` }],
@@ -134,7 +128,7 @@ function registerMcpTools(server, surface, terminalId = null) {
134
128
  });
135
129
  }
136
130
  if (surface === "assistant" && !process.env.VH_TEAM_SCOPE_FILE) {
137
- index.registerAssistantSessionTools(server);
131
+ assistantTools.registerAssistantSessionTools(server);
138
132
  }
139
133
  }
140
134
  async function handleMcpCommand(terminalToolsOnly = false) {
@@ -147,10 +141,10 @@ async function handleMcpCommand(terminalToolsOnly = false) {
147
141
  if (terminalToolsOnly && !terminalId) throw new Error("Very Happy terminal context is required");
148
142
  registerMcpTools(server, surface, terminalId);
149
143
  if (terminalId) registerTerminalTitleSuggest(server);
150
- if (!terminalToolsOnly && process.env.HAPPY_MANAGED !== "1" && !process.env.HAPPY_MCP_URL) agentGuidance.registerTeamsTools(server, process.env.HAPPY_SESSION_ID);
144
+ if (!terminalToolsOnly && process.env.HAPPY_MANAGED !== "1" && !process.env.HAPPY_MCP_URL) tools.registerTeamsTools(server, process.env.HAPPY_SESSION_ID);
151
145
  const transport = new stdio_js.StdioServerTransport();
152
146
  await server.connect(transport);
153
- persistence.logger.debug(`[MCP] very-happy stdio MCP server started (surface=${surface}, terminal=${terminalId ?? "none"})`);
147
+ logger.logger.debug(`[MCP] very-happy stdio MCP server started (surface=${surface}, terminal=${terminalId ?? "none"})`);
154
148
  await new Promise((resolve) => {
155
149
  process.stdin.on("close", resolve);
156
150
  process.stdin.on("end", resolve);
@@ -0,0 +1,71 @@
1
+ class MessageBuffer {
2
+ messages = [];
3
+ listeners = [];
4
+ nextId = 1;
5
+ addMessage(content, type = "assistant") {
6
+ const message = {
7
+ id: `msg-${this.nextId++}`,
8
+ timestamp: /* @__PURE__ */ new Date(),
9
+ content,
10
+ type
11
+ };
12
+ this.messages.push(message);
13
+ this.notifyListeners();
14
+ }
15
+ /**
16
+ * Update the last message of a specific type by appending content to it
17
+ * Useful for streaming responses where deltas should accumulate in one message
18
+ */
19
+ updateLastMessage(contentDelta, type = "assistant") {
20
+ for (let i = this.messages.length - 1; i >= 0; i--) {
21
+ if (this.messages[i].type === type) {
22
+ const oldMessage = this.messages[i];
23
+ const updatedMessage = {
24
+ ...oldMessage,
25
+ content: oldMessage.content + contentDelta
26
+ };
27
+ this.messages[i] = updatedMessage;
28
+ this.notifyListeners();
29
+ return;
30
+ }
31
+ }
32
+ this.addMessage(contentDelta, type);
33
+ }
34
+ /**
35
+ * Remove the last message of a specific type
36
+ * Useful for removing placeholder messages like "Thinking..." when actual response starts
37
+ */
38
+ removeLastMessage(type) {
39
+ for (let i = this.messages.length - 1; i >= 0; i--) {
40
+ if (this.messages[i].type === type) {
41
+ this.messages.splice(i, 1);
42
+ this.notifyListeners();
43
+ return true;
44
+ }
45
+ }
46
+ return false;
47
+ }
48
+ getMessages() {
49
+ return [...this.messages];
50
+ }
51
+ clear() {
52
+ this.messages = [];
53
+ this.nextId = 1;
54
+ this.notifyListeners();
55
+ }
56
+ onUpdate(listener) {
57
+ this.listeners.push(listener);
58
+ return () => {
59
+ const index = this.listeners.indexOf(listener);
60
+ if (index > -1) {
61
+ this.listeners.splice(index, 1);
62
+ }
63
+ };
64
+ }
65
+ notifyListeners() {
66
+ const messages = this.getMessages();
67
+ this.listeners.forEach((listener) => listener(messages));
68
+ }
69
+ }
70
+
71
+ export { MessageBuffer as M };
@@ -0,0 +1,73 @@
1
+ 'use strict';
2
+
3
+ class MessageBuffer {
4
+ messages = [];
5
+ listeners = [];
6
+ nextId = 1;
7
+ addMessage(content, type = "assistant") {
8
+ const message = {
9
+ id: `msg-${this.nextId++}`,
10
+ timestamp: /* @__PURE__ */ new Date(),
11
+ content,
12
+ type
13
+ };
14
+ this.messages.push(message);
15
+ this.notifyListeners();
16
+ }
17
+ /**
18
+ * Update the last message of a specific type by appending content to it
19
+ * Useful for streaming responses where deltas should accumulate in one message
20
+ */
21
+ updateLastMessage(contentDelta, type = "assistant") {
22
+ for (let i = this.messages.length - 1; i >= 0; i--) {
23
+ if (this.messages[i].type === type) {
24
+ const oldMessage = this.messages[i];
25
+ const updatedMessage = {
26
+ ...oldMessage,
27
+ content: oldMessage.content + contentDelta
28
+ };
29
+ this.messages[i] = updatedMessage;
30
+ this.notifyListeners();
31
+ return;
32
+ }
33
+ }
34
+ this.addMessage(contentDelta, type);
35
+ }
36
+ /**
37
+ * Remove the last message of a specific type
38
+ * Useful for removing placeholder messages like "Thinking..." when actual response starts
39
+ */
40
+ removeLastMessage(type) {
41
+ for (let i = this.messages.length - 1; i >= 0; i--) {
42
+ if (this.messages[i].type === type) {
43
+ this.messages.splice(i, 1);
44
+ this.notifyListeners();
45
+ return true;
46
+ }
47
+ }
48
+ return false;
49
+ }
50
+ getMessages() {
51
+ return [...this.messages];
52
+ }
53
+ clear() {
54
+ this.messages = [];
55
+ this.nextId = 1;
56
+ this.notifyListeners();
57
+ }
58
+ onUpdate(listener) {
59
+ this.listeners.push(listener);
60
+ return () => {
61
+ const index = this.listeners.indexOf(listener);
62
+ if (index > -1) {
63
+ this.listeners.splice(index, 1);
64
+ }
65
+ };
66
+ }
67
+ notifyListeners() {
68
+ const messages = this.getMessages();
69
+ this.listeners.forEach((listener) => listener(messages));
70
+ }
71
+ }
72
+
73
+ exports.MessageBuffer = MessageBuffer;