@jini-ai/http-kit 0.2.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 (227) hide show
  1. package/LICENSE +201 -0
  2. package/README.md +107 -0
  3. package/dist/active-context.d.ts +99 -0
  4. package/dist/active-context.d.ts.map +1 -0
  5. package/dist/active-context.js +77 -0
  6. package/dist/active-context.js.map +1 -0
  7. package/dist/adapter.d.ts +36 -0
  8. package/dist/adapter.d.ts.map +1 -0
  9. package/dist/adapter.js +92 -0
  10. package/dist/adapter.js.map +1 -0
  11. package/dist/agents.d.ts +55 -0
  12. package/dist/agents.d.ts.map +1 -0
  13. package/dist/agents.js +23 -0
  14. package/dist/agents.js.map +1 -0
  15. package/dist/api-security-middleware.d.ts +146 -0
  16. package/dist/api-security-middleware.d.ts.map +1 -0
  17. package/dist/api-security-middleware.js +276 -0
  18. package/dist/api-security-middleware.js.map +1 -0
  19. package/dist/attachments.d.ts +317 -0
  20. package/dist/attachments.d.ts.map +1 -0
  21. package/dist/attachments.js +664 -0
  22. package/dist/attachments.js.map +1 -0
  23. package/dist/cancel-owned-runs.d.ts +44 -0
  24. package/dist/cancel-owned-runs.d.ts.map +1 -0
  25. package/dist/cancel-owned-runs.js +35 -0
  26. package/dist/cancel-owned-runs.js.map +1 -0
  27. package/dist/compat.d.ts +22 -0
  28. package/dist/compat.d.ts.map +1 -0
  29. package/dist/compat.js +17 -0
  30. package/dist/compat.js.map +1 -0
  31. package/dist/component-catalog.d.ts +74 -0
  32. package/dist/component-catalog.d.ts.map +1 -0
  33. package/dist/component-catalog.js +74 -0
  34. package/dist/component-catalog.js.map +1 -0
  35. package/dist/connectors.d.ts +165 -0
  36. package/dist/connectors.d.ts.map +1 -0
  37. package/dist/connectors.js +474 -0
  38. package/dist/connectors.js.map +1 -0
  39. package/dist/daemon-status.d.ts +72 -0
  40. package/dist/daemon-status.d.ts.map +1 -0
  41. package/dist/daemon-status.js +60 -0
  42. package/dist/daemon-status.js.map +1 -0
  43. package/dist/db-ops.d.ts +116 -0
  44. package/dist/db-ops.d.ts.map +1 -0
  45. package/dist/db-ops.js +191 -0
  46. package/dist/db-ops.js.map +1 -0
  47. package/dist/delegated-tools.d.ts +46 -0
  48. package/dist/delegated-tools.d.ts.map +1 -0
  49. package/dist/delegated-tools.js +155 -0
  50. package/dist/delegated-tools.js.map +1 -0
  51. package/dist/express/run-stream.d.ts +15 -0
  52. package/dist/express/run-stream.d.ts.map +1 -0
  53. package/dist/express/run-stream.js +11 -0
  54. package/dist/express/run-stream.js.map +1 -0
  55. package/dist/express-index.d.ts +32 -0
  56. package/dist/express-index.d.ts.map +1 -0
  57. package/dist/express-index.js +14 -0
  58. package/dist/express-index.js.map +1 -0
  59. package/dist/fastify/adapter.d.ts +31 -0
  60. package/dist/fastify/adapter.d.ts.map +1 -0
  61. package/dist/fastify/adapter.js +64 -0
  62. package/dist/fastify/adapter.js.map +1 -0
  63. package/dist/fastify/agents.d.ts +13 -0
  64. package/dist/fastify/agents.d.ts.map +1 -0
  65. package/dist/fastify/agents.js +7 -0
  66. package/dist/fastify/agents.js.map +1 -0
  67. package/dist/fastify/api-security-middleware.d.ts +64 -0
  68. package/dist/fastify/api-security-middleware.d.ts.map +1 -0
  69. package/dist/fastify/api-security-middleware.js +139 -0
  70. package/dist/fastify/api-security-middleware.js.map +1 -0
  71. package/dist/fastify/compat.d.ts +22 -0
  72. package/dist/fastify/compat.d.ts.map +1 -0
  73. package/dist/fastify/compat.js +16 -0
  74. package/dist/fastify/compat.js.map +1 -0
  75. package/dist/fastify/daemon-status.d.ts +22 -0
  76. package/dist/fastify/daemon-status.d.ts.map +1 -0
  77. package/dist/fastify/daemon-status.js +9 -0
  78. package/dist/fastify/daemon-status.js.map +1 -0
  79. package/dist/fastify/host-tools.d.ts +13 -0
  80. package/dist/fastify/host-tools.d.ts.map +1 -0
  81. package/dist/fastify/host-tools.js +8 -0
  82. package/dist/fastify/host-tools.js.map +1 -0
  83. package/dist/fastify/index.d.ts +36 -0
  84. package/dist/fastify/index.d.ts.map +1 -0
  85. package/dist/fastify/index.js +18 -0
  86. package/dist/fastify/index.js.map +1 -0
  87. package/dist/fastify/local-daemon-request.d.ts +43 -0
  88. package/dist/fastify/local-daemon-request.d.ts.map +1 -0
  89. package/dist/fastify/local-daemon-request.js +155 -0
  90. package/dist/fastify/local-daemon-request.js.map +1 -0
  91. package/dist/fastify/origin.d.ts +21 -0
  92. package/dist/fastify/origin.d.ts.map +1 -0
  93. package/dist/fastify/origin.js +14 -0
  94. package/dist/fastify/origin.js.map +1 -0
  95. package/dist/fastify/request.d.ts +20 -0
  96. package/dist/fastify/request.d.ts.map +1 -0
  97. package/dist/fastify/request.js +25 -0
  98. package/dist/fastify/request.js.map +1 -0
  99. package/dist/fastify/response.d.ts +20 -0
  100. package/dist/fastify/response.d.ts.map +1 -0
  101. package/dist/fastify/response.js +41 -0
  102. package/dist/fastify/response.js.map +1 -0
  103. package/dist/fastify/route-registration-guard.d.ts +70 -0
  104. package/dist/fastify/route-registration-guard.d.ts.map +1 -0
  105. package/dist/fastify/route-registration-guard.js +69 -0
  106. package/dist/fastify/route-registration-guard.js.map +1 -0
  107. package/dist/fastify/run-stream.d.ts +18 -0
  108. package/dist/fastify/run-stream.d.ts.map +1 -0
  109. package/dist/fastify/run-stream.js +10 -0
  110. package/dist/fastify/run-stream.js.map +1 -0
  111. package/dist/fastify/runs.d.ts +17 -0
  112. package/dist/fastify/runs.d.ts.map +1 -0
  113. package/dist/fastify/runs.js +33 -0
  114. package/dist/fastify/runs.js.map +1 -0
  115. package/dist/frontend-control.d.ts +131 -0
  116. package/dist/frontend-control.d.ts.map +1 -0
  117. package/dist/frontend-control.js +77 -0
  118. package/dist/frontend-control.js.map +1 -0
  119. package/dist/frontend-sessions.d.ts +100 -0
  120. package/dist/frontend-sessions.d.ts.map +1 -0
  121. package/dist/frontend-sessions.js +180 -0
  122. package/dist/frontend-sessions.js.map +1 -0
  123. package/dist/health.d.ts +91 -0
  124. package/dist/health.d.ts.map +1 -0
  125. package/dist/health.js +53 -0
  126. package/dist/health.js.map +1 -0
  127. package/dist/host-tools.d.ts +174 -0
  128. package/dist/host-tools.d.ts.map +1 -0
  129. package/dist/host-tools.js +338 -0
  130. package/dist/host-tools.js.map +1 -0
  131. package/dist/index.d.ts +86 -0
  132. package/dist/index.d.ts.map +1 -0
  133. package/dist/index.js +40 -0
  134. package/dist/index.js.map +1 -0
  135. package/dist/local-daemon-request.d.ts +44 -0
  136. package/dist/local-daemon-request.d.ts.map +1 -0
  137. package/dist/local-daemon-request.js +145 -0
  138. package/dist/local-daemon-request.js.map +1 -0
  139. package/dist/media.d.ts +131 -0
  140. package/dist/media.d.ts.map +1 -0
  141. package/dist/media.js +352 -0
  142. package/dist/media.js.map +1 -0
  143. package/dist/memory.d.ts +230 -0
  144. package/dist/memory.d.ts.map +1 -0
  145. package/dist/memory.js +331 -0
  146. package/dist/memory.js.map +1 -0
  147. package/dist/model-proxy.d.ts +45 -0
  148. package/dist/model-proxy.d.ts.map +1 -0
  149. package/dist/model-proxy.js +619 -0
  150. package/dist/model-proxy.js.map +1 -0
  151. package/dist/origin-validation.d.ts +64 -0
  152. package/dist/origin-validation.d.ts.map +1 -0
  153. package/dist/origin-validation.js +226 -0
  154. package/dist/origin-validation.js.map +1 -0
  155. package/dist/origin.d.ts +32 -0
  156. package/dist/origin.d.ts.map +1 -0
  157. package/dist/origin.js +14 -0
  158. package/dist/origin.js.map +1 -0
  159. package/dist/pack-http.d.ts +30 -0
  160. package/dist/pack-http.d.ts.map +1 -0
  161. package/dist/pack-http.js +12 -0
  162. package/dist/pack-http.js.map +1 -0
  163. package/dist/raw-sse.d.ts +44 -0
  164. package/dist/raw-sse.d.ts.map +1 -0
  165. package/dist/raw-sse.js +93 -0
  166. package/dist/raw-sse.js.map +1 -0
  167. package/dist/remote-run-events.d.ts +66 -0
  168. package/dist/remote-run-events.d.ts.map +1 -0
  169. package/dist/remote-run-events.js +230 -0
  170. package/dist/remote-run-events.js.map +1 -0
  171. package/dist/request.d.ts +19 -0
  172. package/dist/request.d.ts.map +1 -0
  173. package/dist/request.js +25 -0
  174. package/dist/request.js.map +1 -0
  175. package/dist/research.d.ts +42 -0
  176. package/dist/research.d.ts.map +1 -0
  177. package/dist/research.js +316 -0
  178. package/dist/research.js.map +1 -0
  179. package/dist/response.d.ts +14 -0
  180. package/dist/response.d.ts.map +1 -0
  181. package/dist/response.js +45 -0
  182. package/dist/response.js.map +1 -0
  183. package/dist/route-manifest.d.ts +31 -0
  184. package/dist/route-manifest.d.ts.map +1 -0
  185. package/dist/route-manifest.js +103 -0
  186. package/dist/route-manifest.js.map +1 -0
  187. package/dist/route-registration-guard.d.ts +65 -0
  188. package/dist/route-registration-guard.d.ts.map +1 -0
  189. package/dist/route-registration-guard.js +71 -0
  190. package/dist/route-registration-guard.js.map +1 -0
  191. package/dist/routines.d.ts +114 -0
  192. package/dist/routines.d.ts.map +1 -0
  193. package/dist/routines.js +320 -0
  194. package/dist/routines.js.map +1 -0
  195. package/dist/run-stream.d.ts +60 -0
  196. package/dist/run-stream.d.ts.map +1 -0
  197. package/dist/run-stream.js +108 -0
  198. package/dist/run-stream.js.map +1 -0
  199. package/dist/runs.d.ts +79 -0
  200. package/dist/runs.d.ts.map +1 -0
  201. package/dist/runs.js +232 -0
  202. package/dist/runs.js.map +1 -0
  203. package/dist/sse.d.ts +139 -0
  204. package/dist/sse.d.ts.map +1 -0
  205. package/dist/sse.js +157 -0
  206. package/dist/sse.js.map +1 -0
  207. package/dist/terminals.d.ts +125 -0
  208. package/dist/terminals.d.ts.map +1 -0
  209. package/dist/terminals.js +349 -0
  210. package/dist/terminals.js.map +1 -0
  211. package/dist/tool-catalog.d.ts +68 -0
  212. package/dist/tool-catalog.d.ts.map +1 -0
  213. package/dist/tool-catalog.js +68 -0
  214. package/dist/tool-catalog.js.map +1 -0
  215. package/dist/types.d.ts +58 -0
  216. package/dist/types.d.ts.map +1 -0
  217. package/dist/types.js +5 -0
  218. package/dist/types.js.map +1 -0
  219. package/dist/workspace-root.d.ts +69 -0
  220. package/dist/workspace-root.d.ts.map +1 -0
  221. package/dist/workspace-root.js +63 -0
  222. package/dist/workspace-root.js.map +1 -0
  223. package/dist/xai.d.ts +86 -0
  224. package/dist/xai.d.ts.map +1 -0
  225. package/dist/xai.js +668 -0
  226. package/dist/xai.js.map +1 -0
  227. package/package.json +58 -0
@@ -0,0 +1,474 @@
1
+ /**
2
+ * @module connectors
3
+ *
4
+ * `POST/GET /api/connectors/{auth,storage,payments,db,realtime}/...` — JSON transport over five
5
+ * narrow provider ports. The ports live here because they are the exact behavior this transport
6
+ * consumes; concrete adapters such as `@jini-ai/capability-providers` satisfy them structurally at a
7
+ * product composition root. That dependency direction is deliberate: locked `@jini-ai/http-kit` must not
8
+ * point down into an incubating implementation package.
9
+ *
10
+ * **SEC-005 throughout**: every provider call is wrapped so a raw Stripe/SQL/JWT/WebSocket error
11
+ * never reaches the HTTP caller verbatim — matching `media.ts`/`delegated-tools.ts`'s
12
+ * `reportInternalError` precedent exactly (a correlation-id-bearing generic `INTERNAL_ERROR`, the
13
+ * real error only reaching a host-owned sink).
14
+ *
15
+ * **`NOT_CONFIGURED` (503)**: every route's very first check is whether its one required
16
+ * capability slot (`deps.auth`/`deps.storage`/`deps.payments`/`deps.db`/`deps.realtime`) is even
17
+ * supplied — all five are independently optional on {@link ConnectorsHttpDeps}, and
18
+ * `@jini-ai/server`'s zero-config default (see that package's `create-local-node-daemon.ts` wiring)
19
+ * leaves every slot unconfigured. A request against an unconfigured capability gets a clean 503
20
+ * before touching anything else, never a crash or a fabricated result — the same "capability exists
21
+ * and is reachable but inert until a host configures it" shape `host-tools.ts#denyAllWorkspaceRoots`/
22
+ * `db-ops.ts#denyAllDaemonDbPolicy` already established for other zero-config-default route packs.
23
+ *
24
+ * **Wire shapes, chosen for this route pack specifically (the ports themselves have no opinion on
25
+ * HTTP transport):**
26
+ * - `StorageProvider.put`/`.get` deal in raw `Uint8Array` — JSON has no binary type, so this pack
27
+ * base64-encodes on the wire (`dataBase64` request/response field), the same encoding
28
+ * `media.ts#runMediaGenerationInBackground` already uses for generated bytes.
29
+ * - `AuthProvider.verifySession` takes a bearer token; the session-verification route accepts it in
30
+ * a POST JSON body. Credentials do not belong in URLs, where browser history, reverse proxies,
31
+ * and access logs commonly retain them.
32
+ * - `DbProvider.query`'s optional `where` filter is a JSON-encoded string in the `?where=` query
33
+ * parameter (`{"status":"active"}`), decoded and validated as a plain object before being handed
34
+ * to the provider.
35
+ * - `RealtimeProvider.subscribe` has no route here — see the realtime section below for why.
36
+ */
37
+ import { randomUUID } from 'node:crypto';
38
+ import { createApiError } from '@jini-ai/protocol';
39
+ import { defineJsonRoute, mountJsonRoute } from './adapter.js';
40
+ import { validationError } from './request.js';
41
+ import { err, ok } from './types.js';
42
+ function defaultInternalErrorSink(context) {
43
+ // eslint-disable-next-line no-console
44
+ console.error(`[@jini-ai/http-kit] internal error (connectors/${context.source}.${context.operation}, correlationId=${context.correlationId})`, context.error);
45
+ }
46
+ function notConfiguredError(capability) {
47
+ return createApiError('NOT_CONFIGURED', `${capability} provider not configured`);
48
+ }
49
+ /** Runs one provider call, converting any thrown error into a redacted, correlation-id-bearing `INTERNAL_ERROR` (SEC-005) instead of letting it reach the HTTP caller verbatim. */
50
+ async function guardedCall(deps, source, operation, fn) {
51
+ try {
52
+ return ok(await fn());
53
+ }
54
+ catch (error) {
55
+ const correlationId = randomUUID();
56
+ const sink = deps.onInternalError ?? defaultInternalErrorSink;
57
+ sink({ source, operation, correlationId, error });
58
+ return err(createApiError('INTERNAL_ERROR', 'an internal error occurred', { requestId: correlationId }));
59
+ }
60
+ }
61
+ function isRecord(value) {
62
+ return typeof value === 'object' && value !== null && !Array.isArray(value);
63
+ }
64
+ function nonEmptyString(value) {
65
+ return typeof value === 'string' && value.trim().length > 0 ? value : null;
66
+ }
67
+ function firstQueryValue(raw) {
68
+ const value = Array.isArray(raw) ? raw[0] : raw;
69
+ return typeof value === 'string' ? value : undefined;
70
+ }
71
+ // ---------------------------------------------------------------------------
72
+ // auth
73
+ // ---------------------------------------------------------------------------
74
+ function parseAuthCredentials(input) {
75
+ if (!isRecord(input.body))
76
+ return err(validationError('body must be a JSON object'));
77
+ const email = nonEmptyString(input.body.email);
78
+ if (!email)
79
+ return err(validationError('email must be a non-empty string', [{ path: 'email', message: 'required non-empty string' }]));
80
+ const password = nonEmptyString(input.body.password);
81
+ if (!password)
82
+ return err(validationError('password must be a non-empty string', [{ path: 'password', message: 'required non-empty string' }]));
83
+ return ok({ email, password });
84
+ }
85
+ function parseAuthToken(input) {
86
+ if (!isRecord(input.body))
87
+ return err(validationError('body must be a JSON object'));
88
+ const token = nonEmptyString(input.body.token);
89
+ if (!token)
90
+ return err(validationError('token must be a non-empty string', [{ path: 'token', message: 'required non-empty string' }]));
91
+ return ok(token);
92
+ }
93
+ export const connectorsAuthSignUpRoute = defineJsonRoute({
94
+ method: 'post',
95
+ path: '/api/connectors/auth/signup',
96
+ requireSameOrigin: true,
97
+ parse: parseAuthCredentials,
98
+ handle: async (credentials, deps) => {
99
+ if (!deps.auth)
100
+ return err(notConfiguredError('auth'));
101
+ const result = await guardedCall(deps, 'auth', 'signUp', () => deps.auth.signUp(credentials));
102
+ return result.ok ? ok({ user: result.value }) : result;
103
+ },
104
+ successStatus: 201,
105
+ });
106
+ export const connectorsAuthSignInRoute = defineJsonRoute({
107
+ method: 'post',
108
+ path: '/api/connectors/auth/signin',
109
+ requireSameOrigin: true,
110
+ parse: parseAuthCredentials,
111
+ handle: async (credentials, deps) => {
112
+ if (!deps.auth)
113
+ return err(notConfiguredError('auth'));
114
+ const result = await guardedCall(deps, 'auth', 'signIn', () => deps.auth.signIn(credentials));
115
+ return result.ok ? ok({ session: result.value }) : result;
116
+ },
117
+ });
118
+ export const connectorsAuthSignOutRoute = defineJsonRoute({
119
+ method: 'post',
120
+ path: '/api/connectors/auth/signout',
121
+ requireSameOrigin: true,
122
+ parse: parseAuthToken,
123
+ handle: async (token, deps) => {
124
+ if (!deps.auth)
125
+ return err(notConfiguredError('auth'));
126
+ const result = await guardedCall(deps, 'auth', 'signOut', () => deps.auth.signOut(token));
127
+ return result.ok ? ok({ ok: true }) : result;
128
+ },
129
+ });
130
+ export const connectorsAuthSessionRoute = defineJsonRoute({
131
+ method: 'post',
132
+ path: '/api/connectors/auth/session',
133
+ requireSameOrigin: true,
134
+ parse: parseAuthToken,
135
+ handle: async (token, deps) => {
136
+ if (!deps.auth)
137
+ return err(notConfiguredError('auth'));
138
+ const result = await guardedCall(deps, 'auth', 'verifySession', () => deps.auth.verifySession(token));
139
+ return result.ok ? ok({ user: result.value }) : result;
140
+ },
141
+ });
142
+ // ---------------------------------------------------------------------------
143
+ // storage
144
+ // ---------------------------------------------------------------------------
145
+ function parseStorageKey(input) {
146
+ const key = input.params.key;
147
+ return typeof key === 'string' && key.length > 0 ? ok(key) : err(validationError('key must be a non-empty path parameter'));
148
+ }
149
+ /**
150
+ * Strict base64 well-formedness check.
151
+ *
152
+ * `Buffer.from(value, 'base64')` cannot be used as the validator here because it never rejects
153
+ * anything: it silently skips every character outside the alphabet and returns whatever it managed
154
+ * to decode. `"!!!!"` decodes to zero bytes, and a payload truncated in transit decodes to a
155
+ * shorter one — both of which would then be written over whatever already lived at that key. A
156
+ * storage `put` that quietly persists the wrong bytes is worse than one that refuses them, so this
157
+ * insists on a canonical encoding: alphabet only, at most two trailing pad characters, a length
158
+ * that is a whole number of 4-character groups, and at least one real data character.
159
+ */
160
+ const BASE64_PATTERN = /^[A-Za-z0-9+/]+={0,2}$/;
161
+ function isWellFormedBase64(value) {
162
+ if (value.length === 0 || value.length % 4 !== 0)
163
+ return false;
164
+ return BASE64_PATTERN.test(value);
165
+ }
166
+ function parseStoragePut(input) {
167
+ const keyResult = parseStorageKey(input);
168
+ if (!keyResult.ok)
169
+ return keyResult;
170
+ if (!isRecord(input.body))
171
+ return err(validationError('body must be a JSON object'));
172
+ const dataBase64 = input.body.dataBase64;
173
+ if (typeof dataBase64 !== 'string' || !isWellFormedBase64(dataBase64)) {
174
+ return err(validationError('dataBase64 must be a non-empty base64-encoded string', [{ path: 'dataBase64', message: 'required base64 string' }]));
175
+ }
176
+ const contentType = input.body.contentType;
177
+ if (contentType !== undefined && typeof contentType !== 'string') {
178
+ return err(validationError('contentType must be a string when provided'));
179
+ }
180
+ return ok({ key: keyResult.value, dataBase64, ...(contentType !== undefined ? { contentType: contentType } : {}) });
181
+ }
182
+ function parseStorageListQuery(input) {
183
+ const prefix = firstQueryValue(input.query.prefix);
184
+ return ok(prefix);
185
+ }
186
+ export const connectorsStoragePutRoute = defineJsonRoute({
187
+ method: 'put',
188
+ path: '/api/connectors/storage/:key',
189
+ requireSameOrigin: true,
190
+ parse: parseStoragePut,
191
+ handle: async ({ key, dataBase64, contentType }, deps) => {
192
+ if (!deps.storage)
193
+ return err(notConfiguredError('storage'));
194
+ const options = contentType !== undefined ? { contentType } : undefined;
195
+ const result = await guardedCall(deps, 'storage', 'put', () => deps.storage.put(key, Buffer.from(dataBase64, 'base64'), options));
196
+ return result.ok ? ok({ object: result.value }) : result;
197
+ },
198
+ });
199
+ export const connectorsStorageGetRoute = defineJsonRoute({
200
+ method: 'get',
201
+ path: '/api/connectors/storage/:key',
202
+ parse: parseStorageKey,
203
+ handle: async (key, deps) => {
204
+ if (!deps.storage)
205
+ return err(notConfiguredError('storage'));
206
+ const result = await guardedCall(deps, 'storage', 'get', () => deps.storage.get(key));
207
+ if (!result.ok)
208
+ return result;
209
+ if (result.value === null)
210
+ return err(createApiError('NOT_FOUND', 'storage object not found'));
211
+ return ok({ dataBase64: Buffer.from(result.value).toString('base64') });
212
+ },
213
+ });
214
+ export const connectorsStorageDeleteRoute = defineJsonRoute({
215
+ method: 'delete',
216
+ path: '/api/connectors/storage/:key',
217
+ requireSameOrigin: true,
218
+ parse: parseStorageKey,
219
+ handle: async (key, deps) => {
220
+ if (!deps.storage)
221
+ return err(notConfiguredError('storage'));
222
+ const result = await guardedCall(deps, 'storage', 'delete', () => deps.storage.delete(key));
223
+ return result.ok ? ok({ ok: true }) : result;
224
+ },
225
+ });
226
+ export const connectorsStorageListRoute = defineJsonRoute({
227
+ method: 'get',
228
+ path: '/api/connectors/storage',
229
+ parse: parseStorageListQuery,
230
+ handle: async (prefix, deps) => {
231
+ if (!deps.storage)
232
+ return err(notConfiguredError('storage'));
233
+ const result = await guardedCall(deps, 'storage', 'list', () => deps.storage.list(prefix));
234
+ return result.ok ? ok({ objects: result.value }) : result;
235
+ },
236
+ });
237
+ // ---------------------------------------------------------------------------
238
+ // payments
239
+ // ---------------------------------------------------------------------------
240
+ function parseChargeInput(input) {
241
+ if (!isRecord(input.body))
242
+ return err(validationError('body must be a JSON object'));
243
+ const amountCents = input.body.amountCents;
244
+ // Cents are a whole, positive unit. `isFinite` alone let `-125.5` reach `payments.charge()`,
245
+ // where a negative amount is a refund nobody requested and a fractional one is rounded by the
246
+ // provider in a way the caller cannot predict — and neither is recoverable once the charge
247
+ // exists. `isSafeInteger` also rejects magnitudes past the point where JSON round-trips stop
248
+ // being exact, which at a money boundary is a value nobody should be allowed to guess at.
249
+ if (typeof amountCents !== 'number' || !Number.isSafeInteger(amountCents) || amountCents <= 0) {
250
+ return err(validationError('amountCents must be a positive whole number of cents', [{ path: 'amountCents', message: 'required positive integer' }]));
251
+ }
252
+ const currency = nonEmptyString(input.body.currency);
253
+ if (!currency)
254
+ return err(validationError('currency must be a non-empty string', [{ path: 'currency', message: 'required non-empty string' }]));
255
+ const customerRef = nonEmptyString(input.body.customerRef);
256
+ if (!customerRef) {
257
+ return err(validationError('customerRef must be a non-empty string', [{ path: 'customerRef', message: 'required non-empty string' }]));
258
+ }
259
+ const description = input.body.description;
260
+ if (description !== undefined && typeof description !== 'string') {
261
+ return err(validationError('description must be a string when provided'));
262
+ }
263
+ return ok({ amountCents, currency, customerRef, ...(description !== undefined ? { description: description } : {}) });
264
+ }
265
+ function parseChargeId(input) {
266
+ const id = input.params.id;
267
+ return typeof id === 'string' && id.length > 0 ? ok(id) : err(validationError('id must be a non-empty path parameter'));
268
+ }
269
+ export const connectorsPaymentsChargeRoute = defineJsonRoute({
270
+ method: 'post',
271
+ path: '/api/connectors/payments/charge',
272
+ requireSameOrigin: true,
273
+ parse: parseChargeInput,
274
+ handle: async (input, deps) => {
275
+ if (!deps.payments)
276
+ return err(notConfiguredError('payments'));
277
+ const result = await guardedCall(deps, 'payments', 'charge', () => deps.payments.charge(input));
278
+ return result.ok ? ok({ charge: result.value }) : result;
279
+ },
280
+ successStatus: 201,
281
+ });
282
+ export const connectorsPaymentsGetRoute = defineJsonRoute({
283
+ method: 'get',
284
+ path: '/api/connectors/payments/:id',
285
+ parse: parseChargeId,
286
+ handle: async (id, deps) => {
287
+ if (!deps.payments)
288
+ return err(notConfiguredError('payments'));
289
+ const result = await guardedCall(deps, 'payments', 'getCharge', () => deps.payments.getCharge(id));
290
+ if (!result.ok)
291
+ return result;
292
+ if (result.value === null)
293
+ return err(createApiError('NOT_FOUND', 'charge not found'));
294
+ return ok({ charge: result.value });
295
+ },
296
+ });
297
+ export const connectorsPaymentsRefundRoute = defineJsonRoute({
298
+ method: 'post',
299
+ path: '/api/connectors/payments/:id/refund',
300
+ requireSameOrigin: true,
301
+ parse: parseChargeId,
302
+ handle: async (id, deps) => {
303
+ if (!deps.payments)
304
+ return err(notConfiguredError('payments'));
305
+ const result = await guardedCall(deps, 'payments', 'refund', () => deps.payments.refund(id));
306
+ return result.ok ? ok({ charge: result.value }) : result;
307
+ },
308
+ });
309
+ // ---------------------------------------------------------------------------
310
+ // db
311
+ // ---------------------------------------------------------------------------
312
+ function parseDbCollection(input) {
313
+ const collection = input.params.collection;
314
+ return typeof collection === 'string' && collection.length > 0
315
+ ? ok(collection)
316
+ : err(validationError('collection must be a non-empty path parameter'));
317
+ }
318
+ function parseDbInsert(input) {
319
+ const collectionResult = parseDbCollection(input);
320
+ if (!collectionResult.ok)
321
+ return collectionResult;
322
+ if (!isRecord(input.body))
323
+ return err(validationError('body must be a JSON object'));
324
+ const id = input.body.id;
325
+ if (typeof id !== 'string' || id.length === 0) {
326
+ return err(validationError('id must be a non-empty string field', [{ path: 'id', message: 'required non-empty string' }]));
327
+ }
328
+ return ok({ collection: collectionResult.value, record: input.body });
329
+ }
330
+ function parseDbCollectionId(input) {
331
+ const collectionResult = parseDbCollection(input);
332
+ if (!collectionResult.ok)
333
+ return collectionResult;
334
+ const id = input.params.id;
335
+ if (typeof id !== 'string' || id.length === 0)
336
+ return err(validationError('id must be a non-empty path parameter'));
337
+ return ok({ collection: collectionResult.value, id });
338
+ }
339
+ function parseDbUpdate(input) {
340
+ const parsed = parseDbCollectionId(input);
341
+ if (!parsed.ok)
342
+ return parsed;
343
+ if (!isRecord(input.body))
344
+ return err(validationError('body must be a JSON object'));
345
+ return ok({ ...parsed.value, patch: input.body });
346
+ }
347
+ function parseDbQueryRequest(input) {
348
+ const collectionResult = parseDbCollection(input);
349
+ if (!collectionResult.ok)
350
+ return collectionResult;
351
+ const whereRaw = firstQueryValue(input.query.where);
352
+ if (whereRaw === undefined)
353
+ return ok({ collection: collectionResult.value });
354
+ let parsedWhere;
355
+ try {
356
+ parsedWhere = JSON.parse(whereRaw);
357
+ }
358
+ catch {
359
+ return err(validationError('where must be valid JSON when provided'));
360
+ }
361
+ if (!isRecord(parsedWhere))
362
+ return err(validationError('where must be a JSON object when provided'));
363
+ return ok({ collection: collectionResult.value, query: { where: parsedWhere } });
364
+ }
365
+ export const connectorsDbInsertRoute = defineJsonRoute({
366
+ method: 'post',
367
+ path: '/api/connectors/db/:collection',
368
+ requireSameOrigin: true,
369
+ parse: parseDbInsert,
370
+ handle: async ({ collection, record }, deps) => {
371
+ if (!deps.db)
372
+ return err(notConfiguredError('db'));
373
+ const result = await guardedCall(deps, 'db', 'insert', () => deps.db.insert(collection, record));
374
+ return result.ok ? ok({ record: result.value }) : result;
375
+ },
376
+ successStatus: 201,
377
+ });
378
+ export const connectorsDbGetRoute = defineJsonRoute({
379
+ method: 'get',
380
+ path: '/api/connectors/db/:collection/:id',
381
+ parse: parseDbCollectionId,
382
+ handle: async ({ collection, id }, deps) => {
383
+ if (!deps.db)
384
+ return err(notConfiguredError('db'));
385
+ const result = await guardedCall(deps, 'db', 'get', () => deps.db.get(collection, id));
386
+ if (!result.ok)
387
+ return result;
388
+ if (result.value === null)
389
+ return err(createApiError('NOT_FOUND', 'record not found'));
390
+ return ok({ record: result.value });
391
+ },
392
+ });
393
+ export const connectorsDbUpdateRoute = defineJsonRoute({
394
+ method: 'patch',
395
+ path: '/api/connectors/db/:collection/:id',
396
+ requireSameOrigin: true,
397
+ parse: parseDbUpdate,
398
+ handle: async ({ collection, id, patch }, deps) => {
399
+ if (!deps.db)
400
+ return err(notConfiguredError('db'));
401
+ const result = await guardedCall(deps, 'db', 'update', () => deps.db.update(collection, id, patch));
402
+ if (!result.ok)
403
+ return result;
404
+ if (result.value === null)
405
+ return err(createApiError('NOT_FOUND', 'record not found'));
406
+ return ok({ record: result.value });
407
+ },
408
+ });
409
+ export const connectorsDbDeleteRoute = defineJsonRoute({
410
+ method: 'delete',
411
+ path: '/api/connectors/db/:collection/:id',
412
+ requireSameOrigin: true,
413
+ parse: parseDbCollectionId,
414
+ handle: async ({ collection, id }, deps) => {
415
+ if (!deps.db)
416
+ return err(notConfiguredError('db'));
417
+ const result = await guardedCall(deps, 'db', 'delete', () => deps.db.delete(collection, id));
418
+ return result.ok ? ok({ ok: true }) : result;
419
+ },
420
+ });
421
+ export const connectorsDbQueryRoute = defineJsonRoute({
422
+ method: 'get',
423
+ path: '/api/connectors/db/:collection',
424
+ parse: parseDbQueryRequest,
425
+ handle: async ({ collection, query }, deps) => {
426
+ if (!deps.db)
427
+ return err(notConfiguredError('db'));
428
+ const result = await guardedCall(deps, 'db', 'query', () => deps.db.query(collection, query));
429
+ return result.ok ? ok({ records: result.value }) : result;
430
+ },
431
+ });
432
+ function parseRealtimePublish(input) {
433
+ const channel = input.params.channel;
434
+ if (typeof channel !== 'string' || channel.length === 0) {
435
+ return err(validationError('channel must be a non-empty path parameter'));
436
+ }
437
+ if (!isRecord(input.body) || !('event' in input.body)) {
438
+ return err(validationError('body must be a JSON object with an event field', [{ path: 'event', message: 'required' }]));
439
+ }
440
+ return ok({ channel, event: input.body.event });
441
+ }
442
+ export const connectorsRealtimePublishRoute = defineJsonRoute({
443
+ method: 'post',
444
+ path: '/api/connectors/realtime/:channel/publish',
445
+ requireSameOrigin: true,
446
+ parse: parseRealtimePublish,
447
+ handle: async ({ channel, event }, deps) => {
448
+ if (!deps.realtime)
449
+ return err(notConfiguredError('realtime'));
450
+ const result = await guardedCall(deps, 'realtime', 'publish', () => deps.realtime.publish(channel, event));
451
+ return result.ok ? ok({ ok: true }) : result;
452
+ },
453
+ });
454
+ /** Mounts every connectors route on `app`. A pack's `http(app, services)` calls this directly. */
455
+ export function registerConnectorsRoutes(app, deps, adapter) {
456
+ mountJsonRoute(app, connectorsAuthSignUpRoute, deps, adapter);
457
+ mountJsonRoute(app, connectorsAuthSignInRoute, deps, adapter);
458
+ mountJsonRoute(app, connectorsAuthSignOutRoute, deps, adapter);
459
+ mountJsonRoute(app, connectorsAuthSessionRoute, deps, adapter);
460
+ mountJsonRoute(app, connectorsStoragePutRoute, deps, adapter);
461
+ mountJsonRoute(app, connectorsStorageGetRoute, deps, adapter);
462
+ mountJsonRoute(app, connectorsStorageDeleteRoute, deps, adapter);
463
+ mountJsonRoute(app, connectorsStorageListRoute, deps, adapter);
464
+ mountJsonRoute(app, connectorsPaymentsChargeRoute, deps, adapter);
465
+ mountJsonRoute(app, connectorsPaymentsGetRoute, deps, adapter);
466
+ mountJsonRoute(app, connectorsPaymentsRefundRoute, deps, adapter);
467
+ mountJsonRoute(app, connectorsDbInsertRoute, deps, adapter);
468
+ mountJsonRoute(app, connectorsDbGetRoute, deps, adapter);
469
+ mountJsonRoute(app, connectorsDbUpdateRoute, deps, adapter);
470
+ mountJsonRoute(app, connectorsDbDeleteRoute, deps, adapter);
471
+ mountJsonRoute(app, connectorsDbQueryRoute, deps, adapter);
472
+ mountJsonRoute(app, connectorsRealtimePublishRoute, deps, adapter);
473
+ }
474
+ //# sourceMappingURL=connectors.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"connectors.js","sourceRoot":"","sources":["../src/connectors.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,72 @@
1
+ /**
2
+ * @module daemon-status
3
+ *
4
+ * Generic daemon status + shutdown routes, ported from an origin daemon's
5
+ * status/shutdown route pair — see `source-map.md`'s routes-classification
6
+ * table for the full origin file's MIXED verdict and exact provenance. Only
7
+ * the product-neutral half of that file is here: the origin's plugin-count
8
+ * field, a product-specific config-dir path, and a sandbox-mode flag were all
9
+ * dropped rather than carried over, since none of those concepts exist in the
10
+ * engine kernel. Everything a caller needs is injected via `DaemonStatusDeps`
11
+ * rather than read from globals, so this module has no dependency on any
12
+ * particular process/runtime wiring.
13
+ */
14
+ import type { Express } from 'express';
15
+ import { type AdapterContext } from './adapter.js';
16
+ /**
17
+ * Everything the two routes below need, supplied by the caller. `requestShutdown`
18
+ * is a callback rather than this module calling `process.emit('SIGTERM')`
19
+ * directly, because whether that actually terminates the process depends on a
20
+ * listener the caller (not this package) is responsible for registering — see
21
+ * the origin file's own comment on this being a best-effort signal, not a
22
+ * guaranteed one.
23
+ */
24
+ export interface DaemonStatusDeps {
25
+ /** Resolves the running daemon's version string. May be sync or async. */
26
+ getVersion: () => Promise<string> | string;
27
+ /** The host the daemon is bound to, echoed back verbatim. */
28
+ host: string;
29
+ /** Returns the daemon's resolved listen port. */
30
+ getPort: () => number;
31
+ /** The daemon's data directory, echoed back verbatim. */
32
+ dataDir: string;
33
+ /** Returns whether a shutdown has already been requested. */
34
+ isShuttingDown: () => boolean;
35
+ /** Invoked (after the response is sent) when a shutdown is requested. */
36
+ requestShutdown: () => void;
37
+ }
38
+ export interface DaemonStatusResponse {
39
+ ok: true;
40
+ version: string;
41
+ host: string;
42
+ port: number;
43
+ dataDir: string;
44
+ shuttingDown: boolean;
45
+ pid: number;
46
+ }
47
+ export interface DaemonShutdownResponse {
48
+ ok: true;
49
+ scheduled: true;
50
+ }
51
+ /**
52
+ * `GET /api/daemon/status` — an operator-detail endpoint callers can poll to read the daemon's
53
+ * version/host/port/data-dir/shutdown state. **Not the liveness/readiness contract** — this route
54
+ * has no dedicated always-open exemption in `api-security-middleware.ts`'s `OPEN_PROBE_PATHS` the
55
+ * way `health.ts`'s six routes do, and was never *documented* as one even though nothing here
56
+ * technically gated it same-origin either. A monitoring probe should poll `GET /health`/`GET
57
+ * /ready` (`health.ts`) instead — those are purpose-built for that job (plain liveness vs. a real,
58
+ * injectable readiness check) and are guaranteed reachable without a bearer token or an `Origin`
59
+ * header. This route is still useful for a human/CLI wanting the richer operator detail below.
60
+ */
61
+ export declare const daemonStatusRoute: import("./types.js").JsonRouteSpec<void, DaemonStatusResponse, DaemonStatusDeps>;
62
+ /**
63
+ * `POST /api/daemon/shutdown` — schedules a graceful shutdown. Responds
64
+ * immediately (matching the origin's behavior) and defers the actual
65
+ * `requestShutdown()` call via `setImmediate` so the response has already been
66
+ * written before whatever the caller's shutdown callback does takes effect.
67
+ * Gated same-origin: this is a control-plane action, not a public read.
68
+ */
69
+ export declare const daemonShutdownRoute: import("./types.js").JsonRouteSpec<void, DaemonShutdownResponse, DaemonStatusDeps>;
70
+ /** Mounts both daemon-status routes on `app`. A pack's `http(app, services)` calls this directly. */
71
+ export declare function registerDaemonStatusRoutes(app: Express, deps: DaemonStatusDeps, adapter: AdapterContext): void;
72
+ //# sourceMappingURL=daemon-status.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"daemon-status.d.ts","sourceRoot":"","sources":["../src/daemon-status.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AACH,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC;AACvC,OAAO,EAAmC,KAAK,cAAc,EAAE,MAAM,cAAc,CAAC;AAGpF;;;;;;;GAOG;AACH,MAAM,WAAW,gBAAgB;IAC/B,0EAA0E;IAC1E,UAAU,EAAE,MAAM,OAAO,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC;IAC3C,6DAA6D;IAC7D,IAAI,EAAE,MAAM,CAAC;IACb,iDAAiD;IACjD,OAAO,EAAE,MAAM,MAAM,CAAC;IACtB,yDAAyD;IACzD,OAAO,EAAE,MAAM,CAAC;IAChB,6DAA6D;IAC7D,cAAc,EAAE,MAAM,OAAO,CAAC;IAC9B,yEAAyE;IACzE,eAAe,EAAE,MAAM,IAAI,CAAC;CAC7B;AAED,MAAM,WAAW,oBAAoB;IACnC,EAAE,EAAE,IAAI,CAAC;IACT,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;IAChB,YAAY,EAAE,OAAO,CAAC;IACtB,GAAG,EAAE,MAAM,CAAC;CACb;AAED,MAAM,WAAW,sBAAsB;IACrC,EAAE,EAAE,IAAI,CAAC;IACT,SAAS,EAAE,IAAI,CAAC;CACjB;AAED;;;;;;;;;GASG;AACH,eAAO,MAAM,iBAAiB,kFAgB5B,CAAC;AAEH;;;;;;GAMG;AACH,eAAO,MAAM,mBAAmB,oFAgB9B,CAAC;AAEH,qGAAqG;AACrG,wBAAgB,0BAA0B,CACxC,GAAG,EAAE,OAAO,EACZ,IAAI,EAAE,gBAAgB,EACtB,OAAO,EAAE,cAAc,GACtB,IAAI,CAGN"}
@@ -0,0 +1,60 @@
1
+ import { defineJsonRoute, mountJsonRoute } from './adapter.js';
2
+ import { ok } from './types.js';
3
+ /**
4
+ * `GET /api/daemon/status` — an operator-detail endpoint callers can poll to read the daemon's
5
+ * version/host/port/data-dir/shutdown state. **Not the liveness/readiness contract** — this route
6
+ * has no dedicated always-open exemption in `api-security-middleware.ts`'s `OPEN_PROBE_PATHS` the
7
+ * way `health.ts`'s six routes do, and was never *documented* as one even though nothing here
8
+ * technically gated it same-origin either. A monitoring probe should poll `GET /health`/`GET
9
+ * /ready` (`health.ts`) instead — those are purpose-built for that job (plain liveness vs. a real,
10
+ * injectable readiness check) and are guaranteed reachable without a bearer token or an `Origin`
11
+ * header. This route is still useful for a human/CLI wanting the richer operator detail below.
12
+ */
13
+ export const daemonStatusRoute = defineJsonRoute({
14
+ method: 'get',
15
+ path: '/api/daemon/status',
16
+ parse: () => ok(undefined),
17
+ handle: async (_input, deps) => {
18
+ const version = await deps.getVersion();
19
+ return ok({
20
+ ok: true,
21
+ version,
22
+ host: deps.host,
23
+ port: deps.getPort(),
24
+ dataDir: deps.dataDir,
25
+ shuttingDown: deps.isShuttingDown(),
26
+ pid: process.pid,
27
+ });
28
+ },
29
+ });
30
+ /**
31
+ * `POST /api/daemon/shutdown` — schedules a graceful shutdown. Responds
32
+ * immediately (matching the origin's behavior) and defers the actual
33
+ * `requestShutdown()` call via `setImmediate` so the response has already been
34
+ * written before whatever the caller's shutdown callback does takes effect.
35
+ * Gated same-origin: this is a control-plane action, not a public read.
36
+ */
37
+ export const daemonShutdownRoute = defineJsonRoute({
38
+ method: 'post',
39
+ path: '/api/daemon/shutdown',
40
+ requireSameOrigin: true,
41
+ parse: () => ok(undefined),
42
+ handle: (_input, deps) => {
43
+ setImmediate(() => {
44
+ try {
45
+ deps.requestShutdown();
46
+ }
47
+ catch {
48
+ // Best-effort: if the caller's shutdown wiring is already gone, there's
49
+ // nothing left for this route to do about it.
50
+ }
51
+ });
52
+ return ok({ ok: true, scheduled: true });
53
+ },
54
+ });
55
+ /** Mounts both daemon-status routes on `app`. A pack's `http(app, services)` calls this directly. */
56
+ export function registerDaemonStatusRoutes(app, deps, adapter) {
57
+ mountJsonRoute(app, daemonStatusRoute, deps, adapter);
58
+ mountJsonRoute(app, daemonShutdownRoute, deps, adapter);
59
+ }
60
+ //# sourceMappingURL=daemon-status.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"daemon-status.js","sourceRoot":"","sources":["../src/daemon-status.ts"],"names":[],"mappings":"AAcA,OAAO,EAAE,eAAe,EAAE,cAAc,EAAuB,MAAM,cAAc,CAAC;AACpF,OAAO,EAAE,EAAE,EAAE,MAAM,YAAY,CAAC;AAwChC;;;;;;;;;GASG;AACH,MAAM,CAAC,MAAM,iBAAiB,GAAG,eAAe,CAA+C;IAC7F,MAAM,EAAE,KAAK;IACb,IAAI,EAAE,oBAAoB;IAC1B,KAAK,EAAE,GAAG,EAAE,CAAC,EAAE,CAAC,SAAS,CAAC;IAC1B,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,IAAI,EAAE,EAAE;QAC7B,MAAM,OAAO,GAAG,MAAM,IAAI,CAAC,UAAU,EAAE,CAAC;QACxC,OAAO,EAAE,CAAC;YACR,EAAE,EAAE,IAAI;YACR,OAAO;YACP,IAAI,EAAE,IAAI,CAAC,IAAI;YACf,IAAI,EAAE,IAAI,CAAC,OAAO,EAAE;YACpB,OAAO,EAAE,IAAI,CAAC,OAAO;YACrB,YAAY,EAAE,IAAI,CAAC,cAAc,EAAE;YACnC,GAAG,EAAE,OAAO,CAAC,GAAG;SACjB,CAAC,CAAC;IACL,CAAC;CACF,CAAC,CAAC;AAEH;;;;;;GAMG;AACH,MAAM,CAAC,MAAM,mBAAmB,GAAG,eAAe,CAAiD;IACjG,MAAM,EAAE,MAAM;IACd,IAAI,EAAE,sBAAsB;IAC5B,iBAAiB,EAAE,IAAI;IACvB,KAAK,EAAE,GAAG,EAAE,CAAC,EAAE,CAAC,SAAS,CAAC;IAC1B,MAAM,EAAE,CAAC,MAAM,EAAE,IAAI,EAAE,EAAE;QACvB,YAAY,CAAC,GAAG,EAAE;YAChB,IAAI,CAAC;gBACH,IAAI,CAAC,eAAe,EAAE,CAAC;YACzB,CAAC;YAAC,MAAM,CAAC;gBACP,wEAAwE;gBACxE,8CAA8C;YAChD,CAAC;QACH,CAAC,CAAC,CAAC;QACH,OAAO,EAAE,CAAC,EAAE,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC3C,CAAC;CACF,CAAC,CAAC;AAEH,qGAAqG;AACrG,MAAM,UAAU,0BAA0B,CACxC,GAAY,EACZ,IAAsB,EACtB,OAAuB;IAEvB,cAAc,CAAC,GAAG,EAAE,iBAAiB,EAAE,IAAI,EAAE,OAAO,CAAC,CAAC;IACtD,cAAc,CAAC,GAAG,EAAE,mBAAmB,EAAE,IAAI,EAAE,OAAO,CAAC,CAAC;AAC1D,CAAC"}