codai-sdk 0.7.0 → 0.13.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -415,6 +415,12 @@ var Agents = class {
415
415
  };
416
416
 
417
417
  // src/resources/audio.ts
418
+ function base64ToBytes(b64) {
419
+ const bin = atob(b64);
420
+ const out = new Uint8Array(bin.length);
421
+ for (let i = 0; i < bin.length; i++) out[i] = bin.charCodeAt(i);
422
+ return out;
423
+ }
418
424
  var Audio = class {
419
425
  constructor(http) {
420
426
  this.http = http;
@@ -466,6 +472,29 @@ var Audio = class {
466
472
  headers: res.headers
467
473
  };
468
474
  }
475
+ /**
476
+ * Streaming neural TTS with visemes + word boundaries (`codai-tts-ro`, Azure AI Speech).
477
+ * Yields `start`, then `audio` / `viseme` / `word` in synthesis order, then `done` (or `error`).
478
+ * Voices: `alina` (default), `emil`, or any Azure neural voice name. Default format `pcm`
479
+ * (PCM16 mono 24 kHz). Works with an ephemeral token of scope `audio` or `live`.
480
+ */
481
+ async *speechStream(body, opts = {}) {
482
+ const frames = this.http.sse("/v1/audio/speech/stream", {
483
+ body: { ...body, model: body.model ?? "codai-tts-ro" },
484
+ ext: opts.ext,
485
+ signal: opts.signal
486
+ });
487
+ for await (const frame of frames) {
488
+ const data = frameJson(frame);
489
+ if (!data || typeof data.type !== "string") continue;
490
+ if (data.type === "audio" && typeof data.delta === "string") {
491
+ yield { type: "audio", delta: data.delta, audio: base64ToBytes(data.delta) };
492
+ continue;
493
+ }
494
+ yield data;
495
+ if (data.type === "done" || data.type === "error") return;
496
+ }
497
+ }
469
498
  };
470
499
 
471
500
  // src/resources/chat.ts
@@ -633,6 +662,17 @@ var Devices = class {
633
662
  signal: opts.signal
634
663
  });
635
664
  }
665
+ /**
666
+ * `POST /v1/keys/self/revoke` — the API key this client uses revokes ITSELF (sign out).
667
+ * Every later call with it fails with 401.
668
+ */
669
+ revokeSelfKey(opts = {}) {
670
+ return this.http.json("/v1/keys/self/revoke", {
671
+ method: "POST",
672
+ ext: opts.ext,
673
+ signal: opts.signal
674
+ });
675
+ }
636
676
  /**
637
677
  * `GET /v1/devices/me/dispatch?limit=` — pending controls dispatched at the
638
678
  * calling device (`x-codai-device` required) across all owned sessions.
@@ -1012,6 +1052,60 @@ var Hosts = class {
1012
1052
  }
1013
1053
  };
1014
1054
 
1055
+ // src/resources/images.ts
1056
+ var MIN_IMAGE_TIMEOUT_MS = 15e4;
1057
+ function decodeBase64(b64) {
1058
+ const bin = atob(b64);
1059
+ const out = new Uint8Array(bin.length);
1060
+ for (let i = 0; i < bin.length; i++) out[i] = bin.charCodeAt(i);
1061
+ return out;
1062
+ }
1063
+ var Images = class {
1064
+ constructor(http) {
1065
+ this.http = http;
1066
+ }
1067
+ http;
1068
+ /**
1069
+ * Generate images. Needs a real API key (ephemeral tokens are rejected).
1070
+ * Pass `reference_images` to keep a logo/palette/product consistent.
1071
+ */
1072
+ async generate(body, opts = {}) {
1073
+ return this.post(
1074
+ "/v1/images/generations",
1075
+ { ...body, model: body.model ?? "codai-image" },
1076
+ opts
1077
+ );
1078
+ }
1079
+ /**
1080
+ * Edit one or more input images (`image`: one `{ b64_json, mime_type }` or an array of up to 14)
1081
+ * from a text instruction. JSON body; `mask` is not supported — describe the region in `prompt`.
1082
+ */
1083
+ async edit(body, opts = {}) {
1084
+ return this.post("/v1/images/edits", { ...body, model: body.model ?? "codai-image" }, opts);
1085
+ }
1086
+ async post(path, body, opts) {
1087
+ const res = await this.http.request(path, {
1088
+ body,
1089
+ ext: opts.ext,
1090
+ signal: opts.signal,
1091
+ // 0 = timeout disabled on the client; otherwise never cap below the image floor.
1092
+ timeoutMs: this.http.timeoutMs === 0 ? 0 : Math.max(this.http.timeoutMs, MIN_IMAGE_TIMEOUT_MS)
1093
+ });
1094
+ const raw = await res.json();
1095
+ const cost = res.headers.get("x-codai-cost-micro-usd");
1096
+ const data = raw.data ?? [];
1097
+ return {
1098
+ images: data.map((d) => decodeBase64(d.b64_json)),
1099
+ mimeTypes: data.map((d) => d.mime_type ?? "image/png"),
1100
+ raw,
1101
+ routedTo: res.headers.get("x-codai-routed-to"),
1102
+ dataRegion: res.headers.get("x-codai-data-region"),
1103
+ costMicroUsd: cost === null ? null : Number(cost),
1104
+ headers: res.headers
1105
+ };
1106
+ }
1107
+ };
1108
+
1015
1109
  // src/resources/messages.ts
1016
1110
  var Messages = class {
1017
1111
  constructor(http) {
@@ -1219,6 +1313,167 @@ var Projects = class {
1219
1313
  }
1220
1314
  };
1221
1315
 
1316
+ // src/resources/realtime.ts
1317
+ var OPEN = 1;
1318
+ function toBytes(audio) {
1319
+ if (audio instanceof ArrayBuffer) return new Uint8Array(audio);
1320
+ return new Uint8Array(audio.buffer, audio.byteOffset, audio.byteLength);
1321
+ }
1322
+ function bytesToBase64(bytes) {
1323
+ let bin = "";
1324
+ const CHUNK = 32768;
1325
+ for (let i = 0; i < bytes.length; i += CHUNK) {
1326
+ bin += String.fromCharCode(...bytes.subarray(i, i + CHUNK));
1327
+ }
1328
+ return btoa(bin);
1329
+ }
1330
+ var RealtimeSession = class {
1331
+ constructor(socket, firstFrame) {
1332
+ this.socket = socket;
1333
+ let resolveReady;
1334
+ let rejectReady;
1335
+ this.ready = new Promise((res, rej) => {
1336
+ resolveReady = res;
1337
+ rejectReady = rej;
1338
+ });
1339
+ this.ready.catch(() => void 0);
1340
+ socket.onopen = () => {
1341
+ if (firstFrame) socket.send(JSON.stringify(firstFrame));
1342
+ for (const f of this.outbox.splice(0)) socket.send(f);
1343
+ resolveReady();
1344
+ };
1345
+ socket.onmessage = (ev) => {
1346
+ if (typeof ev.data !== "string") return;
1347
+ let parsed;
1348
+ try {
1349
+ parsed = JSON.parse(ev.data);
1350
+ } catch {
1351
+ return;
1352
+ }
1353
+ if (parsed && typeof parsed === "object" && typeof parsed.type === "string") {
1354
+ this.emit(parsed);
1355
+ }
1356
+ };
1357
+ socket.onerror = () => {
1358
+ };
1359
+ socket.onclose = (ev) => {
1360
+ rejectReady(
1361
+ new Error(`realtime socket closed before open (${String(ev.code)} ${ev.reason})`)
1362
+ );
1363
+ this.emit({ type: "close", code: ev.code, reason: ev.reason });
1364
+ this.closed = true;
1365
+ for (const w of this.waiters.splice(0)) w({ value: void 0, done: true });
1366
+ };
1367
+ }
1368
+ socket;
1369
+ listeners = /* @__PURE__ */ new Map();
1370
+ queue = [];
1371
+ waiters = [];
1372
+ outbox = [];
1373
+ closed = false;
1374
+ /** Resolves when the socket is open (rejects if it closes first). */
1375
+ ready;
1376
+ /** Listen for one event type (`'*'` = every event). Returns an unsubscribe function. */
1377
+ on(type, fn) {
1378
+ let set = this.listeners.get(type);
1379
+ if (!set) this.listeners.set(type, set = /* @__PURE__ */ new Set());
1380
+ set.add(fn);
1381
+ return () => set.delete(fn);
1382
+ }
1383
+ /** Send any client event (JSON). Queued until the socket opens. */
1384
+ send(event) {
1385
+ if (this.closed) throw new Error("realtime session is closed");
1386
+ const frame = JSON.stringify(event);
1387
+ if (this.socket.readyState === OPEN) this.socket.send(frame);
1388
+ else this.outbox.push(frame);
1389
+ }
1390
+ /** Append PCM16 little-endian mono audio (24 kHz for `codai-transcribe-live`). */
1391
+ appendAudio(audio) {
1392
+ const bytes = toBytes(audio);
1393
+ if (bytes.byteLength === 0) return;
1394
+ this.send({ type: "input_audio_buffer.append", audio: bytesToBase64(bytes) });
1395
+ }
1396
+ /** Close the current utterance: the server answers with one `...transcription.completed`. */
1397
+ commit() {
1398
+ this.send({ type: "input_audio_buffer.commit" });
1399
+ }
1400
+ /** Drop audio the server holds for the current utterance. */
1401
+ clear() {
1402
+ this.send({ type: "input_audio_buffer.clear" });
1403
+ }
1404
+ close(code = 1e3, reason = "client closed") {
1405
+ if (this.closed) return;
1406
+ this.socket.close(code, reason);
1407
+ }
1408
+ [Symbol.asyncIterator]() {
1409
+ return {
1410
+ next: () => {
1411
+ const ev = this.queue.shift();
1412
+ if (ev) return Promise.resolve({ value: ev, done: false });
1413
+ if (this.closed) return Promise.resolve({ value: void 0, done: true });
1414
+ return new Promise((resolve) => this.waiters.push(resolve));
1415
+ },
1416
+ return: () => {
1417
+ this.close();
1418
+ return Promise.resolve({ value: void 0, done: true });
1419
+ }
1420
+ };
1421
+ }
1422
+ emit(ev) {
1423
+ for (const fn of this.listeners.get(ev.type) ?? []) fn(ev);
1424
+ for (const fn of this.listeners.get("*") ?? []) fn(ev);
1425
+ const w = this.waiters.shift();
1426
+ if (w) w({ value: ev, done: false });
1427
+ else this.queue.push(ev);
1428
+ }
1429
+ };
1430
+ function realtimeUrl(baseUrl, opts) {
1431
+ const url = new URL(`${baseUrl.replace(/\/$/, "").replace(/^http/, "ws")}/v1/realtime`);
1432
+ url.searchParams.set("model", opts.model ?? "codai-transcribe-live");
1433
+ if (opts.language) url.searchParams.set("language", opts.language);
1434
+ if (opts.sessionId) url.searchParams.set("session_id", opts.sessionId);
1435
+ if (opts.token) url.searchParams.set("key", opts.token);
1436
+ return url.toString();
1437
+ }
1438
+ var Realtime = class {
1439
+ constructor(defaults) {
1440
+ this.defaults = defaults;
1441
+ }
1442
+ defaults;
1443
+ /** Open a realtime session. Returns immediately; `await session.ready` to wait for the socket. */
1444
+ connect(opts = {}) {
1445
+ const Ctor = opts.WebSocket ?? globalThis.WebSocket;
1446
+ if (!Ctor) throw new Error("codai.realtime: no WebSocket available \u2014 pass options.WebSocket");
1447
+ const model = opts.model ?? "codai-transcribe-live";
1448
+ let token = opts.token;
1449
+ let apiKey = token ? void 0 : opts.apiKey ?? this.defaults.apiKey;
1450
+ if (apiKey?.startsWith("codai_eph_v1.")) {
1451
+ token = apiKey;
1452
+ apiKey = void 0;
1453
+ }
1454
+ if (!token && !apiKey) throw new Error("codai.realtime: pass `token` (browser) or `apiKey`");
1455
+ const url = realtimeUrl(opts.baseUrl ?? this.defaults.baseUrl, { ...opts, model, token });
1456
+ const socket = apiKey ? new Ctor(url, void 0, { headers: { Authorization: `Bearer ${apiKey}` } }) : new Ctor(url);
1457
+ if ("binaryType" in socket) socket.binaryType = "arraybuffer";
1458
+ const first = opts.sessionUpdate !== void 0 ? opts.sessionUpdate : model === "codai-transcribe-live" ? {
1459
+ type: "session.update",
1460
+ session: {
1461
+ type: "transcription",
1462
+ audio: {
1463
+ input: {
1464
+ format: { type: "audio/pcm", rate: 24e3 },
1465
+ transcription: {
1466
+ model,
1467
+ ...opts.language ? { language: opts.language } : {}
1468
+ }
1469
+ }
1470
+ }
1471
+ }
1472
+ } : null;
1473
+ return new RealtimeSession(socket, first);
1474
+ }
1475
+ };
1476
+
1222
1477
  // src/resources/resolve.ts
1223
1478
  function verifyResolveWebhook(secret, rawBody, signatureHeader, opts = {}) {
1224
1479
  if (!secret || !signatureHeader) return false;
@@ -1277,7 +1532,7 @@ function canonicalJson(v) {
1277
1532
  const o = v;
1278
1533
  return `{${Object.keys(o).filter((k) => o[k] !== void 0).sort().map((k) => `${JSON.stringify(k)}:${canonicalJson(o[k])}`).join(",")}}`;
1279
1534
  }
1280
- function base64ToBytes(b64) {
1535
+ function base64ToBytes2(b64) {
1281
1536
  const bin = atob(b64);
1282
1537
  const out = new Uint8Array(bin.length);
1283
1538
  for (let i = 0; i < bin.length; i++) out[i] = bin.charCodeAt(i);
@@ -1322,7 +1577,7 @@ function verifyAttestationWithKeys(att, keys) {
1322
1577
  const { createVerify } = verifyCrypto();
1323
1578
  let body;
1324
1579
  try {
1325
- body = base64ToBytes(env.payload);
1580
+ body = base64ToBytes2(env.payload);
1326
1581
  } catch {
1327
1582
  return { ok: false, reason: "BAD_SIGNATURE" };
1328
1583
  }
@@ -1331,7 +1586,7 @@ function verifyAttestationWithKeys(att, keys) {
1331
1586
  outer: for (const s of env.signatures) {
1332
1587
  let sig;
1333
1588
  try {
1334
- sig = base64ToBytes(s.sig);
1589
+ sig = base64ToBytes2(s.sig);
1335
1590
  } catch {
1336
1591
  continue;
1337
1592
  }
@@ -1382,6 +1637,8 @@ var ResolveInsufficientFundsError = class extends ResolveError {
1382
1637
  currency;
1383
1638
  /** pay.codai.ro checkout link for the shortfall — open it, then retry `accept()`. */
1384
1639
  topupUrl;
1640
+ /** Present only for a `t7` job: fix-bundle checkout (10 t7 fix credits for €49). */
1641
+ bundleUrl;
1385
1642
  constructor(message, body, meta = {}) {
1386
1643
  super(message, 402, body, meta);
1387
1644
  this.name = "ResolveInsufficientFundsError";
@@ -1389,6 +1646,7 @@ var ResolveInsufficientFundsError = class extends ResolveError {
1389
1646
  this.required = body.required;
1390
1647
  this.currency = body.currency;
1391
1648
  this.topupUrl = body.topup_url;
1649
+ if (typeof body.bundle_url === "string") this.bundleUrl = body.bundle_url;
1392
1650
  }
1393
1651
  };
1394
1652
  var Resolve = class {
@@ -1420,8 +1678,10 @@ var Resolve = class {
1420
1678
  }
1421
1679
  /**
1422
1680
  * `POST /v1/resolve/jobs/{id}/accept` — accept a paid quote and start the job.
1423
- * Throws `ResolveInsufficientFundsError` (402, carries `topupUrl`) when the
1424
- * wallet is short, `ResolveError` 409 when the job is not `quoted`.
1681
+ * The result's `paid_with` says how it was paid (`intro` €1 hold, `credit`
1682
+ * t7 fix credit, or `wallet`). Throws `ResolveInsufficientFundsError` (402,
1683
+ * carries `topupUrl`, plus `bundleUrl` for t7) when the wallet is short,
1684
+ * `ResolveError` 409 when the job is not `quoted`.
1425
1685
  */
1426
1686
  accept(id, opts = {}) {
1427
1687
  return this.call(`/v1/resolve/jobs/${encodeURIComponent(id)}/accept`, {
@@ -1446,6 +1706,10 @@ var Resolve = class {
1446
1706
  health(opts = {}) {
1447
1707
  return this.call("/health", { signal: opts.signal });
1448
1708
  }
1709
+ /** `GET /v1/resolve/balance` — fix credits (t7 only), intro availability and wallet balance. */
1710
+ balance(opts = {}) {
1711
+ return this.call("/v1/resolve/balance", { signal: opts.signal });
1712
+ }
1449
1713
  /** `GET /v1/resolve/keys` — public keys that sign attestations (no auth needed server-side). */
1450
1714
  keys(opts = {}) {
1451
1715
  return this.call("/v1/resolve/keys", { signal: opts.signal });
@@ -1511,7 +1775,7 @@ function toResolveError(path, err) {
1511
1775
  if (err.status === 402 && isInsufficientFunds(err.body)) {
1512
1776
  const b = err.body;
1513
1777
  return new ResolveInsufficientFundsError(
1514
- `codai-resolve ${path} \u2192 402: insufficient funds (balance ${b.balance}, required ${b.required} ${b.currency}); top up at ${b.topup_url}`,
1778
+ `codai-resolve ${path} \u2192 402: insufficient funds (balance ${b.balance}, required ${b.required} ${b.currency}); top up at ${b.topup_url}${b.bundle_url ? ` or buy 10 t7 fixes for \u20AC49 at ${b.bundle_url}` : ""}`,
1515
1779
  b,
1516
1780
  meta
1517
1781
  );
@@ -1807,7 +2071,10 @@ var Sessions = class {
1807
2071
  signal: opts.signal
1808
2072
  });
1809
2073
  }
1810
- /** `POST /v1/sessions/{id}/dispatch` — queue a `send` for one device and wake it over FCM. */
2074
+ /**
2075
+ * `POST /v1/sessions/{id}/dispatch` — queue a `send` for one device and wake it over FCM.
2076
+ * `{ mode: 'open' }` hands the session off instead: the target just opens it (no user turn).
2077
+ */
1811
2078
  dispatch(sessionId, body, opts = {}) {
1812
2079
  return this.http.json(`/v1/sessions/${enc(sessionId)}/dispatch`, {
1813
2080
  body,
@@ -1840,10 +2107,6 @@ var SystemOne = class {
1840
2107
  this.http = http;
1841
2108
  }
1842
2109
  http;
1843
- /**
1844
- * Ask one or more typed questions about `state`. Throws on 503 `s1_unavailable` like any other
1845
- * error — keep a local fallback and catch it: the gateway never substitutes a generative model.
1846
- */
1847
2110
  async create(body, opts = {}) {
1848
2111
  const res = await this.http.request("/v1/systemone", {
1849
2112
  body,
@@ -1852,6 +2115,10 @@ var SystemOne = class {
1852
2115
  });
1853
2116
  return await res.json();
1854
2117
  }
2118
+ /** Same questions about up to 16 states in one call; results come back in `items` order. */
2119
+ batch(body, opts = {}) {
2120
+ return this.create(body, opts);
2121
+ }
1855
2122
  };
1856
2123
 
1857
2124
  // src/resources/tasks.ts
@@ -1994,6 +2261,63 @@ var Notifications = class {
1994
2261
  }
1995
2262
  };
1996
2263
 
2264
+ // src/resources/prompts.ts
2265
+ var one = (id, suffix = "") => `/v1/prompts/${encodeURIComponent(id)}${suffix}`;
2266
+ var Prompts = class {
2267
+ constructor(http) {
2268
+ this.http = http;
2269
+ }
2270
+ http;
2271
+ /** `GET /v1/prompts?status=&limit=` — default `open`; `due` = open and `not_before` empty or passed. */
2272
+ list(query = {}, opts = {}) {
2273
+ return this.http.json("/v1/prompts", {
2274
+ query: { status: query.status, limit: query.limit },
2275
+ ext: opts.ext,
2276
+ signal: opts.signal
2277
+ });
2278
+ }
2279
+ /** `POST /v1/prompts` — idempotent on the text (`created: false` for a duplicate); `goal_key` supersedes older open ones. */
2280
+ create(body, opts = {}) {
2281
+ return this.http.json("/v1/prompts", {
2282
+ method: "POST",
2283
+ body,
2284
+ ext: opts.ext,
2285
+ signal: opts.signal
2286
+ });
2287
+ }
2288
+ /** `GET /v1/prompts/{id}`. */
2289
+ get(id, opts = {}) {
2290
+ return this.http.json(one(id), { ext: opts.ext, signal: opts.signal });
2291
+ }
2292
+ /** `PATCH /v1/prompts/{id}` — edit, snooze (`not_before`), close (`status: 'done' | 'dismissed'`). */
2293
+ update(id, body, opts = {}) {
2294
+ return this.http.json(one(id), {
2295
+ method: "PATCH",
2296
+ body,
2297
+ ext: opts.ext,
2298
+ signal: opts.signal
2299
+ });
2300
+ }
2301
+ /** `DELETE /v1/prompts/{id}` — `{ deleted: 0 }` when the id is missing or not yours. */
2302
+ delete(id, opts = {}) {
2303
+ return this.http.json(one(id), {
2304
+ method: "DELETE",
2305
+ ext: opts.ext,
2306
+ signal: opts.signal
2307
+ });
2308
+ }
2309
+ /** `POST /v1/prompts/{id}/launch` — new shared session + `send` control on a device; the prompt becomes `launched`. */
2310
+ launch(id, deviceId, opts = {}) {
2311
+ return this.http.json(one(id, "/launch"), {
2312
+ method: "POST",
2313
+ body: deviceId ? { device_id: deviceId } : {},
2314
+ ext: opts.ext,
2315
+ signal: opts.signal,
2316
+ noRetry: true
2317
+ });
2318
+ }
2319
+ };
2320
+
1997
2321
  // src/resources/tokens.ts
1998
2322
  var Tokens = class {
1999
2323
  constructor(http) {
@@ -2038,6 +2362,28 @@ var Tools = class {
2038
2362
  }
2039
2363
  };
2040
2364
 
2365
+ // src/resources/verify.ts
2366
+ var Verify = class {
2367
+ constructor(http) {
2368
+ this.http = http;
2369
+ }
2370
+ http;
2371
+ /** `GET /v1/verify/agent-output/key` — `{ enabled: false }` when signing is off. */
2372
+ agentOutputKey(opts = {}) {
2373
+ return this.http.json("/v1/verify/agent-output/key", { signal: opts.signal });
2374
+ }
2375
+ /** `POST /v1/verify/agent-output` — 503 `signing_disabled` when signing is off. */
2376
+ agentOutput(body, opts = {}) {
2377
+ return this.http.json("/v1/verify/agent-output", {
2378
+ method: "POST",
2379
+ body,
2380
+ signal: opts.signal,
2381
+ // 503 here means `signing_disabled`, not a transient outage.
2382
+ noRetry: true
2383
+ });
2384
+ }
2385
+ };
2386
+
2041
2387
  // src/operations.ts
2042
2388
  var OPERATION_METHODS = {
2043
2389
  // Chat & Completions
@@ -2046,9 +2392,12 @@ var OPERATION_METHODS = {
2046
2392
  createMessage: "messages.create",
2047
2393
  // Embeddings & Audio
2048
2394
  createEmbeddings: "embeddings.create",
2395
+ createImage: "images.generate",
2396
+ editImage: "images.edit",
2049
2397
  createSystemOne: "systemOne.create",
2050
2398
  createTranscription: "audio.transcribe",
2051
2399
  createSpeech: "audio.speech",
2400
+ createSpeechStream: "audio.speechStream",
2052
2401
  createEphemeralToken: "tokens.create",
2053
2402
  // Models
2054
2403
  listModels: "models.list",
@@ -2087,6 +2436,13 @@ var OPERATION_METHODS = {
2087
2436
  markNotificationsRead: "notifications.markRead",
2088
2437
  deleteNotification: "notifications.delete",
2089
2438
  deleteNotifications: "notifications.deleteMany",
2439
+ // Pending prompts
2440
+ listPrompts: "prompts.list",
2441
+ createPrompt: "prompts.create",
2442
+ getPrompt: "prompts.get",
2443
+ updatePrompt: "prompts.update",
2444
+ deletePrompt: "prompts.delete",
2445
+ launchPrompt: "prompts.launch",
2090
2446
  // Sessions
2091
2447
  createSession: "sessions.create",
2092
2448
  listSessions: "sessions.list",
@@ -2108,6 +2464,7 @@ var OPERATION_METHODS = {
2108
2464
  listDevices: "devices.list",
2109
2465
  updateDevice: "devices.update",
2110
2466
  deleteDevice: "devices.delete",
2467
+ revokeSelfKey: "devices.revokeSelfKey",
2111
2468
  // Hosts
2112
2469
  listHosts: "hosts.list",
2113
2470
  streamHost: "hosts.stream",
@@ -2150,6 +2507,9 @@ var OPERATION_METHODS = {
2150
2507
  listEnvironmentTasks: "environments.tasks.list",
2151
2508
  createEnvironmentTask: "environments.tasks.create",
2152
2509
  getEnvironmentTask: "environments.tasks.get",
2510
+ // Agent-output signatures (EXPERIMENTAL, HIDE)
2511
+ getAgentOutputKey: "verify.agentOutputKey",
2512
+ verifyAgentOutput: "verify.agentOutput",
2153
2513
  listEnvironmentPorts: "environments.ports.list",
2154
2514
  setEnvironmentPort: "environments.ports.set",
2155
2515
  removeEnvironmentPort: "environments.ports.remove",
@@ -2166,7 +2526,8 @@ var OPERATION_METHODS = {
2166
2526
  var STREAMING_OPERATIONS = /* @__PURE__ */ new Set([
2167
2527
  "streamAgentRun",
2168
2528
  "streamSession",
2169
- "streamHost"
2529
+ "streamHost",
2530
+ "createSpeechStream"
2170
2531
  ]);
2171
2532
  var RESOLVE_OPERATION_METHODS = {
2172
2533
  resolveHealth: "resolve.health",
@@ -2174,7 +2535,8 @@ var RESOLVE_OPERATION_METHODS = {
2174
2535
  getResolveJob: "resolve.get",
2175
2536
  acceptResolveJob: "resolve.accept",
2176
2537
  getResolveAttestation: "resolve.attestation",
2177
- getResolveKeys: "resolve.keys"
2538
+ getResolveKeys: "resolve.keys",
2539
+ getResolveBalance: "resolve.balance"
2178
2540
  };
2179
2541
 
2180
2542
  // src/index.ts
@@ -2185,10 +2547,14 @@ var Codai = class {
2185
2547
  messages;
2186
2548
  responses;
2187
2549
  embeddings;
2550
+ /** Image generation and editing (`images.generate({ prompt })`, `images.edit({ prompt, image })`; codai-image = gemini-3.1-flash-image, EU). */
2551
+ images;
2188
2552
  audio;
2189
2553
  /** Typed decisions from codai-s1 (`systemOne.create({ state, questions })`). */
2190
2554
  systemOne;
2191
2555
  tokens;
2556
+ /** WebSocket realtime sessions (`realtime.connect({ model, language, token })`) — live STT and voice. */
2557
+ realtime;
2192
2558
  models;
2193
2559
  health;
2194
2560
  agents;
@@ -2198,12 +2564,16 @@ var Codai = class {
2198
2564
  triggers;
2199
2565
  /** Inbox of trigger / cloud-task notifications. */
2200
2566
  notifications;
2567
+ /** Pending prompts — ready-to-paste prompts left for a future chat (handoffs, dated follow-ups). */
2568
+ prompts;
2201
2569
  sessions;
2202
2570
  devices;
2203
2571
  hosts;
2204
2572
  orgs;
2205
2573
  projects;
2206
2574
  environments;
2575
+ /** EXPERIMENTAL (HIDE, unaudited): verify signed agent outputs. Provenance only. */
2576
+ verify;
2207
2577
  account;
2208
2578
  receipt;
2209
2579
  feedback;
@@ -2230,21 +2600,25 @@ var Codai = class {
2230
2600
  const http = this.http;
2231
2601
  this.messages = new Messages(http);
2232
2602
  this.responses = new Responses(http);
2603
+ this.images = new Images(http);
2233
2604
  this.audio = new Audio(http);
2234
2605
  this.systemOne = new SystemOne(http);
2235
2606
  this.tokens = new Tokens(http);
2607
+ this.realtime = new Realtime({ baseUrl: http.baseUrl, apiKey: opts.apiKey });
2236
2608
  this.health = new Health(http);
2237
2609
  this.agents = new Agents(http);
2238
2610
  this.tools = new Tools(http);
2239
2611
  this.tasks = new Tasks(http);
2240
2612
  this.triggers = new Triggers(http);
2241
2613
  this.notifications = new Notifications(http);
2614
+ this.prompts = new Prompts(http);
2242
2615
  this.sessions = new Sessions(http);
2243
2616
  this.devices = new Devices(http);
2244
2617
  this.hosts = new Hosts(http);
2245
2618
  this.orgs = new Orgs(http);
2246
2619
  this.projects = new Projects(http);
2247
2620
  this.environments = new Environments(http);
2621
+ this.verify = new Verify(http);
2248
2622
  this.account = new Account(http);
2249
2623
  this.receipt = new Receipts(http);
2250
2624
  this.phoneModels = new PhoneModels(http);
@@ -2342,6 +2716,6 @@ function allKeys(obj) {
2342
2716
  }
2343
2717
  var index_default = Codai;
2344
2718
 
2345
- export { Account, AgentRuns, Agents, Audio, Chat, ChatCompletions, Codai, CodaiError, Devices, Embeddings, EnvironmentMembers, EnvironmentPorts, EnvironmentSecrets, EnvironmentTasks, Environments, Feedback, Health, Hosts, HttpClient, Messages, Models, Notifications, OPERATION_METHODS, OrgMembers, Orgs, PhoneModels, Projects, RESOLVE_ATTESTATION_PAYLOAD_TYPE, RESOLVE_OPERATION_METHODS, RESOLVE_TERMINAL_STATUSES, Receipts, Resolve, ResolveError, ResolveInsufficientFundsError, Responses, STREAMING_OPERATIONS, SessionControls, SessionEvents, SessionLease, SessionShares, Sessions, Tasks, Tokens, Tools, Triggers, index_default as default, extensionHeaders, frameJson, mergeToolCall, readSse, resolveAttestationStatement, verifyAttestationWithKeys, verifyResolveWebhook };
2719
+ export { Account, AgentRuns, Agents, Audio, Chat, ChatCompletions, Codai, CodaiError, Devices, Embeddings, EnvironmentMembers, EnvironmentPorts, EnvironmentSecrets, EnvironmentTasks, Environments, Feedback, Health, Hosts, HttpClient, Images, Messages, Models, Notifications, OPERATION_METHODS, OrgMembers, Orgs, PhoneModels, Projects, Prompts, RESOLVE_ATTESTATION_PAYLOAD_TYPE, RESOLVE_OPERATION_METHODS, RESOLVE_TERMINAL_STATUSES, Realtime, RealtimeSession, Receipts, Resolve, ResolveError, ResolveInsufficientFundsError, Responses, STREAMING_OPERATIONS, SessionControls, SessionEvents, SessionLease, SessionShares, Sessions, SystemOne, Tasks, Tokens, Tools, Triggers, Verify, index_default as default, extensionHeaders, frameJson, mergeToolCall, readSse, realtimeUrl, resolveAttestationStatement, verifyAttestationWithKeys, verifyResolveWebhook };
2346
2720
  //# sourceMappingURL=index.js.map
2347
2721
  //# sourceMappingURL=index.js.map