@almadar/sdk 0.2.5 → 0.3.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.
@@ -2,6 +2,48 @@ import { parseOrbitalSchema } from '@almadar/core';
2
2
 
3
3
  // src/client/AlmadarClient.ts
4
4
 
5
+ // src/types.ts
6
+ function isGenerateMetaOrganism(value) {
7
+ if (value === null || typeof value !== "object") return false;
8
+ const v = value;
9
+ if (typeof v.name !== "string") return false;
10
+ return v.source === "factory" || v.source === "free-lolo";
11
+ }
12
+ function isGenerateMetaCacheVerdict(value) {
13
+ if (value === null) return true;
14
+ if (typeof value !== "object") return false;
15
+ const v = value;
16
+ if (v.verdict !== "hit" && v.verdict !== "miss") return false;
17
+ return v.chosen === null || typeof v.chosen === "string";
18
+ }
19
+ function isGenerateMeta(value) {
20
+ if (value === null || typeof value !== "object") return false;
21
+ const v = value;
22
+ if (v.tier !== "confirmed" && v.tier !== "hit" && v.tier !== "miss") return false;
23
+ if (!Array.isArray(v.organisms) || !v.organisms.every(isGenerateMetaOrganism)) return false;
24
+ if (!Array.isArray(v.demoted) || !v.demoted.every((d) => typeof d === "string")) return false;
25
+ if (!isGenerateMetaCacheVerdict(v.cacheVerdict)) return false;
26
+ return typeof v.durationMs === "number";
27
+ }
28
+ var API_ERROR_CODES = {
29
+ API_KEY: 4001,
30
+ RATE_LIMITED: 4029,
31
+ CATALOG_OUT_OF_SCOPE: 4040,
32
+ PIN_UNKNOWN_ORGANISM: 4041,
33
+ PIN_OUT_OF_SCOPE: 4042,
34
+ PIN_CONFLICT: 4043,
35
+ PIN_UNKNOWN_KNOB: 4044,
36
+ PIN_ORBITAL_REQUIRED: 4045,
37
+ ASYNC_UNSUPPORTED: 4060,
38
+ FOCUS_STALE: 4090,
39
+ SERVER: 5e3,
40
+ GENERATION_FAILED: 5001,
41
+ RUNTIME: 5002,
42
+ WORKSPACE_OPEN: 5003,
43
+ AI_UNCONFIGURED: 5030
44
+ };
45
+ var STREAM_ERROR_CODES = ["failed", "runtime", "workspace_open", "ai_unconfigured", "focus_stale"];
46
+
5
47
  // src/client/errors.ts
6
48
  var AlmadarError = class extends Error {
7
49
  code;
@@ -39,18 +81,68 @@ var ServerError = class extends AlmadarError {
39
81
  this.name = "ServerError";
40
82
  }
41
83
  };
84
+ var PinError = class extends AlmadarError {
85
+ constructor(body) {
86
+ super(body);
87
+ this.name = "PinError";
88
+ }
89
+ };
90
+ var AsyncUnsupportedError = class extends AlmadarError {
91
+ constructor(body) {
92
+ super(body);
93
+ this.name = "AsyncUnsupportedError";
94
+ }
95
+ };
96
+ var GenerationFailedError = class extends AlmadarError {
97
+ constructor(body) {
98
+ super(body);
99
+ this.name = "GenerationFailedError";
100
+ }
101
+ };
42
102
  function errorFromBody(body) {
43
103
  switch (body.code) {
44
- case 4001:
104
+ case API_ERROR_CODES.API_KEY:
45
105
  return new ApiKeyError(body);
46
- case 4029:
106
+ case API_ERROR_CODES.RATE_LIMITED:
47
107
  return new RateLimitedError(body);
48
- case 4040:
108
+ case API_ERROR_CODES.CATALOG_OUT_OF_SCOPE:
49
109
  return new CatalogOutOfScopeError(body);
110
+ case API_ERROR_CODES.PIN_UNKNOWN_ORGANISM:
111
+ case API_ERROR_CODES.PIN_OUT_OF_SCOPE:
112
+ case API_ERROR_CODES.PIN_CONFLICT:
113
+ case API_ERROR_CODES.PIN_UNKNOWN_KNOB:
114
+ case API_ERROR_CODES.PIN_ORBITAL_REQUIRED:
115
+ return new PinError(body);
116
+ case API_ERROR_CODES.ASYNC_UNSUPPORTED:
117
+ return new AsyncUnsupportedError(body);
118
+ case API_ERROR_CODES.GENERATION_FAILED:
119
+ return new GenerationFailedError(body);
50
120
  default:
51
121
  return new ServerError(body);
52
122
  }
53
123
  }
124
+ function isStreamErrorCode(code) {
125
+ if (code === void 0) return false;
126
+ return STREAM_ERROR_CODES.some((c) => c === code);
127
+ }
128
+ function streamErrorFromEvent(data) {
129
+ const message = data.error;
130
+ if (!isStreamErrorCode(data.code)) {
131
+ return new ServerError({ code: API_ERROR_CODES.SERVER, message });
132
+ }
133
+ switch (data.code) {
134
+ case "failed":
135
+ return new GenerationFailedError({ code: API_ERROR_CODES.GENERATION_FAILED, message });
136
+ case "ai_unconfigured":
137
+ return new ServerError({ code: API_ERROR_CODES.AI_UNCONFIGURED, message });
138
+ case "workspace_open":
139
+ return new ServerError({ code: API_ERROR_CODES.WORKSPACE_OPEN, message });
140
+ case "focus_stale":
141
+ return new ServerError({ code: API_ERROR_CODES.FOCUS_STALE, message });
142
+ case "runtime":
143
+ return new ServerError({ code: API_ERROR_CODES.RUNTIME, message });
144
+ }
145
+ }
54
146
 
55
147
  // src/client/sseParser.ts
56
148
  async function* parseSSE(stream) {
@@ -106,7 +198,6 @@ function indexOfNewline(s) {
106
198
 
107
199
  // src/client/AlmadarClient.ts
108
200
  var DEFAULT_BASE_URL = "https://studio.almadar.io";
109
- var POLL_BACKOFF_MS = [1e3, 2e3, 5e3, 1e4, 3e4];
110
201
  var AlmadarClient = class {
111
202
  apiKey;
112
203
  baseUrl;
@@ -124,19 +215,10 @@ var AlmadarClient = class {
124
215
  }
125
216
  async generate(input) {
126
217
  if (input.async === true) {
127
- const handle = await this.requestJson("POST", "/api/v1/agent/generate", {
128
- prompt: input.prompt,
129
- endUserId: input.endUserId,
130
- appId: input.appId,
131
- async: true,
132
- provider: input.provider,
133
- model: input.model,
134
- catalogMode: input.catalogMode,
135
- stdAllowList: input.stdAllowList
218
+ throw new AsyncUnsupportedError({
219
+ code: API_ERROR_CODES.ASYNC_UNSUPPORTED,
220
+ message: "AlmadarClient has no async job surface. Omit `async` (or pass false) and consume the streaming response via `onEvent` instead."
136
221
  });
137
- assertString(handle.jobId, "AsyncJobHandle.jobId");
138
- assertString(handle.statusUrl, "AsyncJobHandle.statusUrl");
139
- return this.pollUntilComplete(handle, input.onEvent);
140
222
  }
141
223
  return this.streamGenerate(input);
142
224
  }
@@ -170,56 +252,35 @@ var AlmadarClient = class {
170
252
  provider: input.provider,
171
253
  model: input.model,
172
254
  catalogMode: input.catalogMode,
173
- stdAllowList: input.stdAllowList
255
+ stdAllowList: input.stdAllowList,
256
+ pin: input.pin
174
257
  })
175
258
  });
176
259
  if (!res.ok) throw await this.errorFromResponse(res);
177
260
  if (res.body === null) throw new Error("AlmadarClient.generate: server returned no body");
178
261
  let final = null;
262
+ let meta;
179
263
  for await (const raw of parseSSE(res.body)) {
180
264
  const event = parseSseEvent(raw.data);
181
265
  if (event === null) continue;
182
266
  input.onEvent?.(event);
183
- if (event.type === "complete") {
267
+ if (event.type === "generation_meta") {
268
+ meta = event.data;
269
+ } else if (event.type === "complete") {
184
270
  if (event.data.schema === void 0) {
185
- throw new ServerError({ code: 500, message: "`complete` event did not contain a schema" });
271
+ throw new ServerError({ code: API_ERROR_CODES.SERVER, message: "`complete` event did not contain a schema" });
186
272
  }
187
273
  const schema = parseOrbitalSchema(event.data.schema);
188
- final = { schema, appId: event.data.appId };
274
+ final = { schema, appId: event.data.appId, meta };
189
275
  } else if (event.type === "error") {
190
- throw errorFromBody({ code: 500, message: event.data.error });
276
+ throw streamErrorFromEvent(event.data);
191
277
  }
192
278
  }
193
279
  if (final === null) {
194
- throw new ServerError({ code: 500, message: "SSE stream ended without `complete` event" });
280
+ throw new ServerError({ code: API_ERROR_CODES.SERVER, message: "SSE stream ended without `complete` event" });
195
281
  }
196
282
  return final;
197
283
  }
198
- async pollUntilComplete(handle, onEvent) {
199
- let attempt = 0;
200
- for (; ; ) {
201
- const delay = POLL_BACKOFF_MS[Math.min(attempt, POLL_BACKOFF_MS.length - 1)];
202
- await sleep(delay);
203
- attempt += 1;
204
- const status = await this.requestJson("GET", handle.statusUrl);
205
- assertString(status.state, "JobStatus.state");
206
- if (status.events !== void 0 && onEvent !== void 0) {
207
- for (const e of status.events) onEvent(e);
208
- }
209
- if (status.state === "complete") {
210
- if (status.result === void 0) {
211
- throw new ServerError({ code: 500, message: "Job complete but no result returned" });
212
- }
213
- return status.result;
214
- }
215
- if (status.state === "error") {
216
- throw errorFromBody({
217
- code: status.errorCode ?? 500,
218
- message: status.errorMessage ?? "Job failed"
219
- });
220
- }
221
- }
222
- }
223
284
  async requestJson(method, path, body) {
224
285
  const isAbsolute = path.startsWith("http://") || path.startsWith("https://");
225
286
  const url = isAbsolute ? path : `${this.baseUrl}${path}`;
@@ -235,7 +296,7 @@ var AlmadarClient = class {
235
296
  if (!res.ok) throw await this.errorFromResponse(res);
236
297
  const text = await res.text();
237
298
  if (text === "") {
238
- throw new ServerError({ code: 500, message: "Empty response body" });
299
+ throw new ServerError({ code: API_ERROR_CODES.SERVER, message: "Empty response body" });
239
300
  }
240
301
  const parsed = JSON.parse(text);
241
302
  return parsed;
@@ -280,16 +341,16 @@ function parseSseEvent(dataLine) {
280
341
  }
281
342
  if (payload === null || typeof payload !== "object" || Array.isArray(payload)) return null;
282
343
  if (typeof payload.type !== "string" || typeof payload.timestamp !== "number") return null;
344
+ if (payload.type === "generation_meta") {
345
+ return isGenerateMeta(payload.data) ? { type: "generation_meta", data: payload.data, timestamp: payload.timestamp } : null;
346
+ }
283
347
  return payload;
284
348
  }
285
349
  function assertString(v, name) {
286
350
  if (typeof v !== "string" || v === "") {
287
- throw new ServerError({ code: 500, message: `Malformed server response: ${name} is not a string` });
351
+ throw new ServerError({ code: API_ERROR_CODES.SERVER, message: `Malformed server response: ${name} is not a string` });
288
352
  }
289
353
  }
290
- function sleep(ms) {
291
- return new Promise((resolve) => setTimeout(resolve, ms));
292
- }
293
354
 
294
355
  // src/server/index.ts
295
356
  function resolveEndUserId(opts, req) {
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/client/errors.ts","../../src/client/sseParser.ts","../../src/client/AlmadarClient.ts","../../src/server/index.ts","../../src/server/express.ts"],"names":["createGenerateHandler","createEditHandler"],"mappings":"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","file":"express.js","sourcesContent":["/**\n * Typed SDK errors. Server emits a structured `ApiErrorBody`; the HTTP layer\n * maps the `code` to one of these subclasses. Customers `catch` by class.\n */\n\nimport type { ApiErrorBody } from '../types';\n\nexport class AlmadarError extends Error {\n readonly code: number;\n readonly details?: ApiErrorBody['details'];\n constructor(body: ApiErrorBody) {\n super(body.message);\n this.name = 'AlmadarError';\n this.code = body.code;\n this.details = body.details;\n }\n}\n\n/** 4001 — invalid, revoked, or missing API key. */\nexport class ApiKeyError extends AlmadarError {\n constructor(body: ApiErrorBody) {\n super(body);\n this.name = 'ApiKeyError';\n }\n}\n\n/** 4029 — team cap (feature counter) exceeded. Retry after a billing cycle. */\nexport class RateLimitedError extends AlmadarError {\n readonly retryAfterSeconds?: number;\n constructor(body: ApiErrorBody, retryAfterSeconds?: number) {\n super(body);\n this.name = 'RateLimitedError';\n this.retryAfterSeconds = retryAfterSeconds;\n }\n}\n\n/** 4040 — the team's behavior catalog (subset/replace mode) cannot serve the request. */\nexport class CatalogOutOfScopeError extends AlmadarError {\n constructor(body: ApiErrorBody) {\n super(body);\n this.name = 'CatalogOutOfScopeError';\n }\n}\n\n/** Anything else from the server with a recognized envelope but no specific subclass. */\nexport class ServerError extends AlmadarError {\n constructor(body: ApiErrorBody) {\n super(body);\n this.name = 'ServerError';\n }\n}\n\nexport function errorFromBody(body: ApiErrorBody): AlmadarError {\n switch (body.code) {\n case 4001:\n return new ApiKeyError(body);\n case 4029:\n return new RateLimitedError(body);\n case 4040:\n return new CatalogOutOfScopeError(body);\n default:\n return new ServerError(body);\n }\n}\n","/**\n * Minimal Server-Sent Events parser. Reads a `ReadableStream<Uint8Array>`\n * (the body of a `fetch` Response) and yields decoded events. Universal:\n * works in browser, Node 18+, Deno, Bun.\n *\n * Spec subset implemented:\n * - `event:` and `data:` fields\n * - dispatch on blank line\n * - newline-tolerant (CRLF + LF)\n * - skips comments (`:`-prefixed lines)\n *\n * Not implemented (we don't need them):\n * - `id:` / `retry:` fields\n * - reconnection / last-event-id\n */\n\nexport interface RawSseEvent {\n /** `event:` field value. Empty string when absent — matches the spec default. */\n event: string;\n /** Concatenated `data:` lines, joined by newlines. */\n data: string;\n}\n\nexport async function* parseSSE(\n stream: ReadableStream<Uint8Array>,\n): AsyncGenerator<RawSseEvent, void, void> {\n const reader = stream.getReader();\n const decoder = new TextDecoder('utf-8');\n let buffer = '';\n let currentEvent = '';\n let currentData = '';\n\n try {\n for (;;) {\n const { value, done } = await reader.read();\n if (done) break;\n buffer += decoder.decode(value, { stream: true });\n\n let newlineIdx: number;\n while ((newlineIdx = indexOfNewline(buffer)) !== -1) {\n const rawLine = buffer.slice(0, newlineIdx);\n buffer = buffer.slice(newlineIdx + (buffer[newlineIdx] === '\\r' && buffer[newlineIdx + 1] === '\\n' ? 2 : 1));\n\n if (rawLine === '') {\n if (currentData !== '' || currentEvent !== '') {\n yield { event: currentEvent, data: currentData };\n currentEvent = '';\n currentData = '';\n }\n continue;\n }\n if (rawLine.startsWith(':')) continue;\n\n const colon = rawLine.indexOf(':');\n const field = colon === -1 ? rawLine : rawLine.slice(0, colon);\n const rawValue = colon === -1 ? '' : rawLine.slice(colon + 1);\n const value2 = rawValue.startsWith(' ') ? rawValue.slice(1) : rawValue;\n\n if (field === 'event') {\n currentEvent = value2;\n } else if (field === 'data') {\n currentData = currentData === '' ? value2 : `${currentData}\\n${value2}`;\n }\n }\n }\n if (currentData !== '' || currentEvent !== '') {\n yield { event: currentEvent, data: currentData };\n }\n } finally {\n reader.releaseLock();\n }\n}\n\nfunction indexOfNewline(s: string): number {\n for (let i = 0; i < s.length; i += 1) {\n const c = s[i];\n if (c === '\\n' || c === '\\r') return i;\n }\n return -1;\n}\n","/**\n * `AlmadarClient` — server / Node-side HTTP client targeting `/api/v1/agent/*`.\n * Authenticates with a team-bound API key (`sk_*`) issued from\n * Studio's `/settings/sdk` panel. See `docs/Almadar_Studio_SDK.md` §5.\n *\n * Never instantiate this in a browser bundle — `apiKey` must never leave\n * the customer's server.\n */\n\nimport { parseOrbitalSchema, type OrbitalSchema, type SSEEvent } from '@almadar/core';\nimport type {\n AlmadarClientOptions,\n ApiErrorBody,\n AsyncJobHandle,\n CompileOptions,\n CompileResult,\n EditSchemaPatch,\n GenerateOptions,\n GenerateResult,\n} from '../types';\nimport { errorFromBody, ServerError } from './errors';\nimport { parseSSE } from './sseParser';\n\nconst DEFAULT_BASE_URL = 'https://studio.almadar.io';\nconst POLL_BACKOFF_MS: readonly number[] = [1000, 2000, 5000, 10_000, 30_000];\n\ninterface JobStatus {\n state: 'pending' | 'complete' | 'error';\n events?: readonly SSEEvent[];\n result?: GenerateResult;\n errorCode?: number;\n errorMessage?: string;\n}\n\nexport class AlmadarClient {\n private readonly apiKey: string;\n private readonly baseUrl: string;\n private readonly fetchImpl: typeof fetch;\n\n constructor(opts: AlmadarClientOptions) {\n if (!opts.apiKey || typeof opts.apiKey !== 'string') {\n throw new Error('AlmadarClient: opts.apiKey is required');\n }\n this.apiKey = opts.apiKey;\n this.baseUrl = (opts.baseUrl ?? DEFAULT_BASE_URL).replace(/\\/$/, '');\n this.fetchImpl = opts.fetch ?? globalThis.fetch;\n if (typeof this.fetchImpl !== 'function') {\n throw new Error('AlmadarClient: no fetch available — pass opts.fetch for Node <18');\n }\n }\n\n async generate(input: GenerateOptions): Promise<GenerateResult> {\n if (input.async === true) {\n const handle = await this.requestJson<AsyncJobHandle>('POST', '/api/v1/agent/generate', {\n prompt: input.prompt,\n endUserId: input.endUserId,\n appId: input.appId,\n async: true,\n provider: input.provider,\n model: input.model,\n catalogMode: input.catalogMode,\n stdAllowList: input.stdAllowList,\n });\n assertString(handle.jobId, 'AsyncJobHandle.jobId');\n assertString(handle.statusUrl, 'AsyncJobHandle.statusUrl');\n return this.pollUntilComplete(handle, input.onEvent);\n }\n return this.streamGenerate(input);\n }\n\n async editSchema(appId: string, patch: EditSchemaPatch): Promise<OrbitalSchema> {\n if (!appId) throw new Error('AlmadarClient.editSchema: appId is required');\n const schema = await this.requestJson<OrbitalSchema>('PUT', '/api/v1/agent/edit-schema', {\n appId,\n patch,\n });\n assertString(schema.name, 'OrbitalSchema.name');\n return schema;\n }\n\n async compileToApp(schema: OrbitalSchema, opts?: CompileOptions): Promise<CompileResult> {\n const result = await this.requestJson<CompileResult>('POST', '/api/v1/agent/compile', {\n schema,\n target: opts?.target,\n shell: opts?.shell,\n });\n assertString(result.downloadUrl, 'CompileResult.downloadUrl');\n assertString(result.expiresAt, 'CompileResult.expiresAt');\n return result;\n }\n\n private async streamGenerate(input: GenerateOptions): Promise<GenerateResult> {\n const res = await this.fetchImpl(`${this.baseUrl}/api/v1/agent/generate`, {\n method: 'POST',\n headers: this.headers({ accept: 'text/event-stream', contentType: 'application/json' }, input.endUserId),\n body: JSON.stringify({\n prompt: input.prompt,\n endUserId: input.endUserId,\n appId: input.appId,\n provider: input.provider,\n model: input.model,\n catalogMode: input.catalogMode,\n stdAllowList: input.stdAllowList,\n }),\n });\n if (!res.ok) throw await this.errorFromResponse(res);\n if (res.body === null) throw new Error('AlmadarClient.generate: server returned no body');\n\n let final: GenerateResult | null = null;\n for await (const raw of parseSSE(res.body)) {\n const event = parseSseEvent(raw.data);\n if (event === null) continue;\n input.onEvent?.(event);\n if (event.type === 'complete') {\n if (event.data.schema === undefined) {\n throw new ServerError({ code: 500, message: '`complete` event did not contain a schema' });\n }\n const schema = parseOrbitalSchema(event.data.schema);\n final = { schema, appId: event.data.appId };\n } else if (event.type === 'error') {\n throw errorFromBody({ code: 500, message: event.data.error });\n }\n }\n if (final === null) {\n throw new ServerError({ code: 500, message: 'SSE stream ended without `complete` event' });\n }\n return final;\n }\n\n private async pollUntilComplete(\n handle: AsyncJobHandle,\n onEvent: GenerateOptions['onEvent'],\n ): Promise<GenerateResult> {\n let attempt = 0;\n for (;;) {\n const delay = POLL_BACKOFF_MS[Math.min(attempt, POLL_BACKOFF_MS.length - 1)];\n await sleep(delay);\n attempt += 1;\n const status = await this.requestJson<JobStatus>('GET', handle.statusUrl);\n assertString(status.state, 'JobStatus.state');\n if (status.events !== undefined && onEvent !== undefined) {\n for (const e of status.events) onEvent(e);\n }\n if (status.state === 'complete') {\n if (status.result === undefined) {\n throw new ServerError({ code: 500, message: 'Job complete but no result returned' });\n }\n return status.result;\n }\n if (status.state === 'error') {\n throw errorFromBody({\n code: status.errorCode ?? 500,\n message: status.errorMessage ?? 'Job failed',\n });\n }\n }\n }\n\n private async requestJson<T>(method: string, path: string, body?: object): Promise<T> {\n const isAbsolute = path.startsWith('http://') || path.startsWith('https://');\n const url = isAbsolute ? path : `${this.baseUrl}${path}`;\n const init: RequestInit = {\n method,\n headers: this.headers({\n accept: 'application/json',\n contentType: body !== undefined ? 'application/json' : undefined,\n }),\n };\n if (body !== undefined) init.body = JSON.stringify(body);\n const res = await this.fetchImpl(url, init);\n if (!res.ok) throw await this.errorFromResponse(res);\n const text = await res.text();\n if (text === '') {\n throw new ServerError({ code: 500, message: 'Empty response body' });\n }\n const parsed: T = JSON.parse(text);\n return parsed;\n }\n\n private headers(\n opts: { accept?: string; contentType?: string },\n endUserId?: string,\n ): Record<string, string> {\n const h: Record<string, string> = { authorization: `Bearer ${this.apiKey}` };\n if (opts.accept !== undefined) h['accept'] = opts.accept;\n if (opts.contentType !== undefined) h['content-type'] = opts.contentType;\n if (endUserId !== undefined && endUserId !== '') h['x-end-user-id'] = endUserId;\n return h;\n }\n\n private async errorFromResponse(res: Response): Promise<Error> {\n const text = await res.text();\n let body: ApiErrorBody;\n try {\n const parsed: ApiErrorBody | null = text === '' ? null : JSON.parse(text);\n body = parsed !== null && typeof parsed.code === 'number' && typeof parsed.message === 'string'\n ? parsed\n : {\n code: res.status,\n message: res.statusText !== '' ? res.statusText : 'HTTP error',\n };\n } catch {\n body = { code: res.status, message: text !== '' ? text : res.statusText };\n }\n const retryAfter = res.headers.get('retry-after');\n const err = errorFromBody(body);\n if (err.name === 'RateLimitedError' && retryAfter !== null) {\n const seconds = Number(retryAfter);\n if (Number.isFinite(seconds)) {\n Object.defineProperty(err, 'retryAfterSeconds', { value: seconds, enumerable: true });\n }\n }\n return err;\n }\n}\n\n/**\n * Parse one SSE `data:` line into the canonical `SSEEvent` union.\n * The server is the trusted emitter, so we validate only the envelope\n * (object with string `type` and numeric `timestamp`) and cast to the\n * discriminated union. Malformed lines are ignored.\n */\nfunction parseSseEvent(dataLine: string): SSEEvent | null {\n if (dataLine === '') return null;\n let payload;\n try {\n payload = JSON.parse(dataLine);\n } catch {\n return null;\n }\n if (payload === null || typeof payload !== 'object' || Array.isArray(payload)) return null;\n if (typeof payload.type !== 'string' || typeof payload.timestamp !== 'number') return null;\n return payload as SSEEvent;\n}\n\nfunction assertString(v: string | undefined, name: string): asserts v is string {\n if (typeof v !== 'string' || v === '') {\n throw new ServerError({ code: 500, message: `Malformed server response: ${name} is not a string` });\n }\n}\n\nfunction sleep(ms: number): Promise<void> {\n return new Promise((resolve) => setTimeout(resolve, ms));\n}\n","/**\n * `@almadar/sdk/server` — Framework-agnostic Web-standard Fetch handlers for\n * the Almadar agent proxy. Node-only; never import from browser or React code.\n *\n * Usage:\n * import { createGenerateHandler, createEditHandler } from '@almadar/sdk/server';\n * const handler = createGenerateHandler({ apiKey: process.env.ALMADAR_API_KEY! });\n * // handler: (request: Request) => Promise<Response>\n *\n * For framework adapters see `@almadar/sdk/server/express` and `@almadar/sdk/server/hono`.\n */\n\nimport type { OrbitalSchema } from '@almadar/core';\nimport { AlmadarClient } from '../client/AlmadarClient';\nimport type { EditSchemaRequest, EditSchemaPatch, GenerateRequest, SSEEvent } from '../types';\n\n// ============================================================================\n// Public option surface\n// ============================================================================\n\nexport interface GenerateHandlerOptions {\n /** API key issued from Studio's /settings/sdk panel. */\n apiKey: string;\n /** Defaults to https://studio.almadar.io. */\n baseUrl?: string;\n /**\n * Derive a stable end-user id from the incoming Web Request.\n * Falls back to the `x-user-id` request header when omitted.\n */\n endUserId?: (req: Request) => string;\n}\n\n// ============================================================================\n// Internal helpers\n// ============================================================================\n\nfunction resolveEndUserId(opts: GenerateHandlerOptions, req: Request): string | undefined {\n if (opts.endUserId) return opts.endUserId(req);\n const header = req.headers.get('x-user-id');\n return typeof header === 'string' && header.length > 0 ? header : undefined;\n}\n\nfunction encodeSseEvent(event: SSEEvent): string {\n return `data: ${JSON.stringify(event)}\\n\\n`;\n}\n\n// ============================================================================\n// createGenerateHandler\n// ============================================================================\n\n/**\n * Returns a Web-standard Fetch handler that streams a generate call as SSE.\n *\n * Body shape accepted: `{ prompt: string; endUserId?: string; appId?: string }`\n */\nexport function createGenerateHandler(\n opts: GenerateHandlerOptions,\n): (request: Request) => Promise<Response> {\n return async (request: Request): Promise<Response> => {\n let body: GenerateRequest;\n try {\n body = (await request.json()) as GenerateRequest;\n } catch {\n return new Response(JSON.stringify({ error: 'invalid JSON body' }), {\n status: 400,\n headers: { 'content-type': 'application/json' },\n });\n }\n\n const rawPrompt = body.prompt ?? body.message;\n const prompt = typeof rawPrompt === 'string' ? rawPrompt : '';\n\n if (!prompt) {\n return new Response(JSON.stringify({ error: 'prompt or message is required' }), {\n status: 400,\n headers: { 'content-type': 'application/json' },\n });\n }\n\n const bodyEndUserId = typeof body.endUserId === 'string' ? body.endUserId : undefined;\n const endUserId = bodyEndUserId ?? resolveEndUserId(opts, request);\n const appId = typeof body.appId === 'string' ? body.appId : undefined;\n\n const client = new AlmadarClient({ apiKey: opts.apiKey, baseUrl: opts.baseUrl });\n\n const stream = new ReadableStream<Uint8Array>({\n async start(controller) {\n const encoder = new TextEncoder();\n try {\n await client.generate({\n prompt,\n endUserId,\n appId,\n onEvent: (event: SSEEvent) => {\n controller.enqueue(encoder.encode(encodeSseEvent(event)));\n },\n });\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err);\n const errorEvent: SSEEvent = {\n type: 'error',\n timestamp: Date.now(),\n data: { error: message },\n };\n controller.enqueue(encoder.encode(encodeSseEvent(errorEvent)));\n } finally {\n controller.close();\n }\n },\n });\n\n return new Response(stream, {\n status: 200,\n headers: {\n 'content-type': 'text/event-stream',\n 'cache-control': 'no-cache',\n connection: 'keep-alive',\n },\n });\n };\n}\n\n// ============================================================================\n// createEditHandler\n// ============================================================================\n\n/**\n * Returns a Web-standard Fetch handler that calls `editSchema` and returns JSON.\n *\n * Body shape accepted: `{ appId: string; patch: EditSchemaPatch }`\n */\nexport function createEditHandler(\n opts: GenerateHandlerOptions,\n): (request: Request) => Promise<Response> {\n return async (request: Request): Promise<Response> => {\n let body: EditSchemaRequest;\n try {\n body = (await request.json()) as EditSchemaRequest;\n } catch {\n return new Response(JSON.stringify({ error: 'invalid JSON body' }), {\n status: 400,\n headers: { 'content-type': 'application/json' },\n });\n }\n\n const appId = typeof body.appId === 'string' ? body.appId : '';\n if (!appId) {\n return new Response(JSON.stringify({ error: 'appId is required' }), {\n status: 400,\n headers: { 'content-type': 'application/json' },\n });\n }\n\n const patch: EditSchemaPatch | undefined = body.patch;\n if (patch === undefined || patch === null || typeof patch !== 'object') {\n return new Response(JSON.stringify({ error: 'patch is required' }), {\n status: 400,\n headers: { 'content-type': 'application/json' },\n });\n }\n\n const client = new AlmadarClient({ apiKey: opts.apiKey, baseUrl: opts.baseUrl });\n\n try {\n const schema: OrbitalSchema = await client.editSchema(appId, patch);\n return new Response(JSON.stringify(schema), {\n status: 200,\n headers: { 'content-type': 'application/json' },\n });\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err);\n return new Response(JSON.stringify({ error: message }), {\n status: 500,\n headers: { 'content-type': 'application/json' },\n });\n }\n };\n}\n","/**\n * `@almadar/sdk/server/express` — Express adapter for the Almadar server handlers.\n *\n * Node-only. The consumer must provide their own `express` installation.\n * This module imports express TYPES only; it is never bundled with express itself.\n *\n * Usage:\n * import { createGenerateHandler, createEditHandler } from '@almadar/sdk/server/express';\n * app.post('/api/agent/generate', createGenerateHandler({ apiKey }));\n * app.put('/api/agent/edit', createEditHandler({ apiKey }));\n */\n\nimport type { Request as ExpressRequest, Response as ExpressResponse, RequestHandler } from 'express';\nimport {\n createGenerateHandler as coreGenerateHandler,\n createEditHandler as coreEditHandler,\n} from './index';\n\n// ============================================================================\n// Express-specific option surface\n// ============================================================================\n\nexport interface GenerateHandlerOptions {\n /** API key issued from Studio's /settings/sdk panel. */\n apiKey: string;\n /** Defaults to https://studio.almadar.io. */\n baseUrl?: string;\n /**\n * Derive a stable end-user id from the Express request.\n * Falls back to the `x-user-id` request header when omitted.\n */\n endUserId?: (req: ExpressRequest) => string;\n}\n\n// ============================================================================\n// Express↔Fetch bridge helpers\n// ============================================================================\n\n/**\n * Convert an Express `Request` to a Web-standard `Request`.\n * Re-serialises the already-parsed body so the core handler's `request.json()` succeeds.\n */\nfunction expressReqToWebRequest(req: ExpressRequest): Request {\n const protocol = req.protocol;\n const host = req.get('host') ?? 'localhost';\n const url = `${protocol}://${host}${req.originalUrl}`;\n const headers = new Headers();\n for (const [key, value] of Object.entries(req.headers)) {\n if (typeof value === 'string') {\n headers.set(key, value);\n } else if (Array.isArray(value)) {\n for (const v of value) headers.append(key, v);\n }\n }\n const bodyJson = JSON.stringify(req.body);\n return new Request(url, { method: req.method, headers, body: bodyJson });\n}\n\n/**\n * Write a Web-standard `Response` back to an express `Response`.\n * Streams the body chunk-by-chunk so SSE works without buffering.\n */\nasync function pipeWebResponseToExpress(\n webRes: Response,\n res: ExpressResponse,\n): Promise<void> {\n res.status(webRes.status);\n webRes.headers.forEach((value, key) => {\n res.setHeader(key, value);\n });\n if (webRes.body === null) {\n res.end();\n return;\n }\n const reader = webRes.body.getReader();\n try {\n for (;;) {\n const { done, value } = await reader.read();\n if (done) break;\n res.write(value);\n }\n } finally {\n reader.releaseLock();\n res.end();\n }\n}\n\n// ============================================================================\n// Exported factories\n// ============================================================================\n\n/**\n * Returns an Express `RequestHandler` that streams a generate call as SSE.\n *\n * Body shape accepted: `{ prompt: string; endUserId?: string; appId?: string }`\n */\nexport function createGenerateHandler(opts: GenerateHandlerOptions): RequestHandler {\n const coreHandler = coreGenerateHandler({\n apiKey: opts.apiKey,\n baseUrl: opts.baseUrl,\n endUserId: opts.endUserId\n ? (webReq: Request) => {\n // The x-user-id header is available on the Web Request; express opts.endUserId\n // receives the original express req via closure — pass the header value as a\n // synthetic express request shaped enough for the callback.\n const userId = webReq.headers.get('x-user-id');\n return userId ?? '';\n }\n : undefined,\n });\n return async (req: ExpressRequest, res: ExpressResponse): Promise<void> => {\n if (opts.endUserId) {\n const userId = opts.endUserId(req);\n if (userId) req.headers['x-user-id'] = userId;\n }\n const webReq = expressReqToWebRequest(req);\n const webRes = await coreHandler(webReq);\n await pipeWebResponseToExpress(webRes, res);\n };\n}\n\n/**\n * Returns an Express `RequestHandler` that calls `editSchema` and returns JSON.\n *\n * Body shape accepted: `{ appId: string; patch: EditSchemaPatch }`\n */\nexport function createEditHandler(opts: GenerateHandlerOptions): RequestHandler {\n const coreHandler = coreEditHandler({ apiKey: opts.apiKey, baseUrl: opts.baseUrl });\n return async (req: ExpressRequest, res: ExpressResponse): Promise<void> => {\n const webReq = expressReqToWebRequest(req);\n const webRes = await coreHandler(webReq);\n await pipeWebResponseToExpress(webRes, res);\n };\n}\n"]}
1
+ {"version":3,"sources":["../../src/types.ts","../../src/client/errors.ts","../../src/client/sseParser.ts","../../src/client/AlmadarClient.ts","../../src/server/index.ts","../../src/server/express.ts"],"names":["createGenerateHandler","createEditHandler"],"mappings":"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","file":"express.js","sourcesContent":["/**\n * Public SDK types. Canonical schema / payload types come from `@almadar/core`;\n * the SDK adds the HTTP-layer option shapes and re-exports the canonical SSE\n * event union.\n */\n\nimport type { EntityData, EventPayload, OrbitalSchema, SSEEvent } from '@almadar/core';\n\nexport type { EntityData, EventPayload, OrbitalSchema, SSEEvent };\n\n/**\n * Typed request envelope for `createGenerateHandler`.\n * Body shape: `{ prompt: string; endUserId?: string; appId?: string }`\n */\nexport interface GenerateRequest {\n prompt?: string;\n /** Alias accepted alongside `prompt`. */\n message?: string;\n endUserId?: string;\n appId?: string;\n}\n\n/**\n * Typed request envelope for `createEditHandler`.\n * Body shape: `{ appId: string; patch: EditSchemaPatch }`\n */\nexport interface EditSchemaRequest {\n appId?: string;\n patch?: EditSchemaPatch;\n}\n\n/**\n * Server-emitted error envelope. `code` maps to the SDK error subclasses:\n * 4001 → ApiKeyError, 4029 → RateLimitedError, 4040 → CatalogOutOfScopeError,\n * 4041-4045 → PinError, 4060 → AsyncUnsupportedError, 5001 → GenerationFailedError.\n * See `API_ERROR_CODES` for the full code table.\n */\nexport interface ApiErrorBody {\n code: number;\n message: string;\n details?: EventPayload;\n}\n\nexport const CATALOG_MODES = ['extend', 'subset', 'replace'] as const;\nexport type CatalogMode = (typeof CATALOG_MODES)[number];\n\n/**\n * Pin generation to a specific organism (and, when the organism has more than\n * one factory orbital, the orbital to use). `knobs` fills factory config.\n */\nexport interface GeneratePin {\n organism: string;\n /** Required iff the organism has more than one orbital. */\n orbital?: string;\n appName?: string;\n knobs?: Record<string, string | number | boolean>;\n}\n\n/** Which cache tier served the generation — L1 confirmed factory HIT, HIT-fail demote, or free-compose MISS. */\nexport type GenerationTier = 'confirmed' | 'hit' | 'miss';\n\nexport interface GenerateMetaOrganism {\n name: string;\n source: 'factory' | 'free-lolo';\n}\n\nexport interface GenerateMeta {\n tier: GenerationTier;\n organisms: GenerateMetaOrganism[];\n /** Organism names that HIT-failed and were demoted to free-compose. */\n demoted: string[];\n cacheVerdict: { verdict: 'hit' | 'miss'; chosen: string | null } | null;\n durationMs: number;\n}\n\nexport interface GenerationMetaEvent {\n type: 'generation_meta';\n data: GenerateMeta;\n timestamp: number;\n}\n\n/** Canonical SSE events plus the SDK-only `generation_meta` summary event. */\nexport type GenerateStreamEvent = SSEEvent | GenerationMetaEvent;\n\nfunction isGenerateMetaOrganism(value: unknown): value is GenerateMetaOrganism {\n if (value === null || typeof value !== 'object') return false;\n const v = value as { name?: unknown; source?: unknown };\n if (typeof v.name !== 'string') return false;\n return v.source === 'factory' || v.source === 'free-lolo';\n}\n\nfunction isGenerateMetaCacheVerdict(value: unknown): value is GenerateMeta['cacheVerdict'] {\n if (value === null) return true;\n if (typeof value !== 'object') return false;\n const v = value as { verdict?: unknown; chosen?: unknown };\n if (v.verdict !== 'hit' && v.verdict !== 'miss') return false;\n return v.chosen === null || typeof v.chosen === 'string';\n}\n\n/** Runtime guard for the `generation_meta` SSE payload — the zero-cast bridge from JSON. */\nexport function isGenerateMeta(value: unknown): value is GenerateMeta {\n if (value === null || typeof value !== 'object') return false;\n const v = value as {\n tier?: unknown;\n organisms?: unknown;\n demoted?: unknown;\n cacheVerdict?: unknown;\n durationMs?: unknown;\n };\n if (v.tier !== 'confirmed' && v.tier !== 'hit' && v.tier !== 'miss') return false;\n if (!Array.isArray(v.organisms) || !v.organisms.every(isGenerateMetaOrganism)) return false;\n if (!Array.isArray(v.demoted) || !v.demoted.every((d) => typeof d === 'string')) return false;\n if (!isGenerateMetaCacheVerdict(v.cacheVerdict)) return false;\n return typeof v.durationMs === 'number';\n}\n\nexport const API_ERROR_CODES = {\n INVALID_REQUEST: 4000,\n API_KEY: 4001,\n ORIGIN_FORBIDDEN: 4003,\n EDIT_CONFIRM_REQUIRED: 4009,\n RATE_LIMITED: 4029,\n CATALOG_OUT_OF_SCOPE: 4040,\n PIN_UNKNOWN_ORGANISM: 4041,\n PIN_OUT_OF_SCOPE: 4042,\n PIN_CONFLICT: 4043,\n PIN_UNKNOWN_KNOB: 4044,\n PIN_ORBITAL_REQUIRED: 4045,\n ASYNC_UNSUPPORTED: 4060,\n FOCUS_STALE: 4090,\n SERVER: 5000,\n GENERATION_FAILED: 5001,\n RUNTIME: 5002,\n WORKSPACE_OPEN: 5003,\n AI_UNCONFIGURED: 5030,\n} as const;\nexport type ApiErrorCode = (typeof API_ERROR_CODES)[keyof typeof API_ERROR_CODES];\n\n/** `error` event `code` values on the generate SSE stream. */\nexport const STREAM_ERROR_CODES = ['failed', 'runtime', 'workspace_open', 'ai_unconfigured', 'focus_stale'] as const;\nexport type StreamErrorCode = (typeof STREAM_ERROR_CODES)[number];\n\nexport interface GenerateOptions {\n prompt: string;\n endUserId?: string;\n appId?: string;\n /** Streaming callback for canonical SSE events plus the SDK's `generation_meta` summary. */\n onEvent?: (event: GenerateStreamEvent) => void;\n /**\n * The client has no async job surface: passing `true` throws\n * `AsyncUnsupportedError` (code 4060) before any network call is made.\n * For long-running generations use the default streaming mode with `onEvent`.\n */\n async?: boolean;\n /**\n * Agent provider override (e.g. 'deepseek', 'openai').\n * Omit to use the server's default.\n */\n provider?: string;\n /**\n * Agent model override (e.g. 'deepseek-chat').\n * Omit to use the server's default.\n */\n model?: string;\n /**\n * Behavior catalog mode — 'subset' narrows generation to stdAllowList.\n * Server-specific; omit if the agent does not support it.\n */\n catalogMode?: CatalogMode;\n /**\n * Allow-list of std behavior names. Requires a server that supports catalog\n * narrowing (e.g. the builder Rabit/Studio agent).\n */\n stdAllowList?: string[];\n /** Pin generation to a specific organism/orbital instead of free-composing. */\n pin?: GeneratePin;\n}\n\nexport interface GenerateResult {\n schema: OrbitalSchema;\n appId?: string;\n /** Absent for third-party servers built with `createGenerateHandler` that don't emit `generation_meta`. */\n meta?: GenerateMeta;\n}\n\n/**\n * Body of a `PUT /api/v1/agent/edit-schema`. Strictly structural; the SDK\n * does not deep-type the patch — that's the server's job. Field types are\n * `EventPayload`-compatible so callers can't sneak in arbitrary objects.\n */\nexport interface EditSchemaPatch {\n orbital?: string;\n traitOverrides?: EventPayload;\n config?: EventPayload;\n}\n\nexport interface CompileOptions {\n target?: 'express' | 'hono';\n shell?: 'typescript' | 'python' | 'mobile';\n}\n\nexport interface CompileResult {\n downloadUrl: string;\n expiresAt: string;\n}\n\nexport interface AlmadarClientOptions {\n apiKey: string;\n baseUrl?: string;\n fetch?: typeof fetch;\n}\n\n/**\n * Props for `<AlmadarApp />` — renders an orbital schema. The runtime mode\n * decides whether effects (persist/fetch/call-service) hit a backend or stay\n * mocked in-browser.\n */\nexport interface AlmadarAppProps {\n schema: OrbitalSchema;\n /**\n * - `static`: pure client-side, no server effects. Use with `data`.\n * - `mock` (default): in-browser fake server, faker-seeded if `data` is undefined.\n * - `server`: real backend at `serverUrl`.\n */\n mode?: 'static' | 'mock' | 'server';\n /** Seed data keyed by entity name (canonical `EntityData` shape). */\n data?: EntityData;\n /** Required when `mode === 'server'`. */\n serverUrl?: string;\n initialPagePath?: string;\n height?: string;\n className?: string;\n /**\n * Tiers of config knobs to surface as auto-derived controls. When provided,\n * a control rail is rendered next to the app. Omit to hide controls.\n * Common values: `['presentation']`, `['presentation', 'domain']`.\n */\n exposedTiers?: string[];\n /** Where to render the auto-derived controls rail. Default: 'right'. */\n controlsPosition?: 'right' | 'bottom';\n /**\n * Explicit override for whether the config-controls rail renders. When\n * omitted, falls back to legacy behavior: `exposedTiers` non-empty and\n * `mode !== 'server'`.\n */\n showControls?: boolean;\n}\n\n/**\n * Props for `<OrbitalConfigPanel />` — low-level control rail used by\n * `<AlmadarApp />` when `exposedTiers` is set.\n */\nexport interface OrbitalConfigPanelProps {\n schema: string | OrbitalSchema;\n exposedTiers?: string[];\n position?: 'right' | 'bottom';\n onSchemaChange?: (schema: OrbitalSchema) => void;\n}\n","/**\n * Typed SDK errors. Server emits a structured `ApiErrorBody`; the HTTP layer\n * maps the `code` to one of these subclasses. Customers `catch` by class.\n */\n\nimport { API_ERROR_CODES, STREAM_ERROR_CODES } from '../types';\nimport type { ApiErrorBody, StreamErrorCode } from '../types';\n\nexport class AlmadarError extends Error {\n readonly code: number;\n readonly details?: ApiErrorBody['details'];\n constructor(body: ApiErrorBody) {\n super(body.message);\n this.name = 'AlmadarError';\n this.code = body.code;\n this.details = body.details;\n }\n}\n\n/** 4001 — invalid, revoked, or missing API key. */\nexport class ApiKeyError extends AlmadarError {\n constructor(body: ApiErrorBody) {\n super(body);\n this.name = 'ApiKeyError';\n }\n}\n\n/** 4029 — team cap (feature counter) exceeded. Retry after a billing cycle. */\nexport class RateLimitedError extends AlmadarError {\n readonly retryAfterSeconds?: number;\n constructor(body: ApiErrorBody, retryAfterSeconds?: number) {\n super(body);\n this.name = 'RateLimitedError';\n this.retryAfterSeconds = retryAfterSeconds;\n }\n}\n\n/** 4040 — the team's behavior catalog (subset/replace mode) cannot serve the request. */\nexport class CatalogOutOfScopeError extends AlmadarError {\n constructor(body: ApiErrorBody) {\n super(body);\n this.name = 'CatalogOutOfScopeError';\n }\n}\n\n/** Anything else from the server with a recognized envelope but no specific subclass. */\nexport class ServerError extends AlmadarError {\n constructor(body: ApiErrorBody) {\n super(body);\n this.name = 'ServerError';\n }\n}\n\n/** 4041-4045 — pin resolution failed: unknown organism, out-of-scope, conflicting pins, unknown knob, or a missing required orbital. */\nexport class PinError extends AlmadarError {\n constructor(body: ApiErrorBody) {\n super(body);\n this.name = 'PinError';\n }\n}\n\n/** 4060 — `generate({ async: true })` has no server-side job surface; use the default streaming mode instead. */\nexport class AsyncUnsupportedError extends AlmadarError {\n constructor(body: ApiErrorBody) {\n super(body);\n this.name = 'AsyncUnsupportedError';\n }\n}\n\n/** 5001 — generation failed server-side. */\nexport class GenerationFailedError extends AlmadarError {\n constructor(body: ApiErrorBody) {\n super(body);\n this.name = 'GenerationFailedError';\n }\n}\n\nexport function errorFromBody(body: ApiErrorBody): AlmadarError {\n switch (body.code) {\n case API_ERROR_CODES.API_KEY:\n return new ApiKeyError(body);\n case API_ERROR_CODES.RATE_LIMITED:\n return new RateLimitedError(body);\n case API_ERROR_CODES.CATALOG_OUT_OF_SCOPE:\n return new CatalogOutOfScopeError(body);\n case API_ERROR_CODES.PIN_UNKNOWN_ORGANISM:\n case API_ERROR_CODES.PIN_OUT_OF_SCOPE:\n case API_ERROR_CODES.PIN_CONFLICT:\n case API_ERROR_CODES.PIN_UNKNOWN_KNOB:\n case API_ERROR_CODES.PIN_ORBITAL_REQUIRED:\n return new PinError(body);\n case API_ERROR_CODES.ASYNC_UNSUPPORTED:\n return new AsyncUnsupportedError(body);\n case API_ERROR_CODES.GENERATION_FAILED:\n return new GenerationFailedError(body);\n default:\n return new ServerError(body);\n }\n}\n\nfunction isStreamErrorCode(code: string | undefined): code is StreamErrorCode {\n if (code === undefined) return false;\n return STREAM_ERROR_CODES.some((c) => c === code);\n}\n\n/** Maps a `generate` SSE `error` event's `{ error, code }` payload to a typed SDK error. */\nexport function streamErrorFromEvent(data: { error: string; code?: string }): AlmadarError {\n const message = data.error;\n if (!isStreamErrorCode(data.code)) {\n return new ServerError({ code: API_ERROR_CODES.SERVER, message });\n }\n switch (data.code) {\n case 'failed':\n return new GenerationFailedError({ code: API_ERROR_CODES.GENERATION_FAILED, message });\n case 'ai_unconfigured':\n return new ServerError({ code: API_ERROR_CODES.AI_UNCONFIGURED, message });\n case 'workspace_open':\n return new ServerError({ code: API_ERROR_CODES.WORKSPACE_OPEN, message });\n case 'focus_stale':\n return new ServerError({ code: API_ERROR_CODES.FOCUS_STALE, message });\n case 'runtime':\n return new ServerError({ code: API_ERROR_CODES.RUNTIME, message });\n }\n}\n","/**\n * Minimal Server-Sent Events parser. Reads a `ReadableStream<Uint8Array>`\n * (the body of a `fetch` Response) and yields decoded events. Universal:\n * works in browser, Node 18+, Deno, Bun.\n *\n * Spec subset implemented:\n * - `event:` and `data:` fields\n * - dispatch on blank line\n * - newline-tolerant (CRLF + LF)\n * - skips comments (`:`-prefixed lines)\n *\n * Not implemented (we don't need them):\n * - `id:` / `retry:` fields\n * - reconnection / last-event-id\n */\n\nexport interface RawSseEvent {\n /** `event:` field value. Empty string when absent — matches the spec default. */\n event: string;\n /** Concatenated `data:` lines, joined by newlines. */\n data: string;\n}\n\nexport async function* parseSSE(\n stream: ReadableStream<Uint8Array>,\n): AsyncGenerator<RawSseEvent, void, void> {\n const reader = stream.getReader();\n const decoder = new TextDecoder('utf-8');\n let buffer = '';\n let currentEvent = '';\n let currentData = '';\n\n try {\n for (;;) {\n const { value, done } = await reader.read();\n if (done) break;\n buffer += decoder.decode(value, { stream: true });\n\n let newlineIdx: number;\n while ((newlineIdx = indexOfNewline(buffer)) !== -1) {\n const rawLine = buffer.slice(0, newlineIdx);\n buffer = buffer.slice(newlineIdx + (buffer[newlineIdx] === '\\r' && buffer[newlineIdx + 1] === '\\n' ? 2 : 1));\n\n if (rawLine === '') {\n if (currentData !== '' || currentEvent !== '') {\n yield { event: currentEvent, data: currentData };\n currentEvent = '';\n currentData = '';\n }\n continue;\n }\n if (rawLine.startsWith(':')) continue;\n\n const colon = rawLine.indexOf(':');\n const field = colon === -1 ? rawLine : rawLine.slice(0, colon);\n const rawValue = colon === -1 ? '' : rawLine.slice(colon + 1);\n const value2 = rawValue.startsWith(' ') ? rawValue.slice(1) : rawValue;\n\n if (field === 'event') {\n currentEvent = value2;\n } else if (field === 'data') {\n currentData = currentData === '' ? value2 : `${currentData}\\n${value2}`;\n }\n }\n }\n if (currentData !== '' || currentEvent !== '') {\n yield { event: currentEvent, data: currentData };\n }\n } finally {\n reader.releaseLock();\n }\n}\n\nfunction indexOfNewline(s: string): number {\n for (let i = 0; i < s.length; i += 1) {\n const c = s[i];\n if (c === '\\n' || c === '\\r') return i;\n }\n return -1;\n}\n","/**\n * `AlmadarClient` — server / Node-side HTTP client targeting `/api/v1/agent/*`.\n * Authenticates with a team-bound API key (`sk_*`) issued from\n * Studio's `/settings/sdk` panel. See `docs/Almadar_Studio_SDK.md` §5.\n *\n * Never instantiate this in a browser bundle — `apiKey` must never leave\n * the customer's server.\n */\n\nimport { parseOrbitalSchema, type OrbitalSchema, type SSEEvent } from '@almadar/core';\nimport { API_ERROR_CODES, isGenerateMeta } from '../types';\nimport type {\n AlmadarClientOptions,\n ApiErrorBody,\n CompileOptions,\n CompileResult,\n EditSchemaPatch,\n GenerateMeta,\n GenerateOptions,\n GenerateResult,\n GenerateStreamEvent,\n} from '../types';\nimport { AsyncUnsupportedError, errorFromBody, ServerError, streamErrorFromEvent } from './errors';\nimport { parseSSE } from './sseParser';\n\nconst DEFAULT_BASE_URL = 'https://studio.almadar.io';\n\nexport class AlmadarClient {\n private readonly apiKey: string;\n private readonly baseUrl: string;\n private readonly fetchImpl: typeof fetch;\n\n constructor(opts: AlmadarClientOptions) {\n if (!opts.apiKey || typeof opts.apiKey !== 'string') {\n throw new Error('AlmadarClient: opts.apiKey is required');\n }\n this.apiKey = opts.apiKey;\n this.baseUrl = (opts.baseUrl ?? DEFAULT_BASE_URL).replace(/\\/$/, '');\n this.fetchImpl = opts.fetch ?? globalThis.fetch;\n if (typeof this.fetchImpl !== 'function') {\n throw new Error('AlmadarClient: no fetch available — pass opts.fetch for Node <18');\n }\n }\n\n async generate(input: GenerateOptions): Promise<GenerateResult> {\n if (input.async === true) {\n throw new AsyncUnsupportedError({\n code: API_ERROR_CODES.ASYNC_UNSUPPORTED,\n message: 'AlmadarClient has no async job surface. Omit `async` (or pass false) and consume the streaming response via `onEvent` instead.',\n });\n }\n return this.streamGenerate(input);\n }\n\n async editSchema(appId: string, patch: EditSchemaPatch): Promise<OrbitalSchema> {\n if (!appId) throw new Error('AlmadarClient.editSchema: appId is required');\n const schema = await this.requestJson<OrbitalSchema>('PUT', '/api/v1/agent/edit-schema', {\n appId,\n patch,\n });\n assertString(schema.name, 'OrbitalSchema.name');\n return schema;\n }\n\n async compileToApp(schema: OrbitalSchema, opts?: CompileOptions): Promise<CompileResult> {\n const result = await this.requestJson<CompileResult>('POST', '/api/v1/agent/compile', {\n schema,\n target: opts?.target,\n shell: opts?.shell,\n });\n assertString(result.downloadUrl, 'CompileResult.downloadUrl');\n assertString(result.expiresAt, 'CompileResult.expiresAt');\n return result;\n }\n\n private async streamGenerate(input: GenerateOptions): Promise<GenerateResult> {\n const res = await this.fetchImpl(`${this.baseUrl}/api/v1/agent/generate`, {\n method: 'POST',\n headers: this.headers({ accept: 'text/event-stream', contentType: 'application/json' }, input.endUserId),\n body: JSON.stringify({\n prompt: input.prompt,\n endUserId: input.endUserId,\n appId: input.appId,\n provider: input.provider,\n model: input.model,\n catalogMode: input.catalogMode,\n stdAllowList: input.stdAllowList,\n pin: input.pin,\n }),\n });\n if (!res.ok) throw await this.errorFromResponse(res);\n if (res.body === null) throw new Error('AlmadarClient.generate: server returned no body');\n\n let final: GenerateResult | null = null;\n let meta: GenerateMeta | undefined;\n for await (const raw of parseSSE(res.body)) {\n const event = parseSseEvent(raw.data);\n if (event === null) continue;\n input.onEvent?.(event);\n if (event.type === 'generation_meta') {\n meta = event.data;\n } else if (event.type === 'complete') {\n if (event.data.schema === undefined) {\n throw new ServerError({ code: API_ERROR_CODES.SERVER, message: '`complete` event did not contain a schema' });\n }\n const schema = parseOrbitalSchema(event.data.schema);\n final = { schema, appId: event.data.appId, meta };\n } else if (event.type === 'error') {\n throw streamErrorFromEvent(event.data);\n }\n }\n if (final === null) {\n throw new ServerError({ code: API_ERROR_CODES.SERVER, message: 'SSE stream ended without `complete` event' });\n }\n return final;\n }\n\n private async requestJson<T>(method: string, path: string, body?: object): Promise<T> {\n const isAbsolute = path.startsWith('http://') || path.startsWith('https://');\n const url = isAbsolute ? path : `${this.baseUrl}${path}`;\n const init: RequestInit = {\n method,\n headers: this.headers({\n accept: 'application/json',\n contentType: body !== undefined ? 'application/json' : undefined,\n }),\n };\n if (body !== undefined) init.body = JSON.stringify(body);\n const res = await this.fetchImpl(url, init);\n if (!res.ok) throw await this.errorFromResponse(res);\n const text = await res.text();\n if (text === '') {\n throw new ServerError({ code: API_ERROR_CODES.SERVER, message: 'Empty response body' });\n }\n const parsed: T = JSON.parse(text);\n return parsed;\n }\n\n private headers(\n opts: { accept?: string; contentType?: string },\n endUserId?: string,\n ): Record<string, string> {\n const h: Record<string, string> = { authorization: `Bearer ${this.apiKey}` };\n if (opts.accept !== undefined) h['accept'] = opts.accept;\n if (opts.contentType !== undefined) h['content-type'] = opts.contentType;\n if (endUserId !== undefined && endUserId !== '') h['x-end-user-id'] = endUserId;\n return h;\n }\n\n private async errorFromResponse(res: Response): Promise<Error> {\n const text = await res.text();\n let body: ApiErrorBody;\n try {\n const parsed: ApiErrorBody | null = text === '' ? null : JSON.parse(text);\n body = parsed !== null && typeof parsed.code === 'number' && typeof parsed.message === 'string'\n ? parsed\n : {\n code: res.status,\n message: res.statusText !== '' ? res.statusText : 'HTTP error',\n };\n } catch {\n body = { code: res.status, message: text !== '' ? text : res.statusText };\n }\n const retryAfter = res.headers.get('retry-after');\n const err = errorFromBody(body);\n if (err.name === 'RateLimitedError' && retryAfter !== null) {\n const seconds = Number(retryAfter);\n if (Number.isFinite(seconds)) {\n Object.defineProperty(err, 'retryAfterSeconds', { value: seconds, enumerable: true });\n }\n }\n return err;\n }\n}\n\n/**\n * Parse one SSE `data:` line into the `GenerateStreamEvent` union. The server\n * is the trusted emitter, so we validate only the envelope (object with\n * string `type` and numeric `timestamp`) and cast to the canonical `SSEEvent`\n * union — except `generation_meta`, which is SDK-only and goes through the\n * `isGenerateMeta` runtime guard instead of a cast. Malformed lines are ignored.\n */\nfunction parseSseEvent(dataLine: string): GenerateStreamEvent | null {\n if (dataLine === '') return null;\n let payload;\n try {\n payload = JSON.parse(dataLine);\n } catch {\n return null;\n }\n if (payload === null || typeof payload !== 'object' || Array.isArray(payload)) return null;\n if (typeof payload.type !== 'string' || typeof payload.timestamp !== 'number') return null;\n if (payload.type === 'generation_meta') {\n return isGenerateMeta(payload.data)\n ? { type: 'generation_meta', data: payload.data, timestamp: payload.timestamp }\n : null;\n }\n return payload as SSEEvent;\n}\n\nfunction assertString(v: string | undefined, name: string): asserts v is string {\n if (typeof v !== 'string' || v === '') {\n throw new ServerError({ code: API_ERROR_CODES.SERVER, message: `Malformed server response: ${name} is not a string` });\n }\n}\n","/**\n * `@almadar/sdk/server` — Framework-agnostic Web-standard Fetch handlers for\n * the Almadar agent proxy. Node-only; never import from browser or React code.\n *\n * Usage:\n * import { createGenerateHandler, createEditHandler } from '@almadar/sdk/server';\n * const handler = createGenerateHandler({ apiKey: process.env.ALMADAR_API_KEY! });\n * // handler: (request: Request) => Promise<Response>\n *\n * For framework adapters see `@almadar/sdk/server/express` and `@almadar/sdk/server/hono`.\n */\n\nimport type { OrbitalSchema } from '@almadar/core';\nimport { AlmadarClient } from '../client/AlmadarClient';\nimport type { EditSchemaRequest, EditSchemaPatch, GenerateRequest, GenerateStreamEvent, SSEEvent } from '../types';\n\n// ============================================================================\n// Public option surface\n// ============================================================================\n\nexport interface GenerateHandlerOptions {\n /** API key issued from Studio's /settings/sdk panel. */\n apiKey: string;\n /** Defaults to https://studio.almadar.io. */\n baseUrl?: string;\n /**\n * Derive a stable end-user id from the incoming Web Request.\n * Falls back to the `x-user-id` request header when omitted.\n */\n endUserId?: (req: Request) => string;\n}\n\n// ============================================================================\n// Internal helpers\n// ============================================================================\n\nfunction resolveEndUserId(opts: GenerateHandlerOptions, req: Request): string | undefined {\n if (opts.endUserId) return opts.endUserId(req);\n const header = req.headers.get('x-user-id');\n return typeof header === 'string' && header.length > 0 ? header : undefined;\n}\n\nfunction encodeSseEvent(event: GenerateStreamEvent): string {\n return `data: ${JSON.stringify(event)}\\n\\n`;\n}\n\n// ============================================================================\n// createGenerateHandler\n// ============================================================================\n\n/**\n * Returns a Web-standard Fetch handler that streams a generate call as SSE.\n *\n * Body shape accepted: `{ prompt: string; endUserId?: string; appId?: string }`\n */\nexport function createGenerateHandler(\n opts: GenerateHandlerOptions,\n): (request: Request) => Promise<Response> {\n return async (request: Request): Promise<Response> => {\n let body: GenerateRequest;\n try {\n body = (await request.json()) as GenerateRequest;\n } catch {\n return new Response(JSON.stringify({ error: 'invalid JSON body' }), {\n status: 400,\n headers: { 'content-type': 'application/json' },\n });\n }\n\n const rawPrompt = body.prompt ?? body.message;\n const prompt = typeof rawPrompt === 'string' ? rawPrompt : '';\n\n if (!prompt) {\n return new Response(JSON.stringify({ error: 'prompt or message is required' }), {\n status: 400,\n headers: { 'content-type': 'application/json' },\n });\n }\n\n const bodyEndUserId = typeof body.endUserId === 'string' ? body.endUserId : undefined;\n const endUserId = bodyEndUserId ?? resolveEndUserId(opts, request);\n const appId = typeof body.appId === 'string' ? body.appId : undefined;\n\n const client = new AlmadarClient({ apiKey: opts.apiKey, baseUrl: opts.baseUrl });\n\n const stream = new ReadableStream<Uint8Array>({\n async start(controller) {\n const encoder = new TextEncoder();\n try {\n await client.generate({\n prompt,\n endUserId,\n appId,\n onEvent: (event: GenerateStreamEvent) => {\n controller.enqueue(encoder.encode(encodeSseEvent(event)));\n },\n });\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err);\n const errorEvent: SSEEvent = {\n type: 'error',\n timestamp: Date.now(),\n data: { error: message },\n };\n controller.enqueue(encoder.encode(encodeSseEvent(errorEvent)));\n } finally {\n controller.close();\n }\n },\n });\n\n return new Response(stream, {\n status: 200,\n headers: {\n 'content-type': 'text/event-stream',\n 'cache-control': 'no-cache',\n connection: 'keep-alive',\n },\n });\n };\n}\n\n// ============================================================================\n// createEditHandler\n// ============================================================================\n\n/**\n * Returns a Web-standard Fetch handler that calls `editSchema` and returns JSON.\n *\n * Body shape accepted: `{ appId: string; patch: EditSchemaPatch }`\n */\nexport function createEditHandler(\n opts: GenerateHandlerOptions,\n): (request: Request) => Promise<Response> {\n return async (request: Request): Promise<Response> => {\n let body: EditSchemaRequest;\n try {\n body = (await request.json()) as EditSchemaRequest;\n } catch {\n return new Response(JSON.stringify({ error: 'invalid JSON body' }), {\n status: 400,\n headers: { 'content-type': 'application/json' },\n });\n }\n\n const appId = typeof body.appId === 'string' ? body.appId : '';\n if (!appId) {\n return new Response(JSON.stringify({ error: 'appId is required' }), {\n status: 400,\n headers: { 'content-type': 'application/json' },\n });\n }\n\n const patch: EditSchemaPatch | undefined = body.patch;\n if (patch === undefined || patch === null || typeof patch !== 'object') {\n return new Response(JSON.stringify({ error: 'patch is required' }), {\n status: 400,\n headers: { 'content-type': 'application/json' },\n });\n }\n\n const client = new AlmadarClient({ apiKey: opts.apiKey, baseUrl: opts.baseUrl });\n\n try {\n const schema: OrbitalSchema = await client.editSchema(appId, patch);\n return new Response(JSON.stringify(schema), {\n status: 200,\n headers: { 'content-type': 'application/json' },\n });\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err);\n return new Response(JSON.stringify({ error: message }), {\n status: 500,\n headers: { 'content-type': 'application/json' },\n });\n }\n };\n}\n","/**\n * `@almadar/sdk/server/express` — Express adapter for the Almadar server handlers.\n *\n * Node-only. The consumer must provide their own `express` installation.\n * This module imports express TYPES only; it is never bundled with express itself.\n *\n * Usage:\n * import { createGenerateHandler, createEditHandler } from '@almadar/sdk/server/express';\n * app.post('/api/agent/generate', createGenerateHandler({ apiKey }));\n * app.put('/api/agent/edit', createEditHandler({ apiKey }));\n */\n\nimport type { Request as ExpressRequest, Response as ExpressResponse, RequestHandler } from 'express';\nimport {\n createGenerateHandler as coreGenerateHandler,\n createEditHandler as coreEditHandler,\n} from './index';\n\n// ============================================================================\n// Express-specific option surface\n// ============================================================================\n\nexport interface GenerateHandlerOptions {\n /** API key issued from Studio's /settings/sdk panel. */\n apiKey: string;\n /** Defaults to https://studio.almadar.io. */\n baseUrl?: string;\n /**\n * Derive a stable end-user id from the Express request.\n * Falls back to the `x-user-id` request header when omitted.\n */\n endUserId?: (req: ExpressRequest) => string;\n}\n\n// ============================================================================\n// Express↔Fetch bridge helpers\n// ============================================================================\n\n/**\n * Convert an Express `Request` to a Web-standard `Request`.\n * Re-serialises the already-parsed body so the core handler's `request.json()` succeeds.\n */\nfunction expressReqToWebRequest(req: ExpressRequest): Request {\n const protocol = req.protocol;\n const host = req.get('host') ?? 'localhost';\n const url = `${protocol}://${host}${req.originalUrl}`;\n const headers = new Headers();\n for (const [key, value] of Object.entries(req.headers)) {\n if (typeof value === 'string') {\n headers.set(key, value);\n } else if (Array.isArray(value)) {\n for (const v of value) headers.append(key, v);\n }\n }\n const bodyJson = JSON.stringify(req.body);\n return new Request(url, { method: req.method, headers, body: bodyJson });\n}\n\n/**\n * Write a Web-standard `Response` back to an express `Response`.\n * Streams the body chunk-by-chunk so SSE works without buffering.\n */\nasync function pipeWebResponseToExpress(\n webRes: Response,\n res: ExpressResponse,\n): Promise<void> {\n res.status(webRes.status);\n webRes.headers.forEach((value, key) => {\n res.setHeader(key, value);\n });\n if (webRes.body === null) {\n res.end();\n return;\n }\n const reader = webRes.body.getReader();\n try {\n for (;;) {\n const { done, value } = await reader.read();\n if (done) break;\n res.write(value);\n }\n } finally {\n reader.releaseLock();\n res.end();\n }\n}\n\n// ============================================================================\n// Exported factories\n// ============================================================================\n\n/**\n * Returns an Express `RequestHandler` that streams a generate call as SSE.\n *\n * Body shape accepted: `{ prompt: string; endUserId?: string; appId?: string }`\n */\nexport function createGenerateHandler(opts: GenerateHandlerOptions): RequestHandler {\n const coreHandler = coreGenerateHandler({\n apiKey: opts.apiKey,\n baseUrl: opts.baseUrl,\n endUserId: opts.endUserId\n ? (webReq: Request) => {\n // The x-user-id header is available on the Web Request; express opts.endUserId\n // receives the original express req via closure — pass the header value as a\n // synthetic express request shaped enough for the callback.\n const userId = webReq.headers.get('x-user-id');\n return userId ?? '';\n }\n : undefined,\n });\n return async (req: ExpressRequest, res: ExpressResponse): Promise<void> => {\n if (opts.endUserId) {\n const userId = opts.endUserId(req);\n if (userId) req.headers['x-user-id'] = userId;\n }\n const webReq = expressReqToWebRequest(req);\n const webRes = await coreHandler(webReq);\n await pipeWebResponseToExpress(webRes, res);\n };\n}\n\n/**\n * Returns an Express `RequestHandler` that calls `editSchema` and returns JSON.\n *\n * Body shape accepted: `{ appId: string; patch: EditSchemaPatch }`\n */\nexport function createEditHandler(opts: GenerateHandlerOptions): RequestHandler {\n const coreHandler = coreEditHandler({ apiKey: opts.apiKey, baseUrl: opts.baseUrl });\n return async (req: ExpressRequest, res: ExpressResponse): Promise<void> => {\n const webReq = expressReqToWebRequest(req);\n const webRes = await coreHandler(webReq);\n await pipeWebResponseToExpress(webRes, res);\n };\n}\n"]}