memeloop 0.0.1 → 0.1.1

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 (228) hide show
  1. package/README.md +63 -0
  2. package/dist/browser.cjs +1413 -0
  3. package/dist/browser.cjs.map +1 -0
  4. package/dist/browser.d.cts +3066 -0
  5. package/dist/browser.d.ts +3066 -0
  6. package/dist/browser.js +43 -0
  7. package/dist/chunk-2C6BJZI3.js +382 -0
  8. package/dist/chunk-2C6BJZI3.js.map +1 -0
  9. package/dist/chunk-426CJUZP.js +630 -0
  10. package/dist/chunk-426CJUZP.js.map +1 -0
  11. package/dist/chunk-7ZDTB4VZ.js +63 -0
  12. package/dist/chunk-7ZDTB4VZ.js.map +1 -0
  13. package/dist/chunk-AZFYDWIN.js +98 -0
  14. package/dist/chunk-AZFYDWIN.js.map +1 -0
  15. package/dist/chunk-BGPU4RR7.js +367 -0
  16. package/dist/chunk-BGPU4RR7.js.map +1 -0
  17. package/dist/chunk-CCEFAOSH.js +496 -0
  18. package/dist/chunk-CCEFAOSH.js.map +1 -0
  19. package/dist/chunk-FWSY5HOA.js +63 -0
  20. package/dist/chunk-FWSY5HOA.js.map +1 -0
  21. package/dist/chunk-GYIOMQMY.js +8726 -0
  22. package/dist/chunk-GYIOMQMY.js.map +1 -0
  23. package/dist/chunk-K6P63KD4.js +68 -0
  24. package/dist/chunk-K6P63KD4.js.map +1 -0
  25. package/dist/chunk-KFS2EJT6.js +42 -0
  26. package/dist/chunk-KFS2EJT6.js.map +1 -0
  27. package/dist/chunk-MAJWHAKR.js +3637 -0
  28. package/dist/chunk-MAJWHAKR.js.map +1 -0
  29. package/dist/chunk-MRKY4HGF.js +205 -0
  30. package/dist/chunk-MRKY4HGF.js.map +1 -0
  31. package/dist/chunk-T7FSXWFR.js +2744 -0
  32. package/dist/chunk-T7FSXWFR.js.map +1 -0
  33. package/dist/chunk-VZKQX5PP.js +1 -0
  34. package/dist/chunk-VZKQX5PP.js.map +1 -0
  35. package/dist/chunk-WAI6BODI.js +175 -0
  36. package/dist/chunk-WAI6BODI.js.map +1 -0
  37. package/dist/chunk-YMNXDNDW.js +798 -0
  38. package/dist/chunk-YMNXDNDW.js.map +1 -0
  39. package/dist/conversation.cjs +208 -0
  40. package/dist/conversation.cjs.map +1 -0
  41. package/dist/conversation.d.cts +100 -0
  42. package/dist/conversation.d.ts +100 -0
  43. package/dist/conversation.js +21 -0
  44. package/dist/conversation.js.map +1 -0
  45. package/dist/device-network-portable.cjs +702 -0
  46. package/dist/device-network-portable.cjs.map +1 -0
  47. package/dist/device-network-portable.d.cts +110 -0
  48. package/dist/device-network-portable.d.ts +110 -0
  49. package/dist/device-network-portable.js +53 -0
  50. package/dist/device-network-portable.js.map +1 -0
  51. package/dist/device-network.cjs +906 -0
  52. package/dist/device-network.cjs.map +1 -0
  53. package/dist/device-network.d.cts +6 -0
  54. package/dist/device-network.d.ts +6 -0
  55. package/dist/device-network.js +59 -0
  56. package/dist/device-network.js.map +1 -0
  57. package/dist/fetchProvider-WWnWnQFP.d.ts +91 -0
  58. package/dist/fetchProvider-toTHy5Nu.d.cts +91 -0
  59. package/dist/index.cjs +28051 -5459
  60. package/dist/index.cjs.map +1 -1
  61. package/dist/index.d.cts +94 -1320
  62. package/dist/index.d.ts +94 -1320
  63. package/dist/index.js +10616 -2420
  64. package/dist/index.js.map +1 -1
  65. package/dist/interface-IrKBFtL1.d.cts +493 -0
  66. package/dist/interface-IrKBFtL1.d.ts +493 -0
  67. package/dist/llm-providers.cjs +43 -8
  68. package/dist/llm-providers.cjs.map +1 -1
  69. package/dist/llm-providers.d.cts +2 -1
  70. package/dist/llm-providers.d.ts +2 -1
  71. package/dist/llm-providers.js +4 -2
  72. package/dist/llm-providers.js.map +1 -1
  73. package/dist/loop-api.cjs +5227 -2010
  74. package/dist/loop-api.cjs.map +1 -1
  75. package/dist/loop-api.d.cts +11 -5
  76. package/dist/loop-api.d.ts +11 -5
  77. package/dist/loop-api.js +86 -49
  78. package/dist/mobile.cjs +2711 -0
  79. package/dist/mobile.cjs.map +1 -0
  80. package/dist/mobile.d.cts +6 -0
  81. package/dist/mobile.d.ts +6 -0
  82. package/dist/mobile.js +22 -0
  83. package/dist/mobile.js.map +1 -0
  84. package/dist/orchestration-portable-BHB_YrNN.d.ts +2192 -0
  85. package/dist/orchestration-portable-mvYBvGBb.d.cts +2192 -0
  86. package/dist/orchestration-portable.cjs +9553 -0
  87. package/dist/orchestration-portable.cjs.map +1 -0
  88. package/dist/orchestration-portable.d.cts +5 -0
  89. package/dist/orchestration-portable.d.ts +5 -0
  90. package/dist/orchestration-portable.js +290 -0
  91. package/dist/orchestration-portable.js.map +1 -0
  92. package/dist/pairingInvite-BXPWY3aM.d.cts +149 -0
  93. package/dist/pairingInvite-Cuz0wuq9.d.ts +149 -0
  94. package/dist/promptConcat-0WNFTg4l.d.ts +516 -0
  95. package/dist/promptConcat-D6wr5V-V.d.cts +516 -0
  96. package/dist/providerRegistry-Bi6pAvSj.d.ts +86 -0
  97. package/dist/providerRegistry-CPsktuiX.d.cts +86 -0
  98. package/dist/registry-D0kbxksn.d.cts +393 -0
  99. package/dist/registry-DDbvhlhs.d.ts +393 -0
  100. package/dist/remoteClient-B_spK019.d.ts +87 -0
  101. package/dist/remoteClient-CBggnRy3.d.cts +87 -0
  102. package/dist/runtime-PGWR6FIV.js +18 -0
  103. package/dist/runtime-PGWR6FIV.js.map +1 -0
  104. package/dist/scriptDeploymentPipeline-CXJcC82H.d.ts +2464 -0
  105. package/dist/scriptDeploymentPipeline-yG1ZhVVI.d.cts +2464 -0
  106. package/dist/syncCloudDevices-BEqwgrhD.d.ts +49 -0
  107. package/dist/syncCloudDevices-Ds_Kcgrv.d.cts +49 -0
  108. package/dist/types-7pYti-k9.d.cts +255 -0
  109. package/dist/types-CdFVSntj.d.ts +255 -0
  110. package/package.json +110 -35
  111. package/dist/anthropic.cjs +0 -72
  112. package/dist/anthropic.cjs.map +0 -1
  113. package/dist/anthropic.d.cts +0 -21
  114. package/dist/anthropic.d.ts +0 -21
  115. package/dist/anthropic.js +0 -21
  116. package/dist/anthropic.js.map +0 -1
  117. package/dist/azure.cjs +0 -72
  118. package/dist/azure.cjs.map +0 -1
  119. package/dist/azure.d.cts +0 -21
  120. package/dist/azure.d.ts +0 -21
  121. package/dist/azure.js +0 -21
  122. package/dist/azure.js.map +0 -1
  123. package/dist/chunk-3CN7DFBL.js +0 -4894
  124. package/dist/chunk-3CN7DFBL.js.map +0 -1
  125. package/dist/chunk-4AZ4D7U5.js +0 -32
  126. package/dist/chunk-4AZ4D7U5.js.map +0 -1
  127. package/dist/chunk-6ON4XSOV.js +0 -63
  128. package/dist/chunk-6ON4XSOV.js.map +0 -1
  129. package/dist/chunk-DJQNGIXX.js +0 -4793
  130. package/dist/chunk-DJQNGIXX.js.map +0 -1
  131. package/dist/chunk-FKQP6AOQ.js +0 -32
  132. package/dist/chunk-FKQP6AOQ.js.map +0 -1
  133. package/dist/chunk-OVJ7JJBA.js +0 -35
  134. package/dist/chunk-OVJ7JJBA.js.map +0 -1
  135. package/dist/chunk-P4UZ7IXC.js +0 -42
  136. package/dist/chunk-YHJ2AEFR.js +0 -4933
  137. package/dist/chunk-YHJ2AEFR.js.map +0 -1
  138. package/dist/chunk-YVK7RYRO.js +0 -4973
  139. package/dist/chunk-YVK7RYRO.js.map +0 -1
  140. package/dist/code-assistant.json +0 -114
  141. package/dist/cohere.cjs +0 -72
  142. package/dist/cohere.cjs.map +0 -1
  143. package/dist/cohere.d.cts +0 -21
  144. package/dist/cohere.d.ts +0 -21
  145. package/dist/cohere.js +0 -21
  146. package/dist/cohere.js.map +0 -1
  147. package/dist/deepseek.cjs +0 -72
  148. package/dist/deepseek.cjs.map +0 -1
  149. package/dist/deepseek.d.cts +0 -21
  150. package/dist/deepseek.d.ts +0 -21
  151. package/dist/deepseek.js +0 -21
  152. package/dist/deepseek.js.map +0 -1
  153. package/dist/dist-65U7OYRG.js +0 -1257
  154. package/dist/dist-65U7OYRG.js.map +0 -1
  155. package/dist/fetchProvider-Cu4WkU5O.d.cts +0 -819
  156. package/dist/fetchProvider-Cu4WkU5O.d.ts +0 -819
  157. package/dist/frontend-ui-ux.json +0 -105
  158. package/dist/general-assistant.json +0 -95
  159. package/dist/git-master.json +0 -51
  160. package/dist/google-vertex.cjs +0 -72
  161. package/dist/google-vertex.cjs.map +0 -1
  162. package/dist/google-vertex.d.cts +0 -21
  163. package/dist/google-vertex.d.ts +0 -21
  164. package/dist/google-vertex.js +0 -21
  165. package/dist/google-vertex.js.map +0 -1
  166. package/dist/google.cjs +0 -72
  167. package/dist/google.cjs.map +0 -1
  168. package/dist/google.d.cts +0 -21
  169. package/dist/google.d.ts +0 -21
  170. package/dist/google.js +0 -21
  171. package/dist/google.js.map +0 -1
  172. package/dist/groq.cjs +0 -72
  173. package/dist/groq.cjs.map +0 -1
  174. package/dist/groq.d.cts +0 -21
  175. package/dist/groq.d.ts +0 -21
  176. package/dist/groq.js +0 -21
  177. package/dist/groq.js.map +0 -1
  178. package/dist/index.d.mts +0 -3203
  179. package/dist/index.mjs +0 -7064
  180. package/dist/index.mjs.map +0 -1
  181. package/dist/mistral.cjs +0 -72
  182. package/dist/mistral.cjs.map +0 -1
  183. package/dist/mistral.d.cts +0 -21
  184. package/dist/mistral.d.ts +0 -21
  185. package/dist/mistral.js +0 -21
  186. package/dist/mistral.js.map +0 -1
  187. package/dist/multipart-parser-EJCXIUHC.js +0 -372
  188. package/dist/multipart-parser-EJCXIUHC.js.map +0 -1
  189. package/dist/openai.cjs +0 -72
  190. package/dist/openai.cjs.map +0 -1
  191. package/dist/openai.d.cts +0 -21
  192. package/dist/openai.d.ts +0 -21
  193. package/dist/openai.js +0 -21
  194. package/dist/openai.js.map +0 -1
  195. package/dist/perplexity.cjs +0 -72
  196. package/dist/perplexity.cjs.map +0 -1
  197. package/dist/perplexity.d.cts +0 -21
  198. package/dist/perplexity.d.ts +0 -21
  199. package/dist/perplexity.js +0 -21
  200. package/dist/perplexity.js.map +0 -1
  201. package/dist/playwright.json +0 -52
  202. package/dist/promptConcat-BJdazTg5.d.cts +0 -1832
  203. package/dist/promptConcat-BJdazTg5.d.ts +0 -1832
  204. package/dist/promptConcat-CAkpni_8.d.cts +0 -1834
  205. package/dist/promptConcat-CAkpni_8.d.ts +0 -1834
  206. package/dist/promptConcat-CfH5-GAE.d.cts +0 -1036
  207. package/dist/promptConcat-ChcAZOOL.d.ts +0 -1036
  208. package/dist/promptConcat-G5TnJVRy.d.cts +0 -1800
  209. package/dist/promptConcat-G5TnJVRy.d.ts +0 -1800
  210. package/dist/promptConcat-L72eowzp.d.ts +0 -1090
  211. package/dist/promptConcat-eLHdN7K8.d.cts +0 -1090
  212. package/dist/src-VTSXKG72.js +0 -1409
  213. package/dist/src-VTSXKG72.js.map +0 -1
  214. package/dist/togetherai.cjs +0 -72
  215. package/dist/togetherai.cjs.map +0 -1
  216. package/dist/togetherai.d.cts +0 -21
  217. package/dist/togetherai.d.ts +0 -21
  218. package/dist/togetherai.js +0 -21
  219. package/dist/togetherai.js.map +0 -1
  220. package/dist/types-B0Jm2l38.d.cts +0 -767
  221. package/dist/types-B0Jm2l38.d.ts +0 -767
  222. package/dist/xai.cjs +0 -72
  223. package/dist/xai.cjs.map +0 -1
  224. package/dist/xai.d.cts +0 -21
  225. package/dist/xai.d.ts +0 -21
  226. package/dist/xai.js +0 -21
  227. package/dist/xai.js.map +0 -1
  228. /package/dist/{chunk-P4UZ7IXC.js.map → browser.js.map} +0 -0
@@ -0,0 +1,798 @@
1
+ import {
2
+ OrchestrationError
3
+ } from "./chunk-FWSY5HOA.js";
4
+
5
+ // src/storage/tiddlyWikiHttpStorage.ts
6
+ var PREFIX = "$:/memeloop";
7
+ var DEFAULT_MAX_INLINE_BLOB = 256 * 1024;
8
+ var DEFAULT_CAS_ATTEMPTS = 3;
9
+ function bytesToBase64(bytes) {
10
+ let binary = "";
11
+ for (const byte of bytes) binary += String.fromCharCode(byte);
12
+ return btoa(binary);
13
+ }
14
+ function base64ToBytes(value) {
15
+ const binary = atob(value);
16
+ const bytes = new Uint8Array(binary.length);
17
+ for (let index = 0; index < binary.length; index += 1) bytes[index] = binary.charCodeAt(index);
18
+ return bytes;
19
+ }
20
+ function escapeFilterValue(value) {
21
+ return value.replace(/["\\[\]]/g, (character) => `\\${character}`);
22
+ }
23
+ var TiddlyWikiHttpStorage = class {
24
+ baseUrl;
25
+ recipe;
26
+ fetchImpl;
27
+ credentialHandle;
28
+ credentialResolver;
29
+ maxInlineBlobBytes;
30
+ maxCasAttempts;
31
+ constructor(options) {
32
+ this.baseUrl = options.baseUrl.replace(/\/+$/, "");
33
+ this.recipe = options.recipe ?? "default";
34
+ this.fetchImpl = options.fetchImpl ?? globalThis.fetch.bind(globalThis);
35
+ this.maxInlineBlobBytes = options.maxInlineBlobBytes ?? DEFAULT_MAX_INLINE_BLOB;
36
+ this.maxCasAttempts = options.maxCasAttempts ?? DEFAULT_CAS_ATTEMPTS;
37
+ if (options.credentialHandle === void 0 !== (options.credentialResolver === void 0)) {
38
+ throw new OrchestrationError({
39
+ code: "INVALID",
40
+ message: "credentialHandle and credentialResolver must be provided together",
41
+ retryable: false
42
+ });
43
+ }
44
+ this.credentialHandle = options.credentialHandle;
45
+ this.credentialResolver = options.credentialResolver;
46
+ }
47
+ eventTitle(conversationId, messageId) {
48
+ return `${PREFIX}/e/${conversationId}/${messageId}`;
49
+ }
50
+ metaTitle(conversationId) {
51
+ return `${PREFIX}/meta/${conversationId}`;
52
+ }
53
+ blobTitle(contentHash) {
54
+ return `${PREFIX}/blob/${contentHash}`;
55
+ }
56
+ definitionTitle(id) {
57
+ return `${PREFIX}/def/${id}`;
58
+ }
59
+ instanceTitle(id) {
60
+ return `${PREFIX}/inst/${id}`;
61
+ }
62
+ imTitle(channelId, imUserId) {
63
+ return `${PREFIX}/im/${channelId}/${imUserId}`;
64
+ }
65
+ tiddlerUrl(title) {
66
+ return `${this.baseUrl}/recipes/${encodeURIComponent(this.recipe)}/tiddlers/${encodeURIComponent(title)}`;
67
+ }
68
+ filterUrl(filter) {
69
+ return `${this.baseUrl}/recipes/${encodeURIComponent(this.recipe)}/tiddlers.json?filter=${encodeURIComponent(filter)}`;
70
+ }
71
+ async headers(url, method, extra = {}) {
72
+ const credentialHeaders = this.credentialHandle && this.credentialResolver ? await this.credentialResolver.resolveHeaders(this.credentialHandle, { url, method }) : {};
73
+ return {
74
+ "content-type": "application/json",
75
+ "x-requested-with": "TiddlyWiki",
76
+ ...credentialHeaders,
77
+ ...extra
78
+ };
79
+ }
80
+ /** GET a tiddler; returns null on 404. Includes the ETag when the server sends one. */
81
+ async readTiddler(title) {
82
+ const url = this.tiddlerUrl(title);
83
+ const response = await this.fetchImpl(url, { headers: await this.headers(url, "GET") });
84
+ if (response.status === 404) return null;
85
+ if (!response.ok) {
86
+ throw new OrchestrationError({ code: "UNAVAILABLE", message: `tiddler read failed: HTTP ${response.status}`, retryable: true });
87
+ }
88
+ const tiddler = await response.json();
89
+ const etag = response.headers.get("etag") ?? void 0;
90
+ return { tiddler, ...etag ? { etag } : {} };
91
+ }
92
+ /** CAS write: If-Match when an ETag is known; bounded retries on 412/409. */
93
+ async writeTiddler(title, build) {
94
+ for (let attempt = 1; attempt <= this.maxCasAttempts; attempt += 1) {
95
+ const current = await this.readTiddler(title);
96
+ if (current && !current.etag) {
97
+ throw new OrchestrationError({ code: "CONFLICT", message: `tiddler '${title}' has no ETag for a safe update`, retryable: false });
98
+ }
99
+ const next = build(current?.tiddler ?? null);
100
+ const url = this.tiddlerUrl(title);
101
+ const precondition = current ? { "if-match": current.etag } : { "if-none-match": "*" };
102
+ const response = await this.fetchImpl(url, {
103
+ method: "PUT",
104
+ headers: await this.headers(url, "PUT", precondition),
105
+ body: JSON.stringify(next)
106
+ });
107
+ if (response.ok) return;
108
+ if (response.status === 412 || response.status === 409) {
109
+ if (attempt === this.maxCasAttempts) {
110
+ throw new OrchestrationError({
111
+ code: "CONFLICT",
112
+ message: `tiddler '${title}' was modified concurrently after ${attempt} CAS attempts`,
113
+ retryable: true
114
+ });
115
+ }
116
+ continue;
117
+ }
118
+ throw new OrchestrationError({ code: "UNAVAILABLE", message: `tiddler write failed: HTTP ${response.status}`, retryable: true });
119
+ }
120
+ }
121
+ async listByPrefix(prefix) {
122
+ const filter = `[prefix["${escapeFilterValue(prefix)}"]]`;
123
+ const url = this.filterUrl(filter);
124
+ const response = await this.fetchImpl(url, { headers: await this.headers(url, "GET") });
125
+ if (!response.ok) {
126
+ throw new OrchestrationError({ code: "UNAVAILABLE", message: `tiddler list failed: HTTP ${response.status}`, retryable: true });
127
+ }
128
+ return await response.json();
129
+ }
130
+ parsePayload(tiddler) {
131
+ return JSON.parse(tiddler.text ?? "{}");
132
+ }
133
+ async listConversations(options = {}) {
134
+ const tiddlers = await this.listByPrefix(`${PREFIX}/meta/`);
135
+ const metas = tiddlers.map((tiddler) => this.parsePayload(tiddler));
136
+ metas.sort((a, b) => (b.lastMessageTimestamp ?? 0) - (a.lastMessageTimestamp ?? 0));
137
+ const offset = options.offset ?? 0;
138
+ const limit = options.limit ?? metas.length;
139
+ return metas.slice(offset, offset + limit);
140
+ }
141
+ async getMessages(conversationId, _options = {}) {
142
+ const tiddlers = await this.listByPrefix(`${PREFIX}/e/${conversationId}/`);
143
+ const messages = tiddlers.map((tiddler) => this.parsePayload(tiddler));
144
+ messages.sort((a, b) => (a.lamportClock ?? 0) - (b.lamportClock ?? 0));
145
+ return messages;
146
+ }
147
+ async appendMessage(message) {
148
+ await this.writeTiddler(this.eventTitle(message.conversationId, message.messageId), () => ({
149
+ title: this.eventTitle(message.conversationId, message.messageId),
150
+ text: JSON.stringify(message)
151
+ }));
152
+ }
153
+ async insertMessagesIfAbsent(messages) {
154
+ for (const message of messages) {
155
+ const title = this.eventTitle(message.conversationId, message.messageId);
156
+ const existing = await this.readTiddler(title);
157
+ if (!existing) {
158
+ await this.writeTiddler(title, () => ({ title, text: JSON.stringify(message) }));
159
+ }
160
+ }
161
+ }
162
+ async getMaxLamportClockForConversation(conversationId) {
163
+ const messages = await this.getMessages(conversationId);
164
+ return messages.reduce((max, message) => Math.max(max, message.lamportClock ?? 0), 0);
165
+ }
166
+ async upsertConversationMetadata(meta) {
167
+ const title = this.metaTitle(meta.conversationId);
168
+ await this.writeTiddler(title, () => ({ title, text: JSON.stringify(meta) }));
169
+ }
170
+ async getConversationMeta(conversationId) {
171
+ const result = await this.readTiddler(this.metaTitle(conversationId));
172
+ return result ? this.parsePayload(result.tiddler) : null;
173
+ }
174
+ async saveAttachment(reference, data) {
175
+ if (data.byteLength > this.maxInlineBlobBytes) {
176
+ throw new OrchestrationError({
177
+ code: "INVALID",
178
+ message: `blob of ${data.byteLength} bytes exceeds the inline limit ${this.maxInlineBlobBytes}; store it in an external BlobStore and keep the reference`,
179
+ retryable: false,
180
+ details: { maxInlineBlobBytes: this.maxInlineBlobBytes }
181
+ });
182
+ }
183
+ const title = this.blobTitle(reference.contentHash);
184
+ await this.writeTiddler(title, () => ({
185
+ title,
186
+ text: JSON.stringify({ reference, dataBase64: bytesToBase64(data) })
187
+ }));
188
+ }
189
+ async getAttachment(contentHash) {
190
+ const result = await this.readTiddler(this.blobTitle(contentHash));
191
+ if (!result) return null;
192
+ return this.parsePayload(result.tiddler).reference;
193
+ }
194
+ async readAttachmentData(contentHash) {
195
+ const result = await this.readTiddler(this.blobTitle(contentHash));
196
+ if (!result) return null;
197
+ return base64ToBytes(this.parsePayload(result.tiddler).dataBase64);
198
+ }
199
+ async getAgentDefinition(id) {
200
+ const result = await this.readTiddler(this.definitionTitle(id));
201
+ return result ? this.parsePayload(result.tiddler) : null;
202
+ }
203
+ async saveAgentDefinition(definition) {
204
+ const title = this.definitionTitle(definition.id);
205
+ await this.writeTiddler(title, () => ({ title, text: JSON.stringify(definition) }));
206
+ }
207
+ async saveAgentInstance(meta) {
208
+ const title = this.instanceTitle(meta.instanceId);
209
+ await this.writeTiddler(title, () => ({ title, text: JSON.stringify(meta) }));
210
+ }
211
+ async getImBinding(channelId, imUserId) {
212
+ const result = await this.readTiddler(this.imTitle(channelId, imUserId));
213
+ return result ? this.parsePayload(result.tiddler) : null;
214
+ }
215
+ async setImBinding(record) {
216
+ const title = this.imTitle(record.channelId, record.imUserId);
217
+ await this.writeTiddler(title, () => ({ title, text: JSON.stringify(record) }));
218
+ }
219
+ };
220
+
221
+ // src/agent-management/AgentSessionController.ts
222
+ var AgentSessionController = class {
223
+ options;
224
+ listener = null;
225
+ snapshot = {
226
+ agent: null,
227
+ loading: false,
228
+ error: null,
229
+ messages: [],
230
+ orderedMessageIds: [],
231
+ streamingMessageIds: /* @__PURE__ */ new Set()
232
+ };
233
+ unsubAgentUpdates = null;
234
+ unsubMessages = null;
235
+ pollingTimer = null;
236
+ agentId = null;
237
+ constructor(options) {
238
+ this.options = {
239
+ pollInterval: 500,
240
+ ...options
241
+ };
242
+ }
243
+ // ── Lifecycle ─────────────────────────────────────────────────
244
+ /**
245
+ * Start a session for the given agent ID.
246
+ * Fetches the agent, subscribes to live updates, and loads messages.
247
+ */
248
+ async start(agentId) {
249
+ this.agentId = agentId;
250
+ this.emitPartial({ loading: true, error: null });
251
+ try {
252
+ const [agent, rawMessages] = await Promise.all([
253
+ this.options.agentInstanceClient.fetchAgent(agentId),
254
+ this.options.conversationClient.getMessages(agentId)
255
+ ]);
256
+ const orderedMessageIds = rawMessages.map((m) => m.messageId);
257
+ const messagesMap = /* @__PURE__ */ new Map();
258
+ for (const m of rawMessages) messagesMap.set(m.messageId, m);
259
+ this.emitPartial({
260
+ agent,
261
+ loading: false,
262
+ messages: rawMessages,
263
+ orderedMessageIds,
264
+ streamingMessageIds: /* @__PURE__ */ new Set()
265
+ });
266
+ this.unsubAgentUpdates = this.options.agentInstanceClient.subscribeToUpdates(
267
+ agentId,
268
+ this.handleAgentUpdate
269
+ );
270
+ this.unsubMessages = this.options.conversationClient.subscribeToMessages(
271
+ agentId,
272
+ this.handleNewMessage
273
+ );
274
+ this.startPolling(agentId);
275
+ } catch (error_) {
276
+ this.emitPartial({
277
+ loading: false,
278
+ error: error_ instanceof Error ? error_ : new Error(String(error_))
279
+ });
280
+ }
281
+ }
282
+ /** Stop the session and clean up subscriptions. */
283
+ stop() {
284
+ this.stopPolling();
285
+ this.unsubAgentUpdates?.();
286
+ this.unsubAgentUpdates = null;
287
+ this.unsubMessages?.();
288
+ this.unsubMessages = null;
289
+ this.agentId = null;
290
+ }
291
+ // ── Actions ───────────────────────────────────────────────────
292
+ /** Send a user message. */
293
+ async sendMessage(content, file, wikiTiddlers) {
294
+ if (!this.agentId) return;
295
+ this.emitPartial({ error: null });
296
+ try {
297
+ await this.options.conversationClient.sendMessage(this.agentId, content, file, wikiTiddlers);
298
+ } catch (error_) {
299
+ this.emitPartial({
300
+ error: error_ instanceof Error ? error_ : new Error(String(error_))
301
+ });
302
+ }
303
+ }
304
+ /** Cancel the current agent operation. */
305
+ async cancel() {
306
+ if (!this.agentId) return;
307
+ try {
308
+ await this.options.agentInstanceClient.cancelAgent(this.agentId);
309
+ } catch (error_) {
310
+ this.emitPartial({
311
+ error: error_ instanceof Error ? error_ : new Error(String(error_))
312
+ });
313
+ }
314
+ }
315
+ /** Delete a turn starting at the given user message ID. */
316
+ async deleteTurn(userMessageId) {
317
+ return this.options.conversationClient.deleteTurn(userMessageId);
318
+ }
319
+ /** Retry a turn starting at the given user message ID. */
320
+ async retryTurn(userMessageId) {
321
+ return this.options.conversationClient.retryTurn(userMessageId);
322
+ }
323
+ // ── Subscription ──────────────────────────────────────────────
324
+ /** Subscribe to snapshot changes. Returns unsubscribe function. */
325
+ subscribe(listener) {
326
+ this.listener = listener;
327
+ listener({ ...this.snapshot, streamingMessageIds: new Set(this.snapshot.streamingMessageIds) });
328
+ return () => {
329
+ if (this.listener === listener) this.listener = null;
330
+ };
331
+ }
332
+ /** Get current snapshot without subscribing. */
333
+ getSnapshot() {
334
+ return this.snapshot;
335
+ }
336
+ // ── Private helpers ───────────────────────────────────────────
337
+ emitPartial(partial) {
338
+ this.snapshot = { ...this.snapshot, ...partial };
339
+ if (this.listener) {
340
+ this.listener({
341
+ ...this.snapshot,
342
+ streamingMessageIds: new Set(this.snapshot.streamingMessageIds)
343
+ });
344
+ }
345
+ }
346
+ handleAgentUpdate = (update) => {
347
+ if (this.snapshot.agent) {
348
+ this.emitPartial({ agent: { ...this.snapshot.agent, ...update } });
349
+ }
350
+ };
351
+ handleNewMessage = (message) => {
352
+ const messages = [...this.snapshot.messages.filter((m) => m.messageId !== message.messageId), message];
353
+ const orderedMessageIds = [.../* @__PURE__ */ new Set([...this.snapshot.orderedMessageIds, message.messageId])];
354
+ this.emitPartial({ messages, orderedMessageIds });
355
+ };
356
+ startPolling(agentId) {
357
+ this.stopPolling();
358
+ this.pollingTimer = setInterval(async () => {
359
+ try {
360
+ const agent = await this.options.agentInstanceClient.fetchAgent(agentId);
361
+ this.emitPartial({ agent });
362
+ } catch {
363
+ }
364
+ }, this.options.pollInterval);
365
+ }
366
+ stopPolling() {
367
+ if (this.pollingTimer !== null) {
368
+ clearInterval(this.pollingTimer);
369
+ this.pollingTimer = null;
370
+ }
371
+ }
372
+ };
373
+
374
+ // src/agent-management/AgentDefinitionEditorController.ts
375
+ var AgentDefinitionEditorController = class {
376
+ options;
377
+ listener = null;
378
+ state = {
379
+ agentDefinition: null,
380
+ agentName: "",
381
+ previewAgentId: null,
382
+ isLoading: false,
383
+ isSaving: false,
384
+ promptSchema: null
385
+ };
386
+ autosaveTimer = null;
387
+ constructor(options) {
388
+ this.options = {
389
+ autosaveDebounceMs: 1e3,
390
+ ...options
391
+ };
392
+ }
393
+ // ── Lifecycle ─────────────────────────────────────────────────
394
+ /** Load an agent definition and its prompt schema. */
395
+ async loadDefinition(definitionId) {
396
+ this.emit({ isLoading: true });
397
+ try {
398
+ const [definition, previewAgentId] = await Promise.all([
399
+ this.options.definitionRepository.getAgentDef(definitionId),
400
+ this.findOrCreatePreviewAgent(definitionId)
401
+ ]);
402
+ if (!definition) {
403
+ this.emit({ isLoading: false });
404
+ return;
405
+ }
406
+ let promptSchema = null;
407
+ if (definition.agentFrameworkID) {
408
+ try {
409
+ promptSchema = await this.options.agentInstanceClient.getFrameworkConfigSchema(
410
+ definition.agentFrameworkID
411
+ );
412
+ } catch {
413
+ promptSchema = null;
414
+ }
415
+ }
416
+ this.state = {
417
+ agentDefinition: definition,
418
+ agentName: definition.name ?? "",
419
+ previewAgentId,
420
+ isLoading: false,
421
+ isSaving: false,
422
+ promptSchema
423
+ };
424
+ this.emit(this.state);
425
+ } catch {
426
+ this.emit({ isLoading: false });
427
+ }
428
+ }
429
+ /** Update the agent definition field. Triggers debounced autosave. */
430
+ updateDefinition(change) {
431
+ if (!this.state.agentDefinition) return;
432
+ const updated = { ...this.state.agentDefinition, ...change };
433
+ this.state = { ...this.state, agentDefinition: updated, agentName: updated.name ?? "" };
434
+ this.emit({ agentDefinition: updated, agentName: this.state.agentName });
435
+ this.scheduleAutosave(updated);
436
+ }
437
+ /** Force an immediate save to the repository. */
438
+ async saveNow() {
439
+ if (!this.state.agentDefinition) return;
440
+ this.emit({ isSaving: true });
441
+ try {
442
+ await this.options.definitionRepository.updateAgentDef({
443
+ id: this.state.agentDefinition.id,
444
+ name: this.state.agentName,
445
+ description: this.state.agentDefinition.description,
446
+ agentFrameworkConfig: this.state.agentDefinition.agentFrameworkConfig,
447
+ aiApiConfig: this.state.agentDefinition.aiApiConfig,
448
+ agentTools: this.state.agentDefinition.agentTools,
449
+ heartbeat: this.state.agentDefinition.heartbeat
450
+ });
451
+ } catch {
452
+ } finally {
453
+ this.emit({ isSaving: false });
454
+ }
455
+ }
456
+ /** Reload the prompt schema for a framework ID. */
457
+ async reloadSchema(frameworkId) {
458
+ try {
459
+ const schema = await this.options.agentInstanceClient.getFrameworkConfigSchema(frameworkId);
460
+ this.emit({ promptSchema: schema });
461
+ } catch {
462
+ this.emit({ promptSchema: null });
463
+ }
464
+ }
465
+ // ── Preview agent lifecycle ───────────────────────────────────
466
+ /** Get or create a preview agent instance tied to this definition. */
467
+ async findOrCreatePreviewAgent(definitionId) {
468
+ try {
469
+ const result = await this.options.agentInstanceClient.createAgent(definitionId, {
470
+ preview: true
471
+ });
472
+ return result.id;
473
+ } catch {
474
+ return null;
475
+ }
476
+ }
477
+ // ── Scheduled tasks ───────────────────────────────────────────
478
+ async loadScheduledTasks() {
479
+ if (!this.state.previewAgentId) return [];
480
+ return this.options.scheduledTaskClient.listScheduledTasksForAgent(
481
+ this.state.previewAgentId
482
+ );
483
+ }
484
+ async saveScheduledTask(input) {
485
+ return this.options.scheduledTaskClient.createScheduledTask(input);
486
+ }
487
+ async deleteScheduledTask(taskId) {
488
+ return this.options.scheduledTaskClient.deleteScheduledTask(taskId);
489
+ }
490
+ // ── Subscription ──────────────────────────────────────────────
491
+ subscribe(listener) {
492
+ this.listener = listener;
493
+ listener(this.state);
494
+ return () => {
495
+ if (this.listener === listener) this.listener = null;
496
+ };
497
+ }
498
+ getState() {
499
+ return this.state;
500
+ }
501
+ // ── Private ───────────────────────────────────────────────────
502
+ emit(change) {
503
+ this.listener?.(change);
504
+ }
505
+ scheduleAutosave(definition) {
506
+ if (this.autosaveTimer !== null) clearTimeout(this.autosaveTimer);
507
+ this.autosaveTimer = setTimeout(() => {
508
+ this.options.definitionRepository.updateAgentDef({
509
+ id: definition.id,
510
+ name: definition.name,
511
+ description: definition.description,
512
+ agentFrameworkConfig: definition.agentFrameworkConfig,
513
+ aiApiConfig: definition.aiApiConfig,
514
+ agentTools: definition.agentTools,
515
+ heartbeat: definition.heartbeat
516
+ }).catch(() => {
517
+ });
518
+ }, this.options.autosaveDebounceMs);
519
+ }
520
+ };
521
+
522
+ // src/agent-management/AgentCreationController.ts
523
+ var AgentCreationController = class {
524
+ options;
525
+ listener = null;
526
+ state = {
527
+ currentStep: 0,
528
+ agentName: "",
529
+ selectedTemplate: null,
530
+ temporaryAgentDefinition: null,
531
+ previewAgentId: null,
532
+ isLoading: false,
533
+ promptSchema: null
534
+ };
535
+ constructor(options) {
536
+ this.options = {
537
+ defaultFrameworkId: "memeloopAgentToolLoop",
538
+ ...options
539
+ };
540
+ }
541
+ /** Initialize the creation wizard, optionally from a saved tab state. */
542
+ async start(definitionId, templateDefinitionId) {
543
+ this.emit({ isLoading: true });
544
+ try {
545
+ if (definitionId) {
546
+ const temporaryDefinition = await this.options.definitionRepository.getAgentDef(definitionId);
547
+ if (temporaryDefinition) {
548
+ this.state = {
549
+ ...this.state,
550
+ temporaryAgentDefinition: temporaryDefinition,
551
+ agentName: temporaryDefinition.name ?? "",
552
+ isLoading: false
553
+ };
554
+ this.emit(this.state);
555
+ if (templateDefinitionId) {
556
+ const template = await this.options.definitionRepository.getAgentDef(templateDefinitionId);
557
+ if (template) {
558
+ this.state = { ...this.state, selectedTemplate: template };
559
+ this.emit(this.state);
560
+ }
561
+ }
562
+ return;
563
+ }
564
+ }
565
+ this.emit({ isLoading: false });
566
+ } catch {
567
+ this.emit({ isLoading: false });
568
+ }
569
+ }
570
+ /** Select a template for the new agent. */
571
+ selectTemplate(template) {
572
+ this.state = { ...this.state, selectedTemplate: template };
573
+ this.emit(this.state);
574
+ }
575
+ /** Update the agent name. */
576
+ setAgentName(name) {
577
+ this.state = { ...this.state, agentName: name };
578
+ this.emit(this.state);
579
+ }
580
+ /** Advance to the next wizard step. */
581
+ nextStep() {
582
+ this.state = { ...this.state, currentStep: Math.min(this.state.currentStep + 1, 2) };
583
+ this.emit(this.state);
584
+ }
585
+ /** Go back to the previous wizard step. */
586
+ previousStep() {
587
+ this.state = { ...this.state, currentStep: Math.max(this.state.currentStep - 1, 0) };
588
+ this.emit(this.state);
589
+ }
590
+ /** Set the current wizard step directly. */
591
+ setStep(step) {
592
+ this.state = { ...this.state, currentStep: Math.max(0, Math.min(step, 2)) };
593
+ this.emit(this.state);
594
+ }
595
+ /** Update the temporary agent definition. */
596
+ updateTemporaryDefinition(change) {
597
+ const updated = this.state.temporaryAgentDefinition ? { ...this.state.temporaryAgentDefinition, ...change } : null;
598
+ this.state = { ...this.state, temporaryAgentDefinition: updated };
599
+ this.emit(this.state);
600
+ }
601
+ /** Set the prompt schema for the selected framework. */
602
+ setPromptSchema(schema) {
603
+ this.state = { ...this.state, promptSchema: schema };
604
+ this.emit(this.state);
605
+ }
606
+ /**
607
+ * Create a preview agent instance for the chat-preview step.
608
+ * Should be called when entering step 2 (or the chat preview step).
609
+ */
610
+ async createPreviewAgent(definitionId) {
611
+ this.emit({ isLoading: true });
612
+ try {
613
+ const result = await this.options.agentInstanceClient.createAgent(definitionId, {
614
+ preview: true
615
+ });
616
+ this.state = { ...this.state, previewAgentId: result.id, isLoading: false };
617
+ this.emit(this.state);
618
+ } catch {
619
+ this.emit({ isLoading: false });
620
+ }
621
+ }
622
+ /**
623
+ * Finalize creation: persist the temporary definition and create the actual
624
+ * agent instance. Returns the final agent instance ID, or null on failure.
625
+ */
626
+ async finalize() {
627
+ if (!this.state.temporaryAgentDefinition) return null;
628
+ try {
629
+ const definition = await this.options.definitionRepository.createAgentDef(
630
+ this.state.temporaryAgentDefinition
631
+ );
632
+ const instance = await this.options.agentInstanceClient.createAgent(definition.id);
633
+ return instance.id;
634
+ } catch {
635
+ return null;
636
+ }
637
+ }
638
+ /** Clean up temporary resources. */
639
+ async cleanup() {
640
+ if (this.state.previewAgentId) {
641
+ try {
642
+ await this.options.agentInstanceClient.deleteAgent(this.state.previewAgentId);
643
+ } catch {
644
+ }
645
+ }
646
+ }
647
+ // ── Subscription ──────────────────────────────────────────────
648
+ subscribe(listener) {
649
+ this.listener = listener;
650
+ listener({ ...this.state });
651
+ return () => {
652
+ if (this.listener === listener) this.listener = null;
653
+ };
654
+ }
655
+ getState() {
656
+ return this.state;
657
+ }
658
+ // ── Private ───────────────────────────────────────────────────
659
+ emit(change) {
660
+ this.state = { ...this.state, ...change };
661
+ this.listener?.({ ...this.state });
662
+ }
663
+ };
664
+
665
+ // src/agent-management/PromptPreviewController.ts
666
+ var PromptPreviewController = class {
667
+ options;
668
+ listener = null;
669
+ state = {
670
+ open: false,
671
+ baseMode: "preview",
672
+ activeTab: "tree",
673
+ loading: false,
674
+ progress: 0,
675
+ currentStep: "",
676
+ currentPlugin: null,
677
+ result: null,
678
+ lastUpdated: null,
679
+ formFieldsToScrollTo: []
680
+ };
681
+ constructor(options) {
682
+ this.options = options;
683
+ }
684
+ /** Open the dialog with an optional base mode. */
685
+ open(baseMode) {
686
+ this.state = {
687
+ ...this.state,
688
+ open: true,
689
+ baseMode: baseMode ?? "preview",
690
+ loading: false,
691
+ progress: 0,
692
+ currentStep: "Starting...",
693
+ currentPlugin: null,
694
+ result: null,
695
+ lastUpdated: null,
696
+ formFieldsToScrollTo: []
697
+ };
698
+ this.emit();
699
+ }
700
+ /** Close the dialog. */
701
+ close() {
702
+ this.state = {
703
+ ...this.state,
704
+ open: false,
705
+ baseMode: "preview",
706
+ lastUpdated: null,
707
+ formFieldsToScrollTo: []
708
+ };
709
+ this.emit();
710
+ }
711
+ /** Set the active tab in the dialog. */
712
+ setActiveTab(tab) {
713
+ this.state = { ...this.state, activeTab: tab };
714
+ this.emit();
715
+ }
716
+ /** Set form fields to scroll to (for edit mode navigation). */
717
+ setFormFieldsToScrollTo(fieldPaths) {
718
+ this.state = { ...this.state, formFieldsToScrollTo: fieldPaths };
719
+ this.emit();
720
+ }
721
+ /**
722
+ * Generate a preview of the prompt tree.
723
+ * @param agentFrameworkConfig The agent's framework configuration
724
+ * @param messages Current conversation messages
725
+ * @param inputText Optional input text to include in the preview
726
+ */
727
+ async generate(agentFrameworkConfig, messages, inputText) {
728
+ this.state = {
729
+ ...this.state,
730
+ loading: true,
731
+ progress: 0,
732
+ currentStep: "Preparing..."
733
+ };
734
+ this.emit();
735
+ try {
736
+ const result = await this.options.previewClient.generatePreview(
737
+ agentFrameworkConfig,
738
+ messages,
739
+ inputText,
740
+ (progress) => {
741
+ this.state = {
742
+ ...this.state,
743
+ progress: progress.progress,
744
+ currentStep: progress.step,
745
+ currentPlugin: progress.currentPlugin ?? null
746
+ };
747
+ this.emit();
748
+ }
749
+ );
750
+ this.state = {
751
+ ...this.state,
752
+ loading: false,
753
+ progress: 1,
754
+ currentStep: "Complete",
755
+ currentPlugin: null,
756
+ result,
757
+ lastUpdated: /* @__PURE__ */ new Date()
758
+ };
759
+ this.emit();
760
+ return result;
761
+ } catch {
762
+ this.state = {
763
+ ...this.state,
764
+ loading: false,
765
+ progress: 0,
766
+ currentStep: "Error occurred",
767
+ currentPlugin: null,
768
+ result: null
769
+ };
770
+ this.emit();
771
+ return null;
772
+ }
773
+ }
774
+ // ── Subscription ──────────────────────────────────────────────
775
+ subscribe(listener) {
776
+ this.listener = listener;
777
+ listener({ ...this.state });
778
+ return () => {
779
+ if (this.listener === listener) this.listener = null;
780
+ };
781
+ }
782
+ getState() {
783
+ return this.state;
784
+ }
785
+ // ── Private ───────────────────────────────────────────────────
786
+ emit() {
787
+ this.listener?.({ ...this.state });
788
+ }
789
+ };
790
+
791
+ export {
792
+ TiddlyWikiHttpStorage,
793
+ AgentSessionController,
794
+ AgentDefinitionEditorController,
795
+ AgentCreationController,
796
+ PromptPreviewController
797
+ };
798
+ //# sourceMappingURL=chunk-YMNXDNDW.js.map