@compose-market/sdk 0.1.1 → 0.3.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 (74) hide show
  1. package/CHANGELOG.md +64 -0
  2. package/LICENSE +21 -0
  3. package/README.md +158 -35
  4. package/dist/errors.d.ts +145 -0
  5. package/dist/errors.d.ts.map +1 -0
  6. package/dist/errors.js +152 -0
  7. package/dist/errors.js.map +1 -0
  8. package/dist/events.d.ts +75 -0
  9. package/dist/events.d.ts.map +1 -0
  10. package/dist/events.js +68 -0
  11. package/dist/events.js.map +1 -0
  12. package/dist/http.d.ts +98 -0
  13. package/dist/http.d.ts.map +1 -0
  14. package/dist/http.js +350 -0
  15. package/dist/http.js.map +1 -0
  16. package/dist/index.d.ts +206 -0
  17. package/dist/index.d.ts.map +1 -0
  18. package/dist/index.js +340 -0
  19. package/dist/index.js.map +1 -0
  20. package/dist/resources/inference.d.ts +175 -0
  21. package/dist/resources/inference.d.ts.map +1 -0
  22. package/dist/resources/inference.js +740 -0
  23. package/dist/resources/inference.js.map +1 -0
  24. package/dist/resources/instrumentation.d.ts +28 -0
  25. package/dist/resources/instrumentation.d.ts.map +1 -0
  26. package/dist/resources/instrumentation.js +43 -0
  27. package/dist/resources/instrumentation.js.map +1 -0
  28. package/dist/resources/keys.d.ts +54 -0
  29. package/dist/resources/keys.d.ts.map +1 -0
  30. package/dist/resources/keys.js +164 -0
  31. package/dist/resources/keys.js.map +1 -0
  32. package/dist/resources/models.d.ts +26 -0
  33. package/dist/resources/models.d.ts.map +1 -0
  34. package/dist/resources/models.js +52 -0
  35. package/dist/resources/models.js.map +1 -0
  36. package/dist/resources/session-events.d.ts +46 -0
  37. package/dist/resources/session-events.d.ts.map +1 -0
  38. package/dist/resources/session-events.js +199 -0
  39. package/dist/resources/session-events.js.map +1 -0
  40. package/dist/resources/webhooks.d.ts +27 -0
  41. package/dist/resources/webhooks.d.ts.map +1 -0
  42. package/dist/resources/webhooks.js +78 -0
  43. package/dist/resources/webhooks.js.map +1 -0
  44. package/dist/resources/x402.d.ts +37 -0
  45. package/dist/resources/x402.d.ts.map +1 -0
  46. package/dist/resources/x402.js +72 -0
  47. package/dist/resources/x402.js.map +1 -0
  48. package/dist/storage.d.ts +27 -0
  49. package/dist/storage.d.ts.map +1 -0
  50. package/dist/storage.js +46 -0
  51. package/dist/storage.js.map +1 -0
  52. package/dist/streaming/budget.d.ts +22 -0
  53. package/dist/streaming/budget.d.ts.map +1 -0
  54. package/dist/streaming/budget.js +40 -0
  55. package/dist/streaming/budget.js.map +1 -0
  56. package/dist/streaming/receipt.d.ts +25 -0
  57. package/dist/streaming/receipt.d.ts.map +1 -0
  58. package/dist/streaming/receipt.js +92 -0
  59. package/dist/streaming/receipt.js.map +1 -0
  60. package/dist/streaming/sse.d.ts +29 -0
  61. package/dist/streaming/sse.d.ts.map +1 -0
  62. package/dist/streaming/sse.js +125 -0
  63. package/dist/streaming/sse.js.map +1 -0
  64. package/dist/types/index.d.ts +540 -0
  65. package/dist/types/index.d.ts.map +1 -0
  66. package/dist/types/index.js +10 -0
  67. package/dist/types/index.js.map +1 -0
  68. package/dist/version.d.ts +9 -0
  69. package/dist/version.d.ts.map +1 -0
  70. package/dist/version.js +9 -0
  71. package/dist/version.js.map +1 -0
  72. package/package.json +32 -21
  73. package/index.d.ts +0 -244
  74. package/index.js +0 -397
@@ -0,0 +1,206 @@
1
+ /**
2
+ * `@compose-market/sdk` — Official SDK for Compose Market.
3
+ *
4
+ * Exposes the canonical header contract (`Authorization: Bearer compose-<jwt>`,
5
+ * `x-session-user-address`, `x-chain-id`) that powers Compose's first-party
6
+ * apps (web/, mesh/) and lets any third-party integrator embed:
7
+ *
8
+ * - Compose Key lifecycle (create / list / get / revoke, session metadata)
9
+ * - 45k+ model catalog (list / listAll / search / get / getParams)
10
+ * - OpenAI-shaped inference (chat.completions, responses, embeddings, images,
11
+ * audio.speech, audio.transcriptions, videos) with full SSE streaming,
12
+ * typed tool-call deltas and reasoning deltas, typed cost receipts, and
13
+ * live session-budget updates emitted on every response.
14
+ * - x402 facilitator access (supported / chains / verify / settle) and typed
15
+ * decoders for PAYMENT-REQUIRED, PAYMENT-RESPONSE, X-Compose-Receipt.
16
+ * - SSE session events (`sdk.session.events`) for budget depletion and
17
+ * expiry notifications, dispatched on the typed event bus as well.
18
+ * - Webhook signature verification (HMAC-SHA256, Stripe-style header).
19
+ *
20
+ * Design:
21
+ * - Zero runtime dependencies. Uses platform `fetch`, WebCrypto, TextDecoder,
22
+ * ReadableStream. Works in Node 20+, Bun, Deno, Cloudflare Workers, browsers.
23
+ * - Identity is whatever the integrator already has. The SDK does NOT call a
24
+ * wallet, does NOT request signatures, does NOT run KYC. The end-user's
25
+ * wallet address — produced by whatever auth stack the integrator already
26
+ * uses — is trusted in the same exact way our first-party apps trust it —
27
+ * via the `x-session-user-address` header. The Compose Key JWT returned by
28
+ * `keys.create(...)` is the real cryptographic identity from that point on.
29
+ * - Every billable call returns a `ComposeCompletion<T>` carrying the parsed
30
+ * body, the settlement receipt (if any), the request id, the live session
31
+ * budget snapshot, the session-invalid reason (if any), and the raw
32
+ * Response so integrators can read non-standard headers without parsing.
33
+ * - Persisted session tokens survive page reloads when a storage adapter is
34
+ * provided (browser `localStorage` is auto-detected).
35
+ */
36
+ import { type FetchLike, type HttpClientOptions, type RetryPolicy } from "./http.js";
37
+ import { KeysResource } from "./resources/keys.js";
38
+ import { ModelsResource } from "./resources/models.js";
39
+ import { InferenceResource } from "./resources/inference.js";
40
+ import { X402Resource } from "./resources/x402.js";
41
+ import { WebhooksResource } from "./resources/webhooks.js";
42
+ import { SessionEventsResource, type SessionEventsOptions } from "./resources/session-events.js";
43
+ import { type ComposeEventBus, type ComposeEventListener } from "./events.js";
44
+ import { type ComposeStorage } from "./storage.js";
45
+ export * from "./types/index.js";
46
+ export * from "./errors.js";
47
+ export type { APIPromise, HeaderBagInput, HttpClientOptions, RequestOptions, RetryPolicy, } from "./http.js";
48
+ export type { ComposeCallOptions, ComposeCompletion, ChatCompletionFinalResult, ResponsesStreamFinalResult, ComposeStreamIterator, InferenceContext, } from "./resources/inference.js";
49
+ export type { ComposeWebhookEvent, VerifyWebhookInput, } from "./resources/webhooks.js";
50
+ export type { BudgetEvent, ComposeEventBus, ComposeEventListener, ComposeEventMap, ComposeEventName, ReceiptEvent, SessionInvalidEvent, } from "./events.js";
51
+ export type { ComposeStorage } from "./storage.js";
52
+ export type { SessionEventsOptions } from "./resources/session-events.js";
53
+ export { decodeReceiptHeader, extractReceiptFromResponse, parseReceiptEvent } from "./streaming/receipt.js";
54
+ export { parseSSEStream } from "./streaming/sse.js";
55
+ export { extractSessionBudgetFromResponse } from "./streaming/budget.js";
56
+ export { createMemoryStorage } from "./storage.js";
57
+ /**
58
+ * Constructor options for `ComposeSDK`.
59
+ */
60
+ export interface ComposeSDKOptions {
61
+ /** API base URL. Defaults to `https://api.compose.market`. */
62
+ baseUrl?: string;
63
+ /** Custom fetch implementation. Defaults to the global `fetch`. */
64
+ fetch?: FetchLike;
65
+ /**
66
+ * End-user wallet address. Whatever identity stack you already use produced
67
+ * this address — pass it through. The SDK relays it exactly as our
68
+ * first-party apps do, and does not care how you obtained it.
69
+ */
70
+ userAddress?: string;
71
+ /**
72
+ * Chain id. Must be one of the facilitator-configured chains. Call
73
+ * `sdk.x402.facilitator.chains()` to enumerate supported chains + USDC
74
+ * contracts at runtime.
75
+ */
76
+ chainId?: number;
77
+ /**
78
+ * A previously-issued Compose Key JWT. The SDK stores this in-memory and
79
+ * attaches it as `Authorization: Bearer compose-<jwt>` on every call.
80
+ *
81
+ * When a `storage` adapter is present, the token is also persisted under
82
+ * the scoped key `<tokenScope>:<address>:<chainId>` so that it survives
83
+ * page reloads. If `composeKey` is omitted at construction, the SDK
84
+ * attempts to hydrate from storage.
85
+ */
86
+ composeKey?: string;
87
+ /** Default timeout for each HTTP call, in milliseconds. Default 60_000. */
88
+ timeoutMs?: number;
89
+ /** Retry policy applied to transient errors (5xx, 429, network). */
90
+ retry?: Partial<RetryPolicy>;
91
+ /** Headers merged into every request. */
92
+ defaultHeaders?: Record<string, string>;
93
+ /**
94
+ * `User-Agent` suffix so Compose analytics can distinguish integrators.
95
+ * The base string is `@compose-market/sdk/<version>`.
96
+ */
97
+ userAgent?: string;
98
+ /** Optional debug/logging hooks. */
99
+ logger?: HttpClientOptions["logger"];
100
+ /**
101
+ * Pluggable persistent storage. Auto-detects `globalThis.localStorage` on
102
+ * browsers/Workers. Pass an explicit adapter on Node/server runtimes if
103
+ * you want the session token to survive process restarts.
104
+ */
105
+ storage?: ComposeStorage;
106
+ /**
107
+ * Namespace prefix for persisted tokens. The full key shape is
108
+ * `<tokenScope>:<lower-address>:<chainId>`. Defaults to
109
+ * `compose.sdk.token`. Bump this only if you need to invalidate every
110
+ * persisted token at once (e.g. after a breaking server auth change).
111
+ */
112
+ tokenScope?: string;
113
+ }
114
+ export declare class ComposeSDK {
115
+ /** The SDK version, sourced from package.json at build time. */
116
+ readonly version: string;
117
+ /** Resolved API base URL, trimmed of trailing slashes. */
118
+ readonly baseUrl: string;
119
+ readonly keys: KeysResource;
120
+ readonly models: ModelsResource;
121
+ readonly inference: InferenceResource;
122
+ readonly x402: X402Resource;
123
+ readonly webhooks: WebhooksResource;
124
+ readonly session: SessionEventsNamespace;
125
+ readonly wallets: {
126
+ attach: (input: {
127
+ address: string;
128
+ chainId: number;
129
+ }) => void;
130
+ current: () => {
131
+ address: string | null;
132
+ chainId: number | null;
133
+ };
134
+ clear: () => void;
135
+ };
136
+ /**
137
+ * Typed, in-memory event bus. Listeners registered here receive:
138
+ * - `budget` — live `x-session-budget-*` snapshot on every billable call.
139
+ * - `sessionInvalid` — `x-compose-session-invalid` header set by the server.
140
+ * - `sessionActive` — SSE `session-active` heartbeat from `/api/session/events`.
141
+ * - `sessionExpired` — SSE `session-expired` frame from `/api/session/events`.
142
+ * - `receipt` — settlement receipt on every billable response / stream.
143
+ */
144
+ readonly events: ComposeEventBus;
145
+ private readonly http;
146
+ private readonly storage;
147
+ private readonly tokenScope;
148
+ private userAddress;
149
+ private chainId;
150
+ private composeKey;
151
+ private readonly rawFetch;
152
+ private readonly userAgent;
153
+ constructor(options?: ComposeSDKOptions);
154
+ private persistToken;
155
+ private deletePersistedToken;
156
+ /**
157
+ * Drop-in `fetch` wrapper that attaches the canonical Compose header
158
+ * contract (`Authorization`, `x-session-user-address`, `x-chain-id`,
159
+ * `User-Agent`) on every request and emits `budget` / `sessionInvalid` /
160
+ * `receipt` events on every response via the SDK event bus.
161
+ *
162
+ * Use this when you need to hit a Compose endpoint that isn't covered
163
+ * by a typed resource yet (agent/workflow runtime endpoints, workspace
164
+ * indexing, custom api/ routes). The URL may be absolute or relative to
165
+ * the SDK's `baseUrl`.
166
+ *
167
+ * Non-Compose URLs (absolute URLs whose host differs from `baseUrl`) are
168
+ * still passed through so this method is safe as a general-purpose fetch
169
+ * replacement; the budget event extraction is a no-op when the response
170
+ * doesn't carry `x-session-budget-*` headers.
171
+ */
172
+ fetch(input: RequestInfo | URL, init?: RequestInit): Promise<Response>;
173
+ }
174
+ /**
175
+ * Thin ergonomic wrapper around `SessionEventsResource` so callers write
176
+ * `sdk.session.events({ ... })` with wallet defaults inferred from the SDK
177
+ * instance.
178
+ */
179
+ declare class SessionEventsNamespace {
180
+ private readonly resource;
181
+ private readonly getWalletMaybe;
182
+ constructor(resource: SessionEventsResource, getWalletMaybe: () => {
183
+ address: string | null;
184
+ chainId: number | null;
185
+ });
186
+ /**
187
+ * Subscribe to `/api/session/events`. Yields `SessionActiveEvent` and
188
+ * `SessionExpiredEvent` until the signal aborts or the server ends the
189
+ * stream. The same events are also emitted on `sdk.events`.
190
+ *
191
+ * When `userAddress` / `chainId` are omitted, the SDK's currently attached
192
+ * wallet context is used. Abort via an `AbortController.signal`.
193
+ */
194
+ subscribe(opts?: Partial<SessionEventsOptions>): AsyncIterable<import("./types/index.js").SessionEvent>;
195
+ /**
196
+ * Shortcut: register a listener on the `sessionActive` + `sessionExpired`
197
+ * events produced by a subscription. Returns a disposer that aborts the
198
+ * underlying stream AND removes the listeners.
199
+ */
200
+ on(handlers: {
201
+ active?: ComposeEventListener<"sessionActive">;
202
+ expired?: ComposeEventListener<"sessionExpired">;
203
+ }, opts?: Partial<SessionEventsOptions>): () => void;
204
+ }
205
+ export default ComposeSDK;
206
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
package/dist/index.js ADDED
@@ -0,0 +1,340 @@
1
+ /**
2
+ * `@compose-market/sdk` — Official SDK for Compose Market.
3
+ *
4
+ * Exposes the canonical header contract (`Authorization: Bearer compose-<jwt>`,
5
+ * `x-session-user-address`, `x-chain-id`) that powers Compose's first-party
6
+ * apps (web/, mesh/) and lets any third-party integrator embed:
7
+ *
8
+ * - Compose Key lifecycle (create / list / get / revoke, session metadata)
9
+ * - 45k+ model catalog (list / listAll / search / get / getParams)
10
+ * - OpenAI-shaped inference (chat.completions, responses, embeddings, images,
11
+ * audio.speech, audio.transcriptions, videos) with full SSE streaming,
12
+ * typed tool-call deltas and reasoning deltas, typed cost receipts, and
13
+ * live session-budget updates emitted on every response.
14
+ * - x402 facilitator access (supported / chains / verify / settle) and typed
15
+ * decoders for PAYMENT-REQUIRED, PAYMENT-RESPONSE, X-Compose-Receipt.
16
+ * - SSE session events (`sdk.session.events`) for budget depletion and
17
+ * expiry notifications, dispatched on the typed event bus as well.
18
+ * - Webhook signature verification (HMAC-SHA256, Stripe-style header).
19
+ *
20
+ * Design:
21
+ * - Zero runtime dependencies. Uses platform `fetch`, WebCrypto, TextDecoder,
22
+ * ReadableStream. Works in Node 20+, Bun, Deno, Cloudflare Workers, browsers.
23
+ * - Identity is whatever the integrator already has. The SDK does NOT call a
24
+ * wallet, does NOT request signatures, does NOT run KYC. The end-user's
25
+ * wallet address — produced by whatever auth stack the integrator already
26
+ * uses — is trusted in the same exact way our first-party apps trust it —
27
+ * via the `x-session-user-address` header. The Compose Key JWT returned by
28
+ * `keys.create(...)` is the real cryptographic identity from that point on.
29
+ * - Every billable call returns a `ComposeCompletion<T>` carrying the parsed
30
+ * body, the settlement receipt (if any), the request id, the live session
31
+ * budget snapshot, the session-invalid reason (if any), and the raw
32
+ * Response so integrators can read non-standard headers without parsing.
33
+ * - Persisted session tokens survive page reloads when a storage adapter is
34
+ * provided (browser `localStorage` is auto-detected).
35
+ */
36
+ import { HttpClient } from "./http.js";
37
+ import { KeysResource } from "./resources/keys.js";
38
+ import { ModelsResource } from "./resources/models.js";
39
+ import { InferenceResource } from "./resources/inference.js";
40
+ import { X402Resource } from "./resources/x402.js";
41
+ import { WebhooksResource } from "./resources/webhooks.js";
42
+ import { SessionEventsResource } from "./resources/session-events.js";
43
+ import { instrumentBillableResponse } from "./resources/instrumentation.js";
44
+ import { BadRequestError } from "./errors.js";
45
+ import { createEventBus } from "./events.js";
46
+ import { resolveStorage, createMemoryStorage, buildTokenStorageKey, DEFAULT_TOKEN_SCOPE, } from "./storage.js";
47
+ import { SDK_VERSION } from "./version.js";
48
+ export * from "./types/index.js";
49
+ export * from "./errors.js";
50
+ export { decodeReceiptHeader, extractReceiptFromResponse, parseReceiptEvent } from "./streaming/receipt.js";
51
+ export { parseSSEStream } from "./streaming/sse.js";
52
+ export { extractSessionBudgetFromResponse } from "./streaming/budget.js";
53
+ export { createMemoryStorage } from "./storage.js";
54
+ const DEFAULT_RETRY = {
55
+ maxRetries: 2,
56
+ initialDelayMs: 500,
57
+ maxDelayMs: 8_000,
58
+ jitter: true,
59
+ };
60
+ function normalizeBaseUrl(value) {
61
+ return (value || "https://api.compose.market").replace(/\/+$/, "");
62
+ }
63
+ function normalizeUserAddress(value) {
64
+ const trimmed = value.trim().toLowerCase();
65
+ if (!/^0x[a-f0-9]{40}$/.test(trimmed)) {
66
+ throw new BadRequestError({ message: "userAddress must be a valid 0x-prefixed EVM address" });
67
+ }
68
+ return trimmed;
69
+ }
70
+ function normalizeChainId(value) {
71
+ if (value === undefined || value === null)
72
+ return null;
73
+ if (!Number.isInteger(value) || value <= 0) {
74
+ throw new BadRequestError({ message: "chainId must be a positive integer" });
75
+ }
76
+ return value;
77
+ }
78
+ export class ComposeSDK {
79
+ /** The SDK version, sourced from package.json at build time. */
80
+ version = SDK_VERSION;
81
+ /** Resolved API base URL, trimmed of trailing slashes. */
82
+ baseUrl;
83
+ keys;
84
+ models;
85
+ inference;
86
+ x402;
87
+ webhooks;
88
+ session;
89
+ wallets;
90
+ /**
91
+ * Typed, in-memory event bus. Listeners registered here receive:
92
+ * - `budget` — live `x-session-budget-*` snapshot on every billable call.
93
+ * - `sessionInvalid` — `x-compose-session-invalid` header set by the server.
94
+ * - `sessionActive` — SSE `session-active` heartbeat from `/api/session/events`.
95
+ * - `sessionExpired` — SSE `session-expired` frame from `/api/session/events`.
96
+ * - `receipt` — settlement receipt on every billable response / stream.
97
+ */
98
+ events;
99
+ http;
100
+ storage;
101
+ tokenScope;
102
+ userAddress;
103
+ chainId;
104
+ composeKey;
105
+ rawFetch;
106
+ userAgent;
107
+ constructor(options = {}) {
108
+ this.userAddress = options.userAddress ? normalizeUserAddress(options.userAddress) : null;
109
+ this.chainId = normalizeChainId(options.chainId);
110
+ this.baseUrl = normalizeBaseUrl(options.baseUrl);
111
+ this.tokenScope = options.tokenScope ?? DEFAULT_TOKEN_SCOPE;
112
+ this.storage = resolveStorage(options.storage) ?? createMemoryStorage();
113
+ this.events = createEventBus({ logger: options.logger });
114
+ // Seed `composeKey` in this priority:
115
+ // 1. explicit constructor option
116
+ // 2. persistent storage scoped to (address, chainId) if both known
117
+ // 3. null
118
+ if (options.composeKey) {
119
+ this.composeKey = options.composeKey;
120
+ this.persistToken(options.composeKey);
121
+ }
122
+ else if (this.userAddress && this.chainId !== null) {
123
+ this.composeKey = this.storage.getItem(buildTokenStorageKey(this.tokenScope, this.userAddress, this.chainId));
124
+ }
125
+ else {
126
+ this.composeKey = null;
127
+ }
128
+ const userAgent = options.userAgent
129
+ ? `@compose-market/sdk/${SDK_VERSION} ${options.userAgent}`
130
+ : `@compose-market/sdk/${SDK_VERSION}`;
131
+ this.rawFetch = options.fetch ?? globalThis.fetch.bind(globalThis);
132
+ this.userAgent = userAgent;
133
+ this.http = new HttpClient({
134
+ baseUrl: this.baseUrl,
135
+ fetch: this.rawFetch,
136
+ timeoutMs: options.timeoutMs ?? 60_000,
137
+ defaultHeaders: { ...(options.defaultHeaders ?? {}) },
138
+ retry: { ...DEFAULT_RETRY, ...(options.retry ?? {}) },
139
+ userAgent,
140
+ logger: options.logger,
141
+ });
142
+ this.wallets = {
143
+ attach: (input) => {
144
+ this.userAddress = normalizeUserAddress(input.address);
145
+ this.chainId = normalizeChainId(input.chainId);
146
+ // Re-hydrate persisted token for the freshly-attached wallet.
147
+ const stored = this.storage.getItem(buildTokenStorageKey(this.tokenScope, this.userAddress, this.chainId));
148
+ if (stored)
149
+ this.composeKey = stored;
150
+ },
151
+ current: () => ({ address: this.userAddress, chainId: this.chainId }),
152
+ clear: () => {
153
+ this.userAddress = null;
154
+ this.chainId = null;
155
+ this.composeKey = null;
156
+ },
157
+ };
158
+ const getWallet = () => {
159
+ if (!this.userAddress) {
160
+ throw new BadRequestError({
161
+ message: "Wallet context is required. Call sdk.wallets.attach({ address, chainId }) first, or pass userAddress + chainId to the constructor.",
162
+ });
163
+ }
164
+ if (this.chainId === null) {
165
+ throw new BadRequestError({
166
+ message: "chainId is required. Call sdk.wallets.attach(...) or pass chainId to the constructor.",
167
+ });
168
+ }
169
+ return { address: this.userAddress, chainId: this.chainId };
170
+ };
171
+ const getWalletMaybe = () => ({
172
+ address: this.userAddress,
173
+ chainId: this.chainId,
174
+ });
175
+ this.keys = new KeysResource(this.http, {
176
+ getWallet,
177
+ getWalletMaybe,
178
+ setToken: (token) => {
179
+ this.composeKey = token;
180
+ this.persistToken(token);
181
+ },
182
+ getToken: () => this.composeKey,
183
+ clearToken: () => {
184
+ this.composeKey = null;
185
+ this.deletePersistedToken();
186
+ },
187
+ });
188
+ this.models = new ModelsResource(this.http);
189
+ this.inference = new InferenceResource(this.http, {
190
+ getWalletMaybe,
191
+ getTokenMaybe: () => this.composeKey,
192
+ events: this.events,
193
+ });
194
+ this.x402 = new X402Resource(this.http);
195
+ this.webhooks = new WebhooksResource();
196
+ this.session = new SessionEventsNamespace(new SessionEventsResource(this.http, this.events), getWalletMaybe);
197
+ }
198
+ persistToken(token) {
199
+ if (!this.userAddress || this.chainId === null)
200
+ return;
201
+ this.storage.setItem(buildTokenStorageKey(this.tokenScope, this.userAddress, this.chainId), token);
202
+ }
203
+ deletePersistedToken() {
204
+ if (!this.userAddress || this.chainId === null)
205
+ return;
206
+ this.storage.removeItem(buildTokenStorageKey(this.tokenScope, this.userAddress, this.chainId));
207
+ }
208
+ /**
209
+ * Drop-in `fetch` wrapper that attaches the canonical Compose header
210
+ * contract (`Authorization`, `x-session-user-address`, `x-chain-id`,
211
+ * `User-Agent`) on every request and emits `budget` / `sessionInvalid` /
212
+ * `receipt` events on every response via the SDK event bus.
213
+ *
214
+ * Use this when you need to hit a Compose endpoint that isn't covered
215
+ * by a typed resource yet (agent/workflow runtime endpoints, workspace
216
+ * indexing, custom api/ routes). The URL may be absolute or relative to
217
+ * the SDK's `baseUrl`.
218
+ *
219
+ * Non-Compose URLs (absolute URLs whose host differs from `baseUrl`) are
220
+ * still passed through so this method is safe as a general-purpose fetch
221
+ * replacement; the budget event extraction is a no-op when the response
222
+ * doesn't carry `x-session-budget-*` headers.
223
+ */
224
+ async fetch(input, init) {
225
+ const headers = new Headers(init?.headers);
226
+ if (!headers.has("User-Agent"))
227
+ headers.set("User-Agent", this.userAgent);
228
+ if (this.composeKey && !headers.has("Authorization")) {
229
+ headers.set("Authorization", `Bearer ${this.composeKey}`);
230
+ }
231
+ if (this.userAddress && !headers.has("x-session-user-address")) {
232
+ headers.set("x-session-user-address", this.userAddress);
233
+ }
234
+ if (this.chainId !== null && !headers.has("x-chain-id")) {
235
+ headers.set("x-chain-id", String(this.chainId));
236
+ }
237
+ // Support absolute URLs, relative paths, and Request objects alike.
238
+ let resolvedInput = input;
239
+ if (typeof input === "string") {
240
+ resolvedInput = input.startsWith("http://") || input.startsWith("https://")
241
+ ? input
242
+ : `${this.baseUrl}${input.startsWith("/") ? input : `/${input}`}`;
243
+ }
244
+ const response = await this.rawFetch(resolvedInput, { ...init, headers });
245
+ // Emit budget/receipt/invalid events when the response carries the
246
+ // relevant Compose headers. Pass `undefined` for the body since we
247
+ // haven't read it; receipt-from-body only fires when the caller later
248
+ // parses the JSON themselves. That's acceptable: header-based receipts
249
+ // are the authoritative path and they're present on every billable
250
+ // response.
251
+ instrumentBillableResponse({ getWalletMaybe: () => ({ address: this.userAddress, chainId: this.chainId }), getTokenMaybe: () => this.composeKey, events: this.events }, response, undefined);
252
+ return response;
253
+ }
254
+ }
255
+ /**
256
+ * Thin ergonomic wrapper around `SessionEventsResource` so callers write
257
+ * `sdk.session.events({ ... })` with wallet defaults inferred from the SDK
258
+ * instance.
259
+ */
260
+ class SessionEventsNamespace {
261
+ resource;
262
+ getWalletMaybe;
263
+ constructor(resource, getWalletMaybe) {
264
+ this.resource = resource;
265
+ this.getWalletMaybe = getWalletMaybe;
266
+ }
267
+ /**
268
+ * Subscribe to `/api/session/events`. Yields `SessionActiveEvent` and
269
+ * `SessionExpiredEvent` until the signal aborts or the server ends the
270
+ * stream. The same events are also emitted on `sdk.events`.
271
+ *
272
+ * When `userAddress` / `chainId` are omitted, the SDK's currently attached
273
+ * wallet context is used. Abort via an `AbortController.signal`.
274
+ */
275
+ subscribe(opts = {}) {
276
+ const wallet = this.getWalletMaybe();
277
+ const userAddress = opts.userAddress ?? wallet.address;
278
+ const chainId = opts.chainId ?? wallet.chainId;
279
+ if (!userAddress) {
280
+ throw new BadRequestError({
281
+ message: "session.subscribe() needs a userAddress (either in opts or via sdk.wallets.attach).",
282
+ });
283
+ }
284
+ if (chainId === null || chainId === undefined) {
285
+ throw new BadRequestError({
286
+ message: "session.subscribe() needs a chainId (either in opts or via sdk.wallets.attach).",
287
+ });
288
+ }
289
+ return this.resource.subscribe({
290
+ userAddress,
291
+ chainId,
292
+ signal: opts.signal,
293
+ reconnectMaxDelayMs: opts.reconnectMaxDelayMs,
294
+ });
295
+ }
296
+ /**
297
+ * Shortcut: register a listener on the `sessionActive` + `sessionExpired`
298
+ * events produced by a subscription. Returns a disposer that aborts the
299
+ * underlying stream AND removes the listeners.
300
+ */
301
+ on(handlers, opts = {}) {
302
+ const controller = new AbortController();
303
+ const signal = mergeAbortSignals(opts.signal, controller.signal);
304
+ const iterable = this.subscribe({ ...opts, signal });
305
+ const unsubActive = handlers.active
306
+ ? this.resource.events.on("sessionActive", handlers.active)
307
+ : () => { };
308
+ const unsubExpired = handlers.expired
309
+ ? this.resource.events.on("sessionExpired", handlers.expired)
310
+ : () => { };
311
+ // Drive the iterator in the background; if the caller never reads it
312
+ // explicitly, the events still flow through the event bus.
313
+ (async () => {
314
+ try {
315
+ for await (const _event of iterable) {
316
+ void _event;
317
+ }
318
+ }
319
+ catch { /* aborted / retries exhausted */ }
320
+ })();
321
+ return () => {
322
+ unsubActive();
323
+ unsubExpired();
324
+ controller.abort();
325
+ };
326
+ }
327
+ }
328
+ function mergeAbortSignals(a, b) {
329
+ if (!a)
330
+ return b;
331
+ const c = new AbortController();
332
+ const forward = () => c.abort();
333
+ if (a.aborted || b.aborted)
334
+ c.abort();
335
+ a.addEventListener("abort", forward, { once: true });
336
+ b.addEventListener("abort", forward, { once: true });
337
+ return c.signal;
338
+ }
339
+ export default ComposeSDK;
340
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}