@jeffusion/bungee-core 5.16.0 → 5.18.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.
Files changed (52) hide show
  1. package/dist/config-publication/worker-runtime-contract.d.ts +1 -1
  2. package/dist/config-storage/gateway-target-validation.d.ts +5 -0
  3. package/dist/config-worker/lifecycle.d.ts +6 -0
  4. package/dist/data-admission/worker.d.ts +1 -0
  5. package/dist/gateway/contracts.d.ts +1 -1
  6. package/dist/gateway/plugin.d.ts +1 -0
  7. package/dist/gateway/plugin.js +15 -1
  8. package/dist/gateway/runtime.d.ts +2 -0
  9. package/dist/gateway/websocket-contracts.d.ts +62 -0
  10. package/dist/gateway/websocket-credential.d.ts +3 -0
  11. package/dist/gateway/websocket-plugin.d.ts +9 -0
  12. package/dist/hooks/plugin-hooks.d.ts +8 -0
  13. package/dist/logger/access-log-writer.d.ts +1 -1
  14. package/dist/main.js +4326 -128
  15. package/dist/plugin.types.d.ts +1 -1
  16. package/dist/plugins/ai-transformer/index.js.map +2 -2
  17. package/dist/plugins/anthropic-request-sanitizer/index.js.map +2 -2
  18. package/dist/plugins/anthropic-tool-name-transformer/index.js.map +2 -2
  19. package/dist/plugins/chatgpt-oauth/index.js +12 -4
  20. package/dist/plugins/chatgpt-oauth/index.js.map +5 -5
  21. package/dist/plugins/chatgpt-oauth/manifest.json +41 -0
  22. package/dist/plugins/codex-router/control.js +49 -0
  23. package/dist/plugins/codex-router/control.js.map +11 -0
  24. package/dist/plugins/codex-router/index.js +318 -0
  25. package/dist/plugins/codex-router/index.js.map +27 -0
  26. package/dist/plugins/codex-router/manifest.json +149 -0
  27. package/dist/plugins/deepseek-reasoning-fix/index.js.map +2 -2
  28. package/dist/plugins/key-access/index.js.map +2 -2
  29. package/dist/plugins/key-rate-limit/index.js.map +2 -2
  30. package/dist/plugins/local-accounts/index.js.map +2 -2
  31. package/dist/plugins/model-mapping/control.js.map +1 -1
  32. package/dist/plugins/model-mapping/index.js.map +3 -3
  33. package/dist/plugins/models-dev/control.js +24 -1
  34. package/dist/plugins/models-dev/control.js.map +5 -5
  35. package/dist/plugins/models-dev/index.js +24 -1
  36. package/dist/plugins/models-dev/index.js.map +6 -6
  37. package/dist/plugins/models-dev/manifest.json +12 -0
  38. package/dist/plugins/openai-messages-to-chat/index.js.map +2 -2
  39. package/dist/plugins/signature-repair/index.js.map +2 -2
  40. package/dist/plugins/token-budget/index.js.map +2 -2
  41. package/dist/plugins/token-metering/index.js +225 -3
  42. package/dist/plugins/token-metering/index.js.map +6 -5
  43. package/dist/plugins/token-stats/control.js.map +1 -1
  44. package/dist/plugins/token-stats/index.js.map +3 -3
  45. package/dist/public-listener/websocket.d.ts +4 -0
  46. package/dist/scoped-plugin-registry.d.ts +12 -0
  47. package/dist/websocket/headers.d.ts +9 -0
  48. package/dist/websocket/index.d.ts +3 -0
  49. package/dist/websocket/message.d.ts +3 -0
  50. package/dist/websocket/observation.d.ts +17 -0
  51. package/dist/websocket/transport.d.ts +77 -0
  52. package/package.json +4 -2
@@ -278,6 +278,31 @@
278
278
  }
279
279
  }
280
280
  },
281
+ {
282
+ "pathname": "/backend-api/codex/responses",
283
+ "methods": [
284
+ "GET"
285
+ ],
286
+ "outboundHeaders": {
287
+ "passthrough": [
288
+ "Version",
289
+ "X-Codex-Beta-Features",
290
+ "X-Codex-Turn-Metadata",
291
+ "X-Client-Request-Id",
292
+ "X-Codex-Window-Id",
293
+ "Thread-Id",
294
+ "Session-Id",
295
+ "X-Codex-Routing-Hint",
296
+ "X-OpenAI-Internal-Codex-Responses-Lite",
297
+ "OpenAI-Beta",
298
+ "Origin"
299
+ ],
300
+ "set": {
301
+ "User-Agent": "codex-tui/0.154.0 (Mac OS 26.5.2; arm64) iTerm.app/3.6.11 (codex-tui; 0.154.0)",
302
+ "Originator": "codex-tui"
303
+ }
304
+ }
305
+ },
281
306
  {
282
307
  "pathname": "/backend-api/codex/models",
283
308
  "methods": [
@@ -324,6 +349,22 @@
324
349
  }
325
350
  }
326
351
  },
352
+ {
353
+ "pathname": "/v1/responses",
354
+ "methods": [
355
+ "GET"
356
+ ],
357
+ "outboundHeaders": {
358
+ "passthrough": [
359
+ "OpenAI-Beta",
360
+ "Origin"
361
+ ],
362
+ "set": {
363
+ "User-Agent": "Bungee/5.11.0",
364
+ "Originator": "Bungee"
365
+ }
366
+ }
367
+ },
327
368
  {
328
369
  "pathname": "/v1/models",
329
370
  "methods": [
@@ -0,0 +1,49 @@
1
+ // @bun
2
+ // plugins/models-dev/contract.ts
3
+ var MODELS_DEV_CATALOG_SERVICE_ID = "models-dev.catalog.v1";
4
+ var MODELS_DEV_CATALOG_CONTRACT_VERSION = 1;
5
+ var MODELS_DEV_CATALOG_SNAPSHOT_ID = "models-dev.catalog.snapshot.v1";
6
+ var MODELS_DEV_CATALOG_SNAPSHOT_CONTRACT_VERSION = 1;
7
+ var MODELS_DEV_CATALOG_SNAPSHOT_SCHEMA = Object.freeze({
8
+ type: "object",
9
+ properties: {
10
+ version: { type: "number", integer: true, minimum: 1 },
11
+ fetchedAt: { type: "number", minimum: 0 },
12
+ catalog: { type: "json", maxBytes: 32 * 1024 * 1024 }
13
+ }
14
+ });
15
+ var MODELS_DEV_CATALOG_SNAPSHOT_CONTRACT = Object.freeze({
16
+ id: MODELS_DEV_CATALOG_SNAPSHOT_ID,
17
+ version: MODELS_DEV_CATALOG_SNAPSHOT_CONTRACT_VERSION,
18
+ content: MODELS_DEV_CATALOG_SNAPSHOT_SCHEMA
19
+ });
20
+ var MODELS_DEV_CAPABILITIES_SERVICE_ID = "models-dev.capabilities.v1";
21
+ var MODELS_DEV_CAPABILITIES_CONTRACT_VERSION = 1;
22
+
23
+ // plugins/codex-router/server/control.ts
24
+ function createControl(host) {
25
+ return {
26
+ rpc: [],
27
+ start() {},
28
+ async dispose() {},
29
+ api: [{ path: "/catalog", methods: ["GET"], handler: "getCatalog", invoke: async ({ request }) => {
30
+ if (host.signal.aborted)
31
+ return Response.json({ error: "inactive" }, { status: 503 });
32
+ const params = new URL(request.url).searchParams;
33
+ const page = Number(params.get("page") ?? 1);
34
+ if (!Number.isSafeInteger(page) || page < 1 || page > 400 || ["provider", "search", "page"].some((key) => params.getAll(key).length > 1 || (params.get(key)?.length ?? 0) > 512))
35
+ return Response.json({ error: "invalid_query" }, { status: 400 });
36
+ const catalog = host.services.consume("models-dev", MODELS_DEV_CATALOG_SERVICE_ID, MODELS_DEV_CATALOG_CONTRACT_VERSION);
37
+ const capabilities = host.services.consume("models-dev", MODELS_DEV_CAPABILITIES_SERVICE_ID, MODELS_DEV_CAPABILITIES_CONTRACT_VERSION);
38
+ const result = catalog.modelOptions({ provider: params.get("provider") ?? undefined, search: params.get("search") ?? undefined, page, pageSize: 50 });
39
+ return Response.json({ ...result, providers: catalog.providers(), status: catalog.status(), models: result.models.map((model) => ({ ...model, capabilities: capabilities.model(model) })) });
40
+ } }]
41
+ };
42
+ }
43
+ var control_default = { createControl };
44
+ export {
45
+ createControl,
46
+ control_default as default
47
+ };
48
+
49
+ //# debugId=6F6F6C474F066F0964756E2164756E21
@@ -0,0 +1,11 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../../../plugins/models-dev/contract.ts", "../../../../../plugins/codex-router/server/control.ts"],
4
+ "sourcesContent": [
5
+ "/**\n * Public contract of the models-dev catalog provider.\n *\n * This is the ONLY file other plugins may import from models-dev. It contains the\n * declared service identity, the wire-contract snapshot literal and the data types\n * of the read surface; it never exposes the downloader, the private storage keys or\n * the internal catalog representation.\n *\n * Consumers must declare a real dependency on `models-dev` and consume the local\n * service for their own process. The service methods are synchronous and read an\n * already-loaded in-memory view: no per-request network or SQL is performed.\n */\n\n/** Provider plugin name. Must match the manifest. */\nexport const MODELS_DEV_PLUGIN_NAME = 'models-dev';\n\n/** The single upstream source; models-dev is the only component allowed to fetch it. */\nexport const MODELS_DEV_SOURCE_URL = 'https://models.dev/api.json';\n\n/** Same-process local read service, published in both the control and worker processes. */\nexport const MODELS_DEV_CATALOG_SERVICE_ID = 'models-dev.catalog.v1';\nexport const MODELS_DEV_CATALOG_CONTRACT_VERSION = 1;\n\n/** Versioned immutable snapshot of the full catalog, published by the control writer. */\nexport const MODELS_DEV_CATALOG_SNAPSHOT_ID = 'models-dev.catalog.snapshot.v1';\nexport const MODELS_DEV_CATALOG_SNAPSHOT_CONTRACT_VERSION = 1;\n/**\n * One atomic record keeps fetchedAt and the immutable catalog with its version.\n * The catalog remains unrestricted JSON so every upstream field is preserved.\n */\nexport const MODELS_DEV_CATALOG_SNAPSHOT_SCHEMA = Object.freeze({\n type: 'object', properties: {\n version: { type: 'number', integer: true, minimum: 1 },\n fetchedAt: { type: 'number', minimum: 0 },\n catalog: { type: 'json', maxBytes: 32 * 1024 * 1024 },\n },\n} as const);\nexport const MODELS_DEV_CATALOG_SNAPSHOT_CONTRACT = Object.freeze({\n id: MODELS_DEV_CATALOG_SNAPSHOT_ID,\n version: MODELS_DEV_CATALOG_SNAPSHOT_CONTRACT_VERSION,\n content: MODELS_DEV_CATALOG_SNAPSHOT_SCHEMA,\n});\n\n/** Catalog availability is separate from whether the service is published. */\nexport type ModelsDevCatalogState = 'empty' | 'ready' | 'stale' | 'failed';\n\nexport interface ModelsDevCatalogStatus {\n readonly state: ModelsDevCatalogState;\n /** Monotonic published data version; `null` before the first successful load. */\n readonly version: number | null;\n readonly fetchedAt: number | null;\n readonly providerCount: number;\n readonly modelCount: number;\n /** Last failure reason; `null` after a fully successful load. */\n readonly error: string | null;\n}\n\nexport interface ModelsDevProviderSummary {\n readonly provider: string;\n readonly name: string;\n /** Normalized upstream API base (`provider.api`), or `null` when models.dev declares none. */\n readonly api: string | null;\n readonly modelCount: number;\n}\n\n/** One selectable catalog model. `provider` is the pricing provider, never the protocol. */\nexport interface ModelsDevModelOption {\n readonly provider: string;\n readonly providerName: string;\n readonly model: string;\n readonly name: string;\n}\n\nexport interface ModelsDevModelPage {\n readonly models: readonly ModelsDevModelOption[];\n readonly total: number;\n /** 1-based page actually returned. */\n readonly page: number;\n readonly pageSize: number;\n}\n\n/** USD per million tokens, applied to the whole request at this input threshold. */\nexport interface ModelsDevContextTier {\n readonly minimumInputTokens: number;\n readonly input: number;\n readonly output: number;\n readonly cacheRead: number | null;\n readonly cacheWrite: number | null;\n}\n\n/** A resolved catalog entry with optional ascending context price bands. */\nexport interface ModelsDevModelMatch {\n readonly provider: string;\n readonly model: string;\n readonly input: number;\n readonly output: number;\n readonly cacheRead: number | null;\n readonly cacheWrite: number | null;\n readonly tiered: boolean;\n readonly contextTiers?: readonly ModelsDevContextTier[];\n}\n\nexport interface ModelsDevProviderMatch {\n readonly provider: string;\n}\n\n/**\n * The declared local read surface. Implementations must be side-effect free and\n * must never throw for a miss/corruption of the current view: an unavailable\n * catalog returns an `empty`/`failed` status instead of a fabricated price.\n */\nexport interface ModelsDevCatalogService {\n status(): ModelsDevCatalogStatus;\n providers(): readonly ModelsDevProviderSummary[];\n modelOptions(input?: { readonly provider?: string; readonly search?: string; readonly page?: number; readonly pageSize?: number }): ModelsDevModelPage;\n /**\n * Resolve exactly one catalog entry for a client model name.\n *\n * `url` (when supplied) is canonicalized to host + path and matched against the\n * full catalog's `provider.api`; more than one candidate is ambiguous and returns\n * null. `pricingProvider` is a catalog provider id and takes priority over URL and\n * prefix inference. A model id present under several providers without an explicit\n * provider is ambiguous. Matching defaults to exact and case-sensitive.\n * `estimate` additionally permits normalized names, original-lab prices and\n * dated members of the same family. Explicit provider IDs remain binding;\n * an unresolved URL is only a hint in estimate mode.\n */\n resolveModel(input: { readonly model: string; readonly pricingProvider?: string; readonly url?: string; readonly mode?: 'exact' | 'estimate' }): ModelsDevModelMatch | null;\n /** Resolve one provider from a real upstream URL via `provider.api`; ambiguous/none => null. */\n resolveProvider(input: { readonly url: string }): ModelsDevProviderMatch | null;\n}\n\n/** Capability reads are additive; existing catalog.v1 consumers stay unchanged. */\nexport const MODELS_DEV_CAPABILITIES_SERVICE_ID = 'models-dev.capabilities.v1';\nexport const MODELS_DEV_CAPABILITIES_CONTRACT_VERSION = 1;\nexport interface ModelsDevCapabilities {\n readonly provider: string;\n readonly model: string;\n readonly name: string;\n readonly contextWindow: number | null;\n readonly outputLimit: number | null;\n readonly toolCall: boolean;\n readonly reasoning: boolean;\n readonly inputModalities: readonly string[];\n}\nexport interface ModelsDevCapabilitiesService {\n status(): ModelsDevCatalogStatus;\n model(input: { readonly provider: string; readonly model: string }): ModelsDevCapabilities | null;\n}\n",
6
+ "import type { ControlHostContext, PluginControl, ControlPlugin } from '@jeffusion/bungee-core/plugin';\nimport { MODELS_DEV_CATALOG_SERVICE_ID, MODELS_DEV_CATALOG_CONTRACT_VERSION, MODELS_DEV_CAPABILITIES_SERVICE_ID, MODELS_DEV_CAPABILITIES_CONTRACT_VERSION, type ModelsDevCatalogService, type ModelsDevCapabilitiesService } from '../../models-dev/contract';\nexport function createControl(host: ControlHostContext): PluginControl {\n return {\n rpc:[], start() {}, async dispose() {},\n api:[{path:'/catalog', methods:['GET'], handler:'getCatalog', invoke:async ({request}) => {\n if (host.signal.aborted) return Response.json({error:'inactive'},{status:503});\n const params = new URL(request.url).searchParams;\n const page = Number(params.get('page') ?? 1);\n if (!Number.isSafeInteger(page) || page < 1 || page > 400\n || ['provider','search','page'].some(key => params.getAll(key).length > 1 || (params.get(key)?.length ?? 0) > 512)) return Response.json({error:'invalid_query'},{status:400});\n const catalog = host.services!.consume<ModelsDevCatalogService>('models-dev',MODELS_DEV_CATALOG_SERVICE_ID,MODELS_DEV_CATALOG_CONTRACT_VERSION);\n const capabilities = host.services!.consume<ModelsDevCapabilitiesService>('models-dev',MODELS_DEV_CAPABILITIES_SERVICE_ID,MODELS_DEV_CAPABILITIES_CONTRACT_VERSION);\n const result = catalog.modelOptions({provider:params.get('provider') ?? undefined,search:params.get('search') ?? undefined,page,pageSize:50});\n return Response.json({...result,providers:catalog.providers(),status:catalog.status(),models:result.models.map(model => ({...model,capabilities:capabilities.model(model)}))});\n }}],\n };\n}\nexport default {createControl} satisfies ControlPlugin;\n"
7
+ ],
8
+ "mappings": ";;AAoBO,IAAM,gCAAgC;AACtC,IAAM,sCAAsC;AAG5C,IAAM,iCAAiC;AACvC,IAAM,+CAA+C;AAKrD,IAAM,qCAAqC,OAAO,OAAO;AAAA,EAC9D,MAAM;AAAA,EAAU,YAAY;AAAA,IAC1B,SAAS,EAAE,MAAM,UAAU,SAAS,MAAM,SAAS,EAAE;AAAA,IACrD,WAAW,EAAE,MAAM,UAAU,SAAS,EAAE;AAAA,IACxC,SAAS,EAAE,MAAM,QAAQ,UAAU,KAAK,OAAO,KAAK;AAAA,EACtD;AACF,CAAU;AACH,IAAM,uCAAuC,OAAO,OAAO;AAAA,EAChE,IAAI;AAAA,EACJ,SAAS;AAAA,EACT,SAAS;AACX,CAAC;AA4FM,IAAM,qCAAqC;AAC3C,IAAM,2CAA2C;;;ACpIjD,SAAS,aAAa,CAAC,MAAyC;AAAA,EACrE,OAAO;AAAA,IACL,KAAI,CAAC;AAAA,IAAG,KAAK,GAAG;AAAA,SAAU,QAAO,GAAG;AAAA,IACpC,KAAI,CAAC,EAAC,MAAK,YAAY,SAAQ,CAAC,KAAK,GAAG,SAAQ,cAAc,QAAO,SAAQ,cAAa;AAAA,MACxF,IAAI,KAAK,OAAO;AAAA,QAAS,OAAO,SAAS,KAAK,EAAC,OAAM,WAAU,GAAE,EAAC,QAAO,IAAG,CAAC;AAAA,MAC7E,MAAM,SAAS,IAAI,IAAI,QAAQ,GAAG,EAAE;AAAA,MACpC,MAAM,OAAO,OAAO,OAAO,IAAI,MAAM,KAAK,CAAC;AAAA,MAC3C,IAAI,CAAC,OAAO,cAAc,IAAI,KAAK,OAAO,KAAK,OAAO,OACjD,CAAC,YAAW,UAAS,MAAM,EAAE,KAAK,SAAO,OAAO,OAAO,GAAG,EAAE,SAAS,MAAM,OAAO,IAAI,GAAG,GAAG,UAAU,KAAK,GAAG;AAAA,QAAG,OAAO,SAAS,KAAK,EAAC,OAAM,gBAAe,GAAE,EAAC,QAAO,IAAG,CAAC;AAAA,MAC/K,MAAM,UAAU,KAAK,SAAU,QAAiC,cAAa,+BAA8B,mCAAmC;AAAA,MAC9I,MAAM,eAAe,KAAK,SAAU,QAAsC,cAAa,oCAAmC,wCAAwC;AAAA,MAClK,MAAM,SAAS,QAAQ,aAAa,EAAC,UAAS,OAAO,IAAI,UAAU,KAAK,WAAU,QAAO,OAAO,IAAI,QAAQ,KAAK,WAAU,MAAK,UAAS,GAAE,CAAC;AAAA,MAC5I,OAAO,SAAS,KAAK,KAAI,QAAO,WAAU,QAAQ,UAAU,GAAE,QAAO,QAAQ,OAAO,GAAE,QAAO,OAAO,OAAO,IAAI,YAAU,KAAI,OAAM,cAAa,aAAa,MAAM,KAAK,EAAC,EAAE,EAAC,CAAC;AAAA,MAC9K,CAAC;AAAA,EACJ;AAAA;AAEF,IAAe,oBAAC,cAAa;",
9
+ "debugId": "6F6F6C474F066F0964756E2164756E21",
10
+ "names": []
11
+ }
@@ -0,0 +1,318 @@
1
+ // @bun
2
+ // packages/core/src/plugin-logger.ts
3
+ var sinkKey = Symbol.for("@jeffusion/bungee/plugin-log-sink");
4
+ function createLogger(bindings = {}) {
5
+ const method = (level) => (value, message) => {
6
+ const sink = globalThis[sinkKey];
7
+ if (sink) {
8
+ if (typeof value === "string")
9
+ sink[level](bindings, value);
10
+ else
11
+ sink[level]({ ...bindings, ...value }, message);
12
+ } else if (level !== "debug" || process.env.LOG_LEVEL === "debug") {
13
+ const write = level === "fatal" ? console.error : console[level];
14
+ write(message ?? (typeof value === "string" ? value : ""), typeof value === "string" ? bindings : { ...bindings, ...value });
15
+ }
16
+ };
17
+ return {
18
+ info: method("info"),
19
+ warn: method("warn"),
20
+ error: method("error"),
21
+ debug: method("debug"),
22
+ fatal: method("fatal"),
23
+ child: (extra) => createLogger({ ...bindings, ...extra })
24
+ };
25
+ }
26
+ var logger = createLogger();
27
+
28
+ // packages/core/src/hooks/impl.ts
29
+ var WATERFALL_VIEW_TRANSFORM = Symbol("waterfall-view-transform");
30
+ // packages/core/src/plugin.types.ts
31
+ function definePlugin(plugin) {
32
+ return plugin;
33
+ }
34
+ // packages/core/src/plugin-extensions.ts
35
+ var ANONYMOUS_PRINCIPAL = Object.freeze({ domain: "anonymous", keyId: "", credentialVersion: 0 });
36
+ // packages/core/src/plugin-durable-state.ts
37
+ var MAX_BYTES = 1024 * 1024;
38
+ // packages/core/src/plugin-services/host-rpc.ts
39
+ import { AsyncLocalStorage } from "async_hooks";
40
+
41
+ // packages/core/src/plugin-services/wire-contract.ts
42
+ var RPC_JSON_MAX_BYTES = 64 * 1024;
43
+ var RPC_CONTRACT_MAX_BYTES = 256 * 1024;
44
+ var RPC_CALL_PURPOSES = new Set(["bootstrap", "background", "management", "request", "attempt"]);
45
+ var RPC_COMMAND_DEDUPLICATION = new Set(["local-transaction", "external-contract", "none"]);
46
+ var RPC_COMMAND_POLICY_KEYS = new Set(["deduplication", "resultRetentionMs", "quotaBytes", "maxResultBytes"]);
47
+
48
+ // packages/core/src/plugin-services/rpc-runtime.ts
49
+ var PROCESSES = new Set(["control", "worker", "ingress"]);
50
+ var SCOPES = new Set(["global", "binding"]);
51
+ var PURPOSES = new Set(["bootstrap", "background", "management", "request", "attempt"]);
52
+ var ENDPOINTS = new WeakMap;
53
+ var REVOKED = new WeakMap;
54
+
55
+ // packages/core/src/plugin-services/host-rpc.ts
56
+ var SERVICE_ERROR_MESSAGES = {
57
+ unauthorized: "RPC call is not authorized",
58
+ not_ready: "RPC endpoint is not ready",
59
+ retired: "RPC endpoint is retiring",
60
+ revoked: "RPC endpoint generation was revoked",
61
+ unsupported_method: "RPC method is not published",
62
+ wrong_purpose: "RPC method is not published for this purpose",
63
+ invalid_input: "RPC input is not valid",
64
+ invalid_output: "RPC output is not valid",
65
+ invalid_operation_id: "RPC command operation id is invalid",
66
+ overloaded: "RPC runtime is at capacity",
67
+ cancelled: "RPC call was cancelled",
68
+ timeout: "RPC call deadline exceeded",
69
+ unknown: "RPC command outcome is unknown",
70
+ capability_unavailable: "RPC command execution is unavailable",
71
+ closed: "RPC runtime is closed",
72
+ failed: "RPC call failed",
73
+ conflict: "RPC command identity conflicts with an existing record",
74
+ expired: "RPC command result has expired",
75
+ pending: "RPC command is still pending",
76
+ rejected: "RPC command was rejected",
77
+ missing: "RPC command has no stored result",
78
+ storage_failure: "RPC command storage failed",
79
+ deadlock: "RPC call chain would deadlock",
80
+ call_depth_exceeded: "RPC call depth exceeded",
81
+ undeclared: "RPC service is not declared by the manifest",
82
+ unavailable: "RPC service is unavailable",
83
+ ambiguous_placement: "RPC service placement is ambiguous",
84
+ invalid_registration: "RPC registration is invalid"
85
+ };
86
+ var SERVICE_ERROR_CODES = new Set(Object.keys(SERVICE_ERROR_MESSAGES));
87
+ var EMPTY_OPTIONS = Object.freeze({});
88
+ var FRAME_STORE = new AsyncLocalStorage;
89
+ var CALLEE_INFO = new WeakMap;
90
+ // packages/core/src/plugin-services/peer-channel-protocol.ts
91
+ var CHANNEL_REQUEST_MAX_BYTES = 4 * 1024;
92
+ var CHANNEL_RESULT_MAX_BYTES = 60 * 1024;
93
+ var CHANNEL_MAX_CHUNK_BYTES = 60 * 1024;
94
+ var PLUGIN_CHANNEL_LANES = Object.freeze(["event", "snapshot", "stream"]);
95
+ var ERROR_CODES = new Set([
96
+ "unavailable",
97
+ "ambiguous",
98
+ "unauthorized",
99
+ "invalid",
100
+ "overloaded",
101
+ "expired",
102
+ "conflict",
103
+ "gap",
104
+ "truncated",
105
+ "rejected",
106
+ "cancelled",
107
+ "closed",
108
+ "unknown",
109
+ "failed"
110
+ ]);
111
+ var RPC_CALL_PURPOSES2 = new Set(["bootstrap", "background", "management", "request", "attempt"]);
112
+
113
+ // packages/core/src/plugin-services/peer-channel-hub.ts
114
+ var CHANNEL_MAX_TRANSFER_BUFFER_BYTES = 4 * CHANNEL_MAX_CHUNK_BYTES;
115
+ var CHANNEL_MAX_TOTAL_BUFFER_BYTES = 16 * CHANNEL_MAX_CHUNK_BYTES;
116
+ var CHANNEL_STREAM_MAX_TOTAL_BYTES = 64 * 1024 * 1024;
117
+ var CHANNEL_STREAM_MAX_CREDIT_BYTES = 8 * CHANNEL_MAX_CHUNK_BYTES;
118
+ var CHANNEL_STREAM_DEFAULT_CREDIT_BYTES = 4 * CHANNEL_MAX_CHUNK_BYTES;
119
+ var CHANNEL_SNAPSHOT_MAX_BYTES = 64 * 1024 * 1024;
120
+ var CHANNEL_EVENT_MAX_PAYLOAD_BYTES = 60 * 1024;
121
+ var EMPTY = new Uint8Array(0);
122
+ var HANDLE_REGISTRATIONS = new WeakMap;
123
+
124
+ // packages/core/src/plugin-services/snapshot-store.ts
125
+ var DEFAULT_CHUNK_BYTES = 60 * 1024;
126
+ var SNAPSHOT_FAMILY_REFS = new Map;
127
+
128
+ // packages/core/src/plugin-services.ts
129
+ var CHANNEL_KINDS = new Set(["events", "snapshot", "stream"]);
130
+ // packages/core/src/gateway/retry-action.ts
131
+ var retryActionBrand = Symbol.for("@jeffusion/bungee/request-retry-action");
132
+ // packages/core/src/token-stats-window.ts
133
+ var HOUR = 3600000;
134
+ var TOKEN_STATS_RETENTION_MS = 31 * 24 * HOUR;
135
+ // plugins/models-dev/contract.ts
136
+ var MODELS_DEV_CATALOG_SNAPSHOT_ID = "models-dev.catalog.snapshot.v1";
137
+ var MODELS_DEV_CATALOG_SNAPSHOT_CONTRACT_VERSION = 1;
138
+ var MODELS_DEV_CATALOG_SNAPSHOT_SCHEMA = Object.freeze({
139
+ type: "object",
140
+ properties: {
141
+ version: { type: "number", integer: true, minimum: 1 },
142
+ fetchedAt: { type: "number", minimum: 0 },
143
+ catalog: { type: "json", maxBytes: 32 * 1024 * 1024 }
144
+ }
145
+ });
146
+ var MODELS_DEV_CATALOG_SNAPSHOT_CONTRACT = Object.freeze({
147
+ id: MODELS_DEV_CATALOG_SNAPSHOT_ID,
148
+ version: MODELS_DEV_CATALOG_SNAPSHOT_CONTRACT_VERSION,
149
+ content: MODELS_DEV_CATALOG_SNAPSHOT_SCHEMA
150
+ });
151
+ var MODELS_DEV_CAPABILITIES_SERVICE_ID = "models-dev.capabilities.v1";
152
+ var MODELS_DEV_CAPABILITIES_CONTRACT_VERSION = 1;
153
+
154
+ // plugins/codex-router/server/config.ts
155
+ function parseBindings(value) {
156
+ if (value === undefined)
157
+ return [];
158
+ if (!Array.isArray(value) || value.length > 100)
159
+ throw new Error("codex_router_invalid_bindings");
160
+ const ids = new Set;
161
+ return Object.freeze(value.map((entry) => {
162
+ if (!entry || typeof entry !== "object" || Array.isArray(entry) || Object.keys(entry).some((key) => !["provider", "model", "alias", "target", "capabilityOverrides"].includes(key)))
163
+ throw new Error("codex_router_invalid_bindings");
164
+ for (const text of [entry.provider, entry.model, ...entry.alias === undefined ? [] : [entry.alias]]) {
165
+ if (typeof text !== "string" || !text || text !== text.trim() || text.length > 512 || /[\x00-\x1f\x7f]/.test(text))
166
+ throw new Error("codex_router_invalid_bindings");
167
+ }
168
+ const target = entry.target;
169
+ if (!target || !["route", "service"].includes(target.type) || typeof target.id !== "string" || !target.id || Object.keys(target).some((key) => !["type", "id"].includes(key)))
170
+ throw new Error("codex_router_invalid_target");
171
+ const publicId = entry.alias ?? entry.model;
172
+ if (ids.has(publicId))
173
+ throw new Error("codex_router_model_conflict");
174
+ ids.add(publicId);
175
+ const overrides = entry.capabilityOverrides;
176
+ if (overrides !== undefined) {
177
+ if (!overrides || typeof overrides !== "object" || Array.isArray(overrides))
178
+ throw new Error("codex_router_invalid_capabilities");
179
+ for (const [key, val] of Object.entries(overrides)) {
180
+ if (key === "contextWindow" ? typeof val !== "number" || !Number.isSafeInteger(val) || val < 1 : !["tools", "reasoning", "images"].includes(key) || typeof val !== "boolean")
181
+ throw new Error("codex_router_invalid_capabilities");
182
+ }
183
+ }
184
+ return Object.freeze(structuredClone(entry));
185
+ }));
186
+ }
187
+
188
+ // plugins/codex-router/server/catalog.ts
189
+ import { createHash } from "crypto";
190
+ // plugins/codex-router/server/model-template-0.160.1.json
191
+ var model_template_0_160_1_default = {
192
+ shell_type: "unified_exec",
193
+ visibility: "list",
194
+ supported_in_api: true,
195
+ default_reasoning_summary: "none",
196
+ support_verbosity: true,
197
+ default_verbosity: "low",
198
+ apply_patch_tool_type: "freeform",
199
+ truncation_policy: {
200
+ mode: "tokens",
201
+ limit: 1e4
202
+ },
203
+ effective_context_window_percent: 95,
204
+ input_modalities: [
205
+ "text",
206
+ "image"
207
+ ],
208
+ slug: "",
209
+ display_name: "",
210
+ description: "",
211
+ priority: 100,
212
+ default_reasoning_level: "none",
213
+ supported_reasoning_levels: [],
214
+ base_instructions: "",
215
+ supports_search_tool: false,
216
+ supports_parallel_tool_calls: false,
217
+ supports_image_detail_original: false,
218
+ supports_reasoning_effort_updates: false,
219
+ use_responses_lite: false,
220
+ multi_agent_version: "v1",
221
+ additional_speed_tiers: [],
222
+ service_tiers: []
223
+ };
224
+
225
+ // plugins/codex-router/server/catalog.ts
226
+ function mergeCatalog(native, bindings, catalog) {
227
+ if (!native || typeof native !== "object" || Array.isArray(native))
228
+ throw new Error("codex_router_invalid_catalog");
229
+ const body = native;
230
+ const rich = Array.isArray(body.models);
231
+ if (!rich && !Array.isArray(body.data))
232
+ throw new Error("codex_router_invalid_catalog");
233
+ const existing = rich ? body.models : body.data;
234
+ const ids = new Set(existing.map((entry) => rich ? entry.slug : entry.id));
235
+ const added = [];
236
+ for (const binding of bindings) {
237
+ const id = binding.alias ?? binding.model;
238
+ if (ids.has(id))
239
+ throw new Error("codex_router_model_conflict");
240
+ ids.add(id);
241
+ const info = catalog.model(binding);
242
+ if (!info || info.contextWindow === null || !info.inputModalities.includes("text"))
243
+ continue;
244
+ if (!rich) {
245
+ added.push({ id, object: "model", owned_by: binding.provider });
246
+ continue;
247
+ }
248
+ const overrides = binding.capabilityOverrides;
249
+ const context = Math.min(info.contextWindow, overrides?.contextWindow ?? info.contextWindow);
250
+ const reasoning = info.reasoning && overrides?.reasoning !== false;
251
+ added.push({
252
+ ...model_template_0_160_1_default,
253
+ slug: id,
254
+ display_name: info.name,
255
+ description: `${info.name} (${binding.provider})`,
256
+ context_window: context,
257
+ max_context_window: context,
258
+ auto_compact_token_limit: Math.floor(context * 0.85),
259
+ input_modalities: ["text", ...info.inputModalities.includes("image") && overrides?.images !== false ? ["image"] : []],
260
+ supported_reasoning_levels: reasoning ? ["low", "medium", "high"].map((effort) => ({ effort, description: effort })) : [],
261
+ default_reasoning_level: reasoning ? "medium" : "none",
262
+ support_verbosity: false
263
+ });
264
+ }
265
+ return { ...body, [rich ? "models" : "data"]: [...existing, ...added] };
266
+ }
267
+ function catalogEtag(body, version, clientVersion) {
268
+ return `"${createHash("sha256").update(JSON.stringify([body, version, clientVersion])).digest("hex")}"`;
269
+ }
270
+
271
+ // plugins/codex-router/server/index.ts
272
+ var CodexRouterPlugin = definePlugin(class {
273
+ static name = "codex-router";
274
+ static version = "1.0.0";
275
+ bindings;
276
+ catalog;
277
+ constructor(options) {
278
+ this.bindings = parseBindings(options?.models);
279
+ }
280
+ async init(context) {
281
+ if (context.scope?.type !== "route")
282
+ throw new Error("codex_router_requires_route_scope");
283
+ this.catalog = context.services.consume("models-dev", MODELS_DEV_CAPABILITIES_SERVICE_ID, MODELS_DEV_CAPABILITIES_CONTRACT_VERSION);
284
+ }
285
+ bodyRequirements(context) {
286
+ return { request: "none", response: context.method === "GET" && /\/models$/.test(context.url.pathname) ? ["json"] : [] };
287
+ }
288
+ register(hooks) {
289
+ hooks.onBeforeRequest.tap("codex-router.catalog-validator", (context) => {
290
+ if (context.method === "GET" && /\/models$/.test(context.originalUrl.pathname)) {
291
+ for (const key of Object.keys(context.headers))
292
+ if (["if-none-match", "if-modified-since"].includes(key.toLowerCase()))
293
+ delete context.headers[key];
294
+ }
295
+ return context;
296
+ });
297
+ hooks.onResponse.tapPromise("codex-router.catalog", async (response, context) => {
298
+ if (context.method !== "GET" || !/\/models$/.test(context.originalUrl.pathname) || !response.ok)
299
+ return response;
300
+ const native = await context.bodyHandle.json({ id: "codex-router.catalog", mandatory: true });
301
+ const body = mergeCatalog(native, this.bindings, this.catalog);
302
+ const headers = new Headers(response.headers);
303
+ for (const key of ["content-length", "content-encoding", "etag", "last-modified"])
304
+ headers.delete(key);
305
+ headers.set("content-type", "application/json");
306
+ headers.set("cache-control", "private, no-store");
307
+ headers.set("etag", catalogEtag(body, this.catalog.status().version, context.originalUrl.searchParams.get("client_version") ?? ""));
308
+ return new Response(JSON.stringify(body), { status: response.status, headers });
309
+ });
310
+ }
311
+ });
312
+ var server_default = CodexRouterPlugin;
313
+ export {
314
+ CodexRouterPlugin,
315
+ server_default as default
316
+ };
317
+
318
+ //# debugId=7896B09FAE2E997364756E2164756E21