@usequeek/app-sdk 0.6.1 → 0.7.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 (107) hide show
  1. package/LICENSE +1 -1
  2. package/README.md +339 -330
  3. package/dist/app-auth.d.ts +15 -17
  4. package/dist/app-auth.js +20 -23
  5. package/dist/auth-fetch.d.ts +14 -5
  6. package/dist/auth-fetch.js +15 -6
  7. package/dist/background.d.ts +10 -2
  8. package/dist/background.js +9 -1
  9. package/dist/browser.d.ts +2 -3
  10. package/dist/browser.js +2 -3
  11. package/dist/client.d.ts +138 -16
  12. package/dist/client.js +200 -43
  13. package/dist/collected.d.ts +13 -15
  14. package/dist/collected.js +4 -5
  15. package/dist/crypto.d.ts +11 -1
  16. package/dist/crypto.js +25 -10
  17. package/dist/delivery.d.ts +22 -9
  18. package/dist/delivery.js +26 -21
  19. package/dist/frame.d.ts +11 -12
  20. package/dist/frame.js +11 -12
  21. package/dist/handoff.d.ts +35 -39
  22. package/dist/handoff.js +9 -10
  23. package/dist/hono.d.ts +3 -4
  24. package/dist/hono.js +3 -4
  25. package/dist/index.d.ts +1 -2
  26. package/dist/index.js +1 -2
  27. package/dist/install-handlers.d.ts +28 -9
  28. package/dist/install-handlers.js +48 -18
  29. package/dist/logger.d.ts +7 -1
  30. package/dist/logger.js +8 -2
  31. package/dist/merchant-schema.d.ts +15678 -6236
  32. package/dist/merchant-schema.js +0 -1
  33. package/dist/proxy.d.ts +21 -24
  34. package/dist/proxy.js +20 -22
  35. package/dist/react.d.ts +10 -2
  36. package/dist/react.js +11 -3
  37. package/dist/resync.d.ts +15 -5
  38. package/dist/resync.js +22 -20
  39. package/dist/scopes.d.ts +36 -27
  40. package/dist/scopes.js +37 -40
  41. package/dist/server.d.ts +0 -1
  42. package/dist/server.js +0 -1
  43. package/dist/session.d.ts +35 -17
  44. package/dist/session.js +32 -15
  45. package/dist/signatures.d.ts +31 -5
  46. package/dist/signatures.js +36 -9
  47. package/dist/store.d.ts +26 -26
  48. package/dist/store.js +16 -20
  49. package/dist/theme.d.ts +1 -2
  50. package/dist/theme.js +1 -2
  51. package/dist/tokens.d.ts +18 -10
  52. package/dist/tokens.js +32 -57
  53. package/dist/webhooks.d.ts +30 -6
  54. package/dist/webhooks.js +27 -10
  55. package/package.json +21 -4
  56. package/dist/app-auth.d.ts.map +0 -1
  57. package/dist/app-auth.js.map +0 -1
  58. package/dist/auth-fetch.d.ts.map +0 -1
  59. package/dist/auth-fetch.js.map +0 -1
  60. package/dist/background.d.ts.map +0 -1
  61. package/dist/background.js.map +0 -1
  62. package/dist/browser.d.ts.map +0 -1
  63. package/dist/browser.js.map +0 -1
  64. package/dist/client.d.ts.map +0 -1
  65. package/dist/client.js.map +0 -1
  66. package/dist/collected.d.ts.map +0 -1
  67. package/dist/collected.js.map +0 -1
  68. package/dist/crypto.d.ts.map +0 -1
  69. package/dist/crypto.js.map +0 -1
  70. package/dist/delivery.d.ts.map +0 -1
  71. package/dist/delivery.js.map +0 -1
  72. package/dist/frame.d.ts.map +0 -1
  73. package/dist/frame.js.map +0 -1
  74. package/dist/handoff.d.ts.map +0 -1
  75. package/dist/handoff.js.map +0 -1
  76. package/dist/hono.d.ts.map +0 -1
  77. package/dist/hono.js.map +0 -1
  78. package/dist/index.d.ts.map +0 -1
  79. package/dist/index.js.map +0 -1
  80. package/dist/install-handlers.d.ts.map +0 -1
  81. package/dist/install-handlers.js.map +0 -1
  82. package/dist/logger.d.ts.map +0 -1
  83. package/dist/logger.js.map +0 -1
  84. package/dist/merchant-schema.d.ts.map +0 -1
  85. package/dist/merchant-schema.js.map +0 -1
  86. package/dist/proxy.d.ts.map +0 -1
  87. package/dist/proxy.js.map +0 -1
  88. package/dist/react.d.ts.map +0 -1
  89. package/dist/react.js.map +0 -1
  90. package/dist/resync.d.ts.map +0 -1
  91. package/dist/resync.js.map +0 -1
  92. package/dist/scopes.d.ts.map +0 -1
  93. package/dist/scopes.js.map +0 -1
  94. package/dist/server.d.ts.map +0 -1
  95. package/dist/server.js.map +0 -1
  96. package/dist/session.d.ts.map +0 -1
  97. package/dist/session.js.map +0 -1
  98. package/dist/signatures.d.ts.map +0 -1
  99. package/dist/signatures.js.map +0 -1
  100. package/dist/store.d.ts.map +0 -1
  101. package/dist/store.js.map +0 -1
  102. package/dist/theme.d.ts.map +0 -1
  103. package/dist/theme.js.map +0 -1
  104. package/dist/tokens.d.ts.map +0 -1
  105. package/dist/tokens.js.map +0 -1
  106. package/dist/webhooks.d.ts.map +0 -1
  107. package/dist/webhooks.js.map +0 -1
package/dist/store.js CHANGED
@@ -50,19 +50,17 @@ const INSTALLATIONS_TABLE_SQLITE = `
50
50
  * built-in `node:sqlite` (`DatabaseSync` — synchronous, file-backed, WAL
51
51
  * mode).
52
52
  *
53
- * Why not better-sqlite3: its prebuilt binary segfaults on the project's
54
- * Node 22.12 runtime (observed, not theorised), and building from source
55
- * would force a C++ toolchain into every environment — dev Macs, CI, and
56
- * the slim alpine app images. `node:sqlite` is dependency-free with an
57
- * identical synchronous shape.
53
+ * Why not better-sqlite3: its prebuilt binary segfaults on Node 22.12, and
54
+ * building from source would force a C++ toolchain into every environment
55
+ * — dev Macs, CI, and slim alpine images. `node:sqlite` is
56
+ * dependency-free with an identical synchronous shape.
58
57
  *
59
- * `node:sqlite` needs no flag since Node 22.13.0 (pinned runtime 22.23.3;
60
- * an ExperimentalWarning on stderr remains — Stability 1.1). Devs on an
61
- * older 22 minor set `NODE_OPTIONS=--experimental-sqlite` in their shell.
62
- * Revisit when the apps run on a Node line where it is fully stable — the
63
- * swap is contained here, behind `InstallationStore`.
58
+ * `node:sqlite` needs no flag since Node 22.13.0 (an ExperimentalWarning on
59
+ * stderr remains — Stability 1.1). Devs on an older 22 minor set
60
+ * `NODE_OPTIONS=--experimental-sqlite` in their shell. The swap to another
61
+ * driver is contained here, behind `InstallationStore`.
64
62
  *
65
- * 0.1.x → 0.2.0 upgrade: databases created by SDK 0.1.x carry a legacy
63
+ * Legacy upgrade: databases created by SDK 0.1.x carry a legacy
66
64
  * `api_key_enc` column (the handoff no longer delivers that key, so its
67
65
  * value is dead — minted tokens replace it; resync restores connectivity).
68
66
  * Opening such a database adds the token-cache columns and drops
@@ -90,21 +88,21 @@ export class SqliteInstallationStore {
90
88
  // its ciphertext is dropped, never decrypted or re-encrypted.
91
89
  this.db.exec(`ALTER TABLE installations DROP COLUMN api_key_enc;`);
92
90
  }
93
- // Schema v2 (B2 review r2): the persisted 409-pending mark. Existing
91
+ // Schema v2: the persisted 409-pending mark. Existing
94
92
  // rows backfill to 0 (not pending); fresh tables already carry the
95
93
  // column via the CREATE above, so this is a no-op for them.
96
94
  const live = new Set(this.db.prepare(`PRAGMA table_info(installations)`).all().map((column) => column.name));
97
95
  if (!live.has("pending")) {
98
96
  this.db.exec(`ALTER TABLE installations ADD COLUMN pending INTEGER NOT NULL DEFAULT 0;`);
99
97
  }
100
- // Schema v3 (FA1): the installation proxy secret for slot-claim
98
+ // Schema v3: the installation proxy secret for slot-claim
101
99
  // signing. Existing rows backfill to NULL (no proxy secret known
102
100
  // until the next install/resync handoff); fresh tables already carry
103
101
  // the column via the CREATE above, so this is a no-op for them.
104
102
  if (!live.has("proxy_secret_enc")) {
105
103
  this.db.exec(`ALTER TABLE installations ADD COLUMN proxy_secret_enc TEXT;`);
106
104
  }
107
- // Schema v4 (S4): the embed secret + app id that verify dashboard
105
+ // Schema v4: the embed secret + app id that verify dashboard
108
106
  // session tokens. Existing rows backfill to NULL until the next
109
107
  // install/resync handoff delivers them.
110
108
  if (!live.has("embed_secret_enc")) {
@@ -252,8 +250,7 @@ export class SqliteInstallationStore {
252
250
  }
253
251
  /**
254
252
  * Canonical integer-string form of a Queek `p_id`: the handoff contract
255
- * types p_ids as strings and the backend casts on the wire, but the
256
- * tolerance stays — a JSON integer would reach here as a JS number, and
253
+ * types p_ids as strings, but the tolerance stays — a JSON integer would reach here as a JS number, and
257
254
  * `node:sqlite` binds that number into a TEXT column as `"1021.0"`, which
258
255
  * never equals the proxy `kid` (`"1021"`). Non-numeric pids pass through
259
256
  * untouched.
@@ -418,17 +415,17 @@ export class PostgresInstallationStore {
418
415
  webhook_id TEXT PRIMARY KEY,
419
416
  seen_at BIGINT NOT NULL
420
417
  );
421
- -- Schema v2 (B2 review r2): the persisted 409-pending mark.
418
+ -- Schema v2: the persisted 409-pending mark.
422
419
  -- Fresh tables already carry the column; this migrates v1
423
420
  -- databases in place (existing rows backfill to FALSE).
424
421
  ALTER TABLE installations
425
422
  ADD COLUMN IF NOT EXISTS pending BOOLEAN NOT NULL DEFAULT FALSE;
426
- -- Schema v3 (FA1): the installation proxy secret for slot-claim
423
+ -- Schema v3: the installation proxy secret for slot-claim
427
424
  -- signing. Existing rows backfill to NULL (unknown until the
428
425
  -- next install/resync handoff).
429
426
  ALTER TABLE installations
430
427
  ADD COLUMN IF NOT EXISTS proxy_secret_enc TEXT;
431
- -- Schema v4 (S4): the embed secret + app id that verify
428
+ -- Schema v4: the embed secret + app id that verify
432
429
  -- dashboard session tokens (NULL until the next handoff).
433
430
  ALTER TABLE installations
434
431
  ADD COLUMN IF NOT EXISTS embed_secret_enc TEXT;
@@ -717,4 +714,3 @@ export function createInstallationStore(options) {
717
714
  storeKey: options.storeKey,
718
715
  });
719
716
  }
720
- //# sourceMappingURL=store.js.map
package/dist/theme.d.ts CHANGED
@@ -1,5 +1,5 @@
1
1
  /**
2
- * Dashboard-following theme (U7): dark when the dashboard is dark, light
2
+ * Dashboard-following theme: dark when the dashboard is dark, light
3
3
  * when light, switching live. First load carries `theme=light|dark` as a
4
4
  * plain UNSIGNED URL query param (dashboard `resolvedTheme`) so the app
5
5
  * server-renders `<html class="dark">` with no flash; live changes arrive
@@ -97,4 +97,3 @@ export interface ThemeListenerOptions {
97
97
  * Returns an unsubscribe function.
98
98
  */
99
99
  export declare function installThemeListener(options: ThemeListenerOptions): () => void;
100
- //# sourceMappingURL=theme.d.ts.map
package/dist/theme.js CHANGED
@@ -1,5 +1,5 @@
1
1
  /**
2
- * Dashboard-following theme (U7): dark when the dashboard is dark, light
2
+ * Dashboard-following theme: dark when the dashboard is dark, light
3
3
  * when light, switching live. First load carries `theme=light|dark` as a
4
4
  * plain UNSIGNED URL query param (dashboard `resolvedTheme`) so the app
5
5
  * server-renders `<html class="dark">` with no flash; live changes arrive
@@ -159,4 +159,3 @@ export function installThemeListener(options) {
159
159
  },
160
160
  });
161
161
  }
162
- //# sourceMappingURL=theme.js.map
package/dist/tokens.d.ts CHANGED
@@ -3,7 +3,7 @@ import { type MerchantPaths, QueekApiError, type QueekClient, type ResolvedPaths
3
3
  import { type Logger } from "./logger.js";
4
4
  import { type InstallationStore } from "./store.js";
5
5
  /**
6
- * Installation tokens (S1, SDK 0.2.0): the app holds ONE asymmetric app
6
+ * Installation tokens: the app holds ONE asymmetric app
7
7
  * credential and mints short-lived installation tokens from Queek on
8
8
  * demand, cached (encrypted) in its own database to near-expiry.
9
9
  *
@@ -13,7 +13,7 @@ import { type InstallationStore } from "./store.js";
13
13
  * installation client goes through it.
14
14
  * - A merchant-API token refusal → drop it, re-mint once, retry once; a
15
15
  * second refusal propagates. Token refusal = any 401, or a 403 with
16
- * `api_key_revoked` / `api_key_expired` / `invalid_client_key` (rev 7).
16
+ * `api_key_revoked` / `api_key_expired` / `invalid_client_key`.
17
17
  * A merchant 403 `insufficient_scope` (stale grant) follows the same
18
18
  * drop + re-mint-once + retry-once path. A merchant 403
19
19
  * `app_token_revoked` is the app-wide kill switch (drop all + halt, no
@@ -22,17 +22,17 @@ import { type InstallationStore } from "./store.js";
22
22
  * mint path below applies those rules.)
23
23
  * - Concurrent callers in one process share ONE in-flight mint per
24
24
  * installation (single-flight). Across containers two mints are harmless
25
- * by design: Queek keeps coexisting tokens valid (K=2 slots) and the
25
+ * by design: Queek keeps coexisting tokens valid (two token slots) and the
26
26
  * last write wins the shared cache row; a residual race self-heals via
27
27
  * re-mint on 401.
28
- * - Error handling exactly per the wire contract: 401 `invalid_client`
28
+ * - Error handling by status and code: 401 `invalid_client`
29
29
  * halts minting app-wide (loud log, no retry loop); 403 kill-switch
30
30
  * drops ALL cached tokens and halts; 404 `app_installation_gone` purges
31
31
  * the installation; 409 `app_installation_pending` retries later with
32
32
  * backoff — NEVER purges, NEVER halts (the persisted pending mark keeps
33
33
  * the row through restarts and resync's purge-absent step); 429 honors
34
- * `Retry-After` +
35
- * jitter with bounded retries; 5xx/network bounded exponential backoff.
34
+ * `Retry-After` + jitter with bounded retries; 5xx/network bounded
35
+ * exponential backoff.
36
36
  */
37
37
  /** Path of the app-credential API below the store host. */
38
38
  export declare const APP_API_PATH = "/api/v1/apps";
@@ -58,7 +58,7 @@ export interface TokenProviderOptions {
58
58
  fetchImpl?: typeof fetch;
59
59
  /** Sent as User-Agent on app-API calls. Defaults to `queek-app/1.0`. */
60
60
  userAgent?: string;
61
- /** Extra allowed `apiBase` hosts (test/local backends). */
61
+ /** Extra allowed `apiBase` hosts (test/local API hosts). */
62
62
  allowedApiHosts?: string[];
63
63
  /** Loud halt/drop logs go here. Defaults to a `queek-app-tokens` logger (stderr on warn+). */
64
64
  logger?: Logger;
@@ -75,7 +75,14 @@ export interface TokenProviderOptions {
75
75
  * (`<origin>/api/v1/apps`). Throws `InvalidApiBaseError` before any fetch.
76
76
  */
77
77
  export declare function resolveAppApiBase(raw: string, allowedApiHosts?: string[]): string;
78
+ /** The app-API path that mints a token for one installation. */
78
79
  export declare function mintPath(installationId: string): string;
80
+ /**
81
+ * Mints, caches and refreshes installation tokens for one app. Tokens are
82
+ * minted with the app's RSA key, cached encrypted in the installation store,
83
+ * and shared by concurrent callers in one process. Build one with
84
+ * {@link createAppTokenProvider} and pass it to `createInstallationClient`.
85
+ */
79
86
  export declare class AppTokenProvider implements AppTokens {
80
87
  private readonly credential;
81
88
  private readonly store;
@@ -104,7 +111,7 @@ export declare class AppTokenProvider implements AppTokens {
104
111
  dropAllCachedTokens(): Promise<void>;
105
112
  /**
106
113
  * Persist the 409 `app_installation_pending` mark for this installation
107
- * (store column — survives restarts, B2 review r2). Resync's purge-absent
114
+ * (store column — survives restarts). Resync's purge-absent
108
115
  * step keeps marked rows (the list covers active installations only).
109
116
  * Called by the mint path and by `resyncFromQueek`; idempotent, and a
110
117
  * no-op when the row is already gone.
@@ -151,8 +158,10 @@ export interface InstallationClientOptions {
151
158
  fetchImpl?: typeof fetch;
152
159
  /** Sent as User-Agent. Defaults to `queek-app/1.0`. */
153
160
  userAgent?: string;
154
- /** Extra allowed `apiBase` hosts (test/local backends). */
161
+ /** Extra allowed `apiBase` hosts (test/local API hosts). */
155
162
  allowedApiHosts?: string[];
163
+ /** Time one attempt may take, in ms (default 30000). `0` disables the client timeout. */
164
+ timeoutMs?: number;
156
165
  }
157
166
  /**
158
167
  * A `QueekClient` whose every call goes through `acquireToken()`: the
@@ -174,4 +183,3 @@ export interface InstallationClientOptions {
174
183
  * does NOT auto-update (re-run codegen in the app; sunset signal at 1.0).
175
184
  */
176
185
  export declare function createInstallationClient<TPaths = MerchantPaths>(options: InstallationClientOptions): QueekClient<ResolvedPaths<TPaths>>;
177
- //# sourceMappingURL=tokens.d.ts.map
package/dist/tokens.js CHANGED
@@ -1,9 +1,9 @@
1
1
  import { APP_TOKEN_REVOKED_CODE, AppMintHaltedError, INVALID_CLIENT_CODE, isAppTokenRevoked, isInstallationGone, isInstallationPending, isInsufficientScope, isTokenRefusal, MAX_MINT_ATTEMPTS, MINT_BACKOFF_BASE_MS, MINT_BACKOFF_MAX_MS, RETRY_JITTER_MAX_MS, signAppJwt, TOKEN_VALIDITY_SKEW_SECONDS, UnknownInstallationError, } from "./app-auth.js";
2
- import { createQueekClient, isWriteMethod, MERCHANT_API_PATH, newIdempotencyKey, QueekApiError, queekApiErrorFromResponse, resolveApiBase, } from "./client.js";
2
+ import { createQueekClient, DEFAULT_REQUEST_TIMEOUT_MS, isWriteMethod, MERCHANT_API_PATH, newIdempotencyKey, parseSuccessBody, QueekApiError, queekApiErrorFromResponse, requestSignal, resolveApiBase, runWithRetry, transportError, tryParseJson, } from "./client.js";
3
3
  import { createLogger } from "./logger.js";
4
4
  import { defaultClearCachedTokenIfMatches } from "./store.js";
5
5
  /**
6
- * Installation tokens (S1, SDK 0.2.0): the app holds ONE asymmetric app
6
+ * Installation tokens: the app holds ONE asymmetric app
7
7
  * credential and mints short-lived installation tokens from Queek on
8
8
  * demand, cached (encrypted) in its own database to near-expiry.
9
9
  *
@@ -13,7 +13,7 @@ import { defaultClearCachedTokenIfMatches } from "./store.js";
13
13
  * installation client goes through it.
14
14
  * - A merchant-API token refusal → drop it, re-mint once, retry once; a
15
15
  * second refusal propagates. Token refusal = any 401, or a 403 with
16
- * `api_key_revoked` / `api_key_expired` / `invalid_client_key` (rev 7).
16
+ * `api_key_revoked` / `api_key_expired` / `invalid_client_key`.
17
17
  * A merchant 403 `insufficient_scope` (stale grant) follows the same
18
18
  * drop + re-mint-once + retry-once path. A merchant 403
19
19
  * `app_token_revoked` is the app-wide kill switch (drop all + halt, no
@@ -22,17 +22,17 @@ import { defaultClearCachedTokenIfMatches } from "./store.js";
22
22
  * mint path below applies those rules.)
23
23
  * - Concurrent callers in one process share ONE in-flight mint per
24
24
  * installation (single-flight). Across containers two mints are harmless
25
- * by design: Queek keeps coexisting tokens valid (K=2 slots) and the
25
+ * by design: Queek keeps coexisting tokens valid (two token slots) and the
26
26
  * last write wins the shared cache row; a residual race self-heals via
27
27
  * re-mint on 401.
28
- * - Error handling exactly per the wire contract: 401 `invalid_client`
28
+ * - Error handling by status and code: 401 `invalid_client`
29
29
  * halts minting app-wide (loud log, no retry loop); 403 kill-switch
30
30
  * drops ALL cached tokens and halts; 404 `app_installation_gone` purges
31
31
  * the installation; 409 `app_installation_pending` retries later with
32
32
  * backoff — NEVER purges, NEVER halts (the persisted pending mark keeps
33
33
  * the row through restarts and resync's purge-absent step); 429 honors
34
- * `Retry-After` +
35
- * jitter with bounded retries; 5xx/network bounded exponential backoff.
34
+ * `Retry-After` + jitter with bounded retries; 5xx/network bounded
35
+ * exponential backoff.
36
36
  */
37
37
  /** Path of the app-credential API below the store host. */
38
38
  export const APP_API_PATH = "/api/v1/apps";
@@ -48,9 +48,16 @@ export function resolveAppApiBase(raw, allowedApiHosts = []) {
48
48
  const merchant = resolveApiBase(raw, allowedApiHosts);
49
49
  return `${merchant.slice(0, merchant.length - MERCHANT_API_PATH.length)}${APP_API_PATH}`;
50
50
  }
51
+ /** The app-API path that mints a token for one installation. */
51
52
  export function mintPath(installationId) {
52
53
  return `/installations/${encodeURIComponent(installationId)}/access_tokens`;
53
54
  }
55
+ /**
56
+ * Mints, caches and refreshes installation tokens for one app. Tokens are
57
+ * minted with the app's RSA key, cached encrypted in the installation store,
58
+ * and shared by concurrent callers in one process. Build one with
59
+ * {@link createAppTokenProvider} and pass it to `createInstallationClient`.
60
+ */
54
61
  export class AppTokenProvider {
55
62
  credential;
56
63
  store;
@@ -148,7 +155,7 @@ export class AppTokenProvider {
148
155
  }
149
156
  /**
150
157
  * Persist the 409 `app_installation_pending` mark for this installation
151
- * (store column — survives restarts, B2 review r2). Resync's purge-absent
158
+ * (store column — survives restarts). Resync's purge-absent
152
159
  * step keeps marked rows (the list covers active installations only).
153
160
  * Called by the mint path and by `resyncFromQueek`; idempotent, and a
154
161
  * no-op when the row is already gone.
@@ -239,8 +246,7 @@ export class AppTokenProvider {
239
246
  await this.handleAppEndpointError(error, { id: installationId, pid: installationPid });
240
247
  }
241
248
  if (error.status === 409 && isInstallationPending(error.code)) {
242
- // Pending installation (rev 8, mark persisted per B2 review
243
- // r2): retry later with backoff — NEVER purge, NEVER halt. The
249
+ // Pending installation: retry later with backoff — NEVER purge, NEVER halt. The
244
250
  // persisted mark keeps the row through restarts and resync's
245
251
  // purge-absent step (the list covers active rows only). After
246
252
  // the bounded budget the 409 propagates to the caller, which
@@ -263,7 +269,7 @@ export class AppTokenProvider {
263
269
  await this.sleep(this.jittered(error.retryAfterMs ?? MINT_BACKOFF_BASE_MS));
264
270
  continue;
265
271
  }
266
- if (error.status >= 500 || error.code === "network_error") {
272
+ if (error.status >= 500 || error.code === "network_error" || error.code === "request_timeout") {
267
273
  const backoff = Math.min(MINT_BACKOFF_MAX_MS, MINT_BACKOFF_BASE_MS * 2 ** attempt);
268
274
  await this.sleep(this.jittered(backoff));
269
275
  continue;
@@ -284,26 +290,23 @@ export class AppTokenProvider {
284
290
  headers.set("Authorization", `Bearer ${jwt}`);
285
291
  headers.set("Accept", "application/json");
286
292
  headers.set("User-Agent", this.userAgent);
293
+ const signal = requestSignal(undefined, DEFAULT_REQUEST_TIMEOUT_MS);
287
294
  let response;
295
+ let text;
288
296
  try {
289
- response = await this.fetchImpl(url, { method: "POST", headers });
297
+ response = await this.fetchImpl(url, { method: "POST", headers, signal });
298
+ text = await response.text();
290
299
  }
291
300
  catch (cause) {
292
- throw new QueekApiError({
293
- status: 0,
294
- code: "network_error",
295
- message: cause instanceof Error ? `Could not reach Queek: ${cause.message}` : "Could not reach Queek.",
296
- });
301
+ throw transportError(cause);
297
302
  }
298
- const text = await response.text();
299
- const parsed = text === "" ? null : tryParseJson(text);
300
303
  if (!response.ok) {
301
- throw queekApiErrorFromResponse(response.status, parsed, response.headers);
304
+ throw queekApiErrorFromResponse(response.status, text === "" ? null : tryParseJson(text), response.headers);
302
305
  }
303
306
  if (response.status !== 201) {
304
- throw new Error(`Unexpected mint status ${response.status} for installation ${installationPid} (expected 201).`);
307
+ throw new Error(`Unexpected mint status ${response.status} for installation ${installationPid} (expected 201). Check that apiBase is the Queek API host and retry; if it persists, report it with the request id.`);
305
308
  }
306
- return parseMintBody(parsed, installationPid, this.credential.keyId);
309
+ return parseMintBody(parseSuccessBody(response, text), installationPid, this.credential.keyId);
307
310
  }
308
311
  }
309
312
  function parseMintBody(body, installationPid, kid) {
@@ -311,7 +314,7 @@ function parseMintBody(body, installationPid, kid) {
311
314
  const token = typeof record.token === "string" && record.token !== "" ? record.token : null;
312
315
  const expiresAt = typeof record.expires_at === "string" ? record.expires_at : null;
313
316
  if (token === null || expiresAt === null || Number.isNaN(Date.parse(expiresAt))) {
314
- throw new Error(`Malformed mint response for installation ${installationPid}: expected {token, expires_at}.`);
317
+ throw new Error(`Malformed mint response for installation ${installationPid}: expected {token, expires_at}. Retry; if it persists, report it to Queek.`);
315
318
  }
316
319
  return { token, expiresAt, kid };
317
320
  }
@@ -340,8 +343,7 @@ export function createAppTokenProvider(options) {
340
343
  */
341
344
  export function createInstallationClient(options) {
342
345
  // Validated here, once, before any fetch — same rules as the static client.
343
- const probe = resolveApiBase(options.apiBase, options.allowedApiHosts ?? []);
344
- void probe;
346
+ resolveApiBase(options.apiBase, options.allowedApiHosts ?? []);
345
347
  const fetchImpl = options.fetchImpl ?? fetch;
346
348
  const userAgent = options.userAgent ?? "queek-app/1.0";
347
349
  const allowedApiHosts = options.allowedApiHosts ?? [];
@@ -356,6 +358,7 @@ export function createInstallationClient(options) {
356
358
  fetchImpl,
357
359
  userAgent,
358
360
  allowedApiHosts,
361
+ timeoutMs: options.timeoutMs,
359
362
  }),
360
363
  };
361
364
  }
@@ -394,7 +397,7 @@ export function createInstallationClient(options) {
394
397
  const fresh = await options.tokens.acquireToken(options.installationId);
395
398
  return (await clientForToken(fresh)).request(method, path, attemptOptions);
396
399
  }
397
- // Token refusals ONLY (rev 7): any 401, or a 403 carrying a
400
+ // Token refusals ONLY: any 401, or a 403 carrying a
398
401
  // revoked/expired-key code. Every other 403 (plan, mode) propagates
399
402
  // to the caller without burning a mint.
400
403
  if (!isTokenRefusal(error.status, error.code))
@@ -409,28 +412,9 @@ export function createInstallationClient(options) {
409
412
  }
410
413
  }
411
414
  async function requestWithRetry(method, path, retryOptions = {}) {
412
- const maxAttempts = Math.max(1, Math.floor(retryOptions.maxAttempts ?? 3));
413
- const baseDelayMs = retryOptions.baseDelayMs ?? 250;
414
- const maxDelayMs = retryOptions.maxDelayMs ?? 5000;
415
- const sleep = retryOptions.sleep ?? defaultSleep;
416
- const idempotencyKey = retryOptions.idempotencyKey;
417
- let lastError;
418
- for (let attempt = 0; attempt < maxAttempts; attempt++) {
419
- try {
420
- return await request(method, path, { ...retryOptions, idempotencyKey });
421
- }
422
- catch (error) {
423
- lastError = error;
424
- const retryable = error instanceof QueekApiError && (error.isRateLimited || error.code === "network_error");
425
- if (!retryable || attempt === maxAttempts - 1)
426
- throw error;
427
- const delay = error instanceof QueekApiError && error.isRateLimited && error.retryAfterMs !== undefined
428
- ? error.retryAfterMs
429
- : Math.min(maxDelayMs, baseDelayMs * 2 ** attempt);
430
- await sleep(delay);
431
- }
432
- }
433
- throw lastError;
415
+ // One key for every attempt: without it each `request()` would mint its
416
+ // own and a retried write could run twice.
417
+ return runWithRetry(method, retryOptions, (idempotencyKey) => request(method, path, { ...retryOptions, idempotencyKey }));
434
418
  }
435
419
  return {
436
420
  getStore: (signal) => request("GET", "/store", { signal }),
@@ -438,12 +422,3 @@ export function createInstallationClient(options) {
438
422
  requestWithRetry,
439
423
  };
440
424
  }
441
- function tryParseJson(text) {
442
- try {
443
- return JSON.parse(text);
444
- }
445
- catch {
446
- return { message: text.slice(0, 500) };
447
- }
448
- }
449
- //# sourceMappingURL=tokens.js.map
@@ -1,9 +1,8 @@
1
- import { type CoreDelivery, type DeliveryResult } from "./delivery.js";
1
+ import { type CoreDelivery, type DeliveryErrorHandler, type DeliveryResult } from "./delivery.js";
2
2
  import type { InstallationRecord, InstallationStore } from "./store.js";
3
3
  /**
4
- * Framework-agnostic receiver for Queek topic deliveries
5
- * (`DeliverWebhookJob` in queek_backend, one signed POST per installation
6
- * endpoint) in three thin layers: layer 1
4
+ * Framework-agnostic receiver for Queek topic deliveries (one signed POST
5
+ * per installation endpoint) in three thin layers: layer 1
7
6
  * `handleWebhookDelivery(input, options)` takes plain data (untouched body
8
7
  * bytes + headers) and returns a plain `{ status, body }` result — zero
9
8
  * request/response types, so whatever request object each framework
@@ -23,7 +22,7 @@ import type { InstallationRecord, InstallationStore } from "./store.js";
23
22
  * installations per app are few). Apps that carry their own routing hint
24
23
  * may pass `resolveSecret` instead.
25
24
  *
26
- * Dedupe: Queek retries a delivery for ~4h until it sees 2xx, so every
25
+ * Dedupe: Queek retries a delivery until it sees 2xx, so every
27
26
  * `webhook-id` is processed AT MOST once — the header id is claimed
28
27
  * atomically up front (exactly one concurrent same-id delivery runs the
29
28
  * handler) and a repeat answers 200 WITHOUT re-running it. A throwing
@@ -33,6 +32,7 @@ import type { InstallationRecord, InstallationStore } from "./store.js";
33
32
  * non-2xx.
34
33
  */
35
34
  export declare const QUEEK_TOPIC_HEADER = "X-Queek-Topic";
35
+ /** The signed envelope of one topic delivery. `data` is the topic payload. */
36
36
  export interface QueekWebhookEnvelope<TData = unknown> {
37
37
  id: string;
38
38
  topic: string;
@@ -50,6 +50,7 @@ export interface SecretResolution {
50
50
  installationId: string;
51
51
  secret: string;
52
52
  }
53
+ /** Options for the topic webhook receiver. `store` and `handlers` are required. */
53
54
  export interface WebhookHandlerOptions {
54
55
  store: InstallationStore;
55
56
  /** `topic → handler`, e.g. `{ "orders/updated": onOrderUpdated }`. */
@@ -62,11 +63,35 @@ export interface WebhookHandlerOptions {
62
63
  }) => Promise<SecretResolution | null>;
63
64
  nowSeconds?: number;
64
65
  maxSkewSeconds?: number;
66
+ /**
67
+ * Called with the error a handler threw, before the 500 goes back. Without
68
+ * it the error is logged to stderr (secrets redacted).
69
+ */
70
+ onError?: DeliveryErrorHandler;
65
71
  }
66
72
  /**
67
73
  * Layer 1: handle one signed Queek topic delivery from plain data — no
68
74
  * `Request`, no framework. Same options, same behaviour, same
69
75
  * errors/status codes at every layer.
76
+ *
77
+ * Answers 401 for a missing header, an unknown installation, a stale
78
+ * timestamp or a bad signature; 400 for a body that is not a JSON envelope;
79
+ * 200 for a handled, repeated or unhandled-topic delivery; 500 when your
80
+ * handler throws (the claim is released so Queek's retry can land).
81
+ *
82
+ * @example
83
+ * const result = await handleWebhookDelivery(
84
+ * { rawBody, headers },
85
+ * {
86
+ * store,
87
+ * handlers: {
88
+ * "orders/updated": async (envelope, { installation }) => {
89
+ * await syncOrder(installation.installationId, envelope.data);
90
+ * },
91
+ * },
92
+ * },
93
+ * );
94
+ * // reply with result.status and result.body
70
95
  */
71
96
  export declare function handleWebhookDelivery(input: CoreDelivery, options: WebhookHandlerOptions): Promise<DeliveryResult>;
72
97
  /**
@@ -75,4 +100,3 @@ export declare function handleWebhookDelivery(input: CoreDelivery, options: Webh
75
100
  * `Response`. Only `POST` is served; anything else answers 405.
76
101
  */
77
102
  export declare function handleWebhookRequest(request: Request, options: WebhookHandlerOptions): Promise<Response>;
78
- //# sourceMappingURL=webhooks.d.ts.map
package/dist/webhooks.js CHANGED
@@ -1,9 +1,8 @@
1
- import { decodeBody, readHeader, toResponse } from "./delivery.js";
2
- import { MAX_TIMESTAMP_SKEW_SECONDS, verifyQueekSignature, WEBHOOK_ID_HEADER, WEBHOOK_SIGNATURE_HEADER, WEBHOOK_TIMESTAMP_HEADER, } from "./signatures.js";
1
+ import { decodeBody, readHeader, reportDeliveryFailure, toResponse, } from "./delivery.js";
2
+ import { isFreshTimestamp, MAX_TIMESTAMP_SKEW_SECONDS, verifyQueekSignature, WEBHOOK_ID_HEADER, WEBHOOK_SIGNATURE_HEADER, WEBHOOK_TIMESTAMP_HEADER, } from "./signatures.js";
3
3
  /**
4
- * Framework-agnostic receiver for Queek topic deliveries
5
- * (`DeliverWebhookJob` in queek_backend, one signed POST per installation
6
- * endpoint) in three thin layers: layer 1
4
+ * Framework-agnostic receiver for Queek topic deliveries (one signed POST
5
+ * per installation endpoint) in three thin layers: layer 1
7
6
  * `handleWebhookDelivery(input, options)` takes plain data (untouched body
8
7
  * bytes + headers) and returns a plain `{ status, body }` result — zero
9
8
  * request/response types, so whatever request object each framework
@@ -23,7 +22,7 @@ import { MAX_TIMESTAMP_SKEW_SECONDS, verifyQueekSignature, WEBHOOK_ID_HEADER, WE
23
22
  * installations per app are few). Apps that carry their own routing hint
24
23
  * may pass `resolveSecret` instead.
25
24
  *
26
- * Dedupe: Queek retries a delivery for ~4h until it sees 2xx, so every
25
+ * Dedupe: Queek retries a delivery until it sees 2xx, so every
27
26
  * `webhook-id` is processed AT MOST once — the header id is claimed
28
27
  * atomically up front (exactly one concurrent same-id delivery runs the
29
28
  * handler) and a repeat answers 200 WITHOUT re-running it. A throwing
@@ -62,6 +61,25 @@ async function defaultResolveSecret(store, rawBody, headers, envelope) {
62
61
  * Layer 1: handle one signed Queek topic delivery from plain data — no
63
62
  * `Request`, no framework. Same options, same behaviour, same
64
63
  * errors/status codes at every layer.
64
+ *
65
+ * Answers 401 for a missing header, an unknown installation, a stale
66
+ * timestamp or a bad signature; 400 for a body that is not a JSON envelope;
67
+ * 200 for a handled, repeated or unhandled-topic delivery; 500 when your
68
+ * handler throws (the claim is released so Queek's retry can land).
69
+ *
70
+ * @example
71
+ * const result = await handleWebhookDelivery(
72
+ * { rawBody, headers },
73
+ * {
74
+ * store,
75
+ * handlers: {
76
+ * "orders/updated": async (envelope, { installation }) => {
77
+ * await syncOrder(installation.installationId, envelope.data);
78
+ * },
79
+ * },
80
+ * },
81
+ * );
82
+ * // reply with result.status and result.body
65
83
  */
66
84
  export async function handleWebhookDelivery(input, options) {
67
85
  const maxSkew = options.maxSkewSeconds ?? MAX_TIMESTAMP_SKEW_SECONDS;
@@ -95,8 +113,7 @@ export async function handleWebhookDelivery(input, options) {
95
113
  // lookup above deliberately skips it so a stale delivery cannot be
96
114
  // misattributed before it is rejected.
97
115
  const now = options.nowSeconds ?? Math.floor(Date.now() / 1000);
98
- const ts = Number(timestamp);
99
- if (!Number.isFinite(ts) || Math.abs(now - ts) > maxSkew) {
116
+ if (!isFreshTimestamp(timestamp, now, maxSkew)) {
100
117
  return { status: 401, body: { ok: false, error: "stale timestamp" } };
101
118
  }
102
119
  // Freshness was enforced above; this re-checks the MAC only, so a
@@ -124,8 +141,9 @@ export async function handleWebhookDelivery(input, options) {
124
141
  try {
125
142
  await handler(envelope, { installation, topic, eventId: id });
126
143
  }
127
- catch {
144
+ catch (error) {
128
145
  await options.store.releaseWebhookId(id);
146
+ reportDeliveryFailure(options.onError, error, { stage: "webhook", eventId: id, topic });
129
147
  return { status: 500, body: { ok: false, error: "handler_failed" } };
130
148
  }
131
149
  return { status: 200, body: { ok: true } };
@@ -144,4 +162,3 @@ export async function handleWebhookRequest(request, options) {
144
162
  headers: request.headers,
145
163
  }, options));
146
164
  }
147
- //# sourceMappingURL=webhooks.js.map
package/package.json CHANGED
@@ -1,17 +1,33 @@
1
1
  {
2
2
  "name": "@usequeek/app-sdk",
3
- "version": "0.6.1",
3
+ "version": "0.7.0",
4
4
  "private": false,
5
5
  "license": "MIT",
6
- "description": "SDK for Queek installable apps: webhook signature verification, install handlers, typed Merchant API client, webhook dispatch, encrypted installation store.",
6
+ "author": "Queekx Technology LTD",
7
+ "description": "SDK for Queek apps: signed install and webhook handlers, a typed Merchant API client with retries and pagination, installation tokens and an encrypted installation store.",
8
+ "keywords": [
9
+ "queek",
10
+ "queek-app",
11
+ "merchant-api",
12
+ "webhooks",
13
+ "webhook-signature",
14
+ "commerce",
15
+ "sdk",
16
+ "typescript"
17
+ ],
7
18
  "repository": {
8
19
  "type": "git",
9
20
  "url": "git+https://github.com/usequeek/app-sdk.git"
10
21
  },
22
+ "bugs": {
23
+ "url": "https://github.com/usequeek/app-sdk/issues"
24
+ },
25
+ "homepage": "https://docs.usequeek.com/docs/apps/sdk",
11
26
  "publishConfig": {
12
27
  "access": "public"
13
28
  },
14
29
  "type": "module",
30
+ "sideEffects": false,
15
31
  "main": "./dist/index.js",
16
32
  "types": "./dist/index.d.ts",
17
33
  "exports": {
@@ -46,7 +62,7 @@
46
62
  "typecheck": "tsc --noEmit -p tsconfig.json",
47
63
  "typecheck:tests": "tsc --noEmit -p tsconfig.tests.json",
48
64
  "lint": "biome check .",
49
- "test": "vitest run",
65
+ "test": "node scripts/check-public-text.mjs && node --test scripts/check-public-text.test.mjs && vitest run",
50
66
  "verify-package": "node scripts/verify-package.mjs",
51
67
  "gen:merchant": "node scripts/gen-merchant-types.mjs",
52
68
  "check:merchant-snapshot": "node scripts/check-merchant-snapshot.mjs",
@@ -70,13 +86,14 @@
70
86
  "@types/pg": "^8.23.1",
71
87
  "@types/react": "^19.3.0",
72
88
  "@types/react-dom": "^19.3.0",
89
+ "esbuild": "0.28.2",
73
90
  "hono": "4.13.9",
74
91
  "jsdom": "^28.1.0",
75
92
  "openapi-typescript": "7.13.0",
76
93
  "react": "^19.3.0",
77
94
  "react-dom": "^19.3.0",
78
95
  "typescript": "5.9.3",
79
- "vitest": "3.2.4"
96
+ "vitest": "4.1.11"
80
97
  },
81
98
  "engines": {
82
99
  "node": ">=22.14"
@@ -1 +0,0 @@
1
- {"version":3,"file":"app-auth.d.ts","sourceRoot":"","sources":["../src/app-auth.ts"],"names":[],"mappings":"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"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"app-auth.js","sourceRoot":"","sources":["../src/app-auth.ts"],"names":[],"mappings":"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"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"auth-fetch.d.ts","sourceRoot":"","sources":["../src/auth-fetch.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;GAoBG;AAEH,OAAO,EAAE,KAAK,gBAAgB,EAAE,KAAK,eAAe,EAAgC,MAAM,YAAY,CAAC;AAEvG;;;;;;;GAOG;AACH,eAAO,MAAM,kBAAkB,gBAAgB,CAAC;AAEhD,wEAAwE;AACxE,eAAO,MAAM,uBAAuB,OAAO,CAAC;AAE5C,MAAM,WAAW,gBAAgB;IAC/B;;;;;OAKG;IACH,QAAQ,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,OAAO,CAAC,MAAM,CAAC,CAAC;IAC7C,iEAAiE;IACjE,eAAe,EAAE,MAAM,CAAC;IACxB,4DAA4D;IAC5D,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,+EAA+E;IAC/E,UAAU,CAAC,EAAE,eAAe,CAAC;IAC7B;;;OAGG;IACH,YAAY,CAAC,EAAE,MAAM,EAAE,CAAC;IACxB,oDAAoD;IACpD,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,gFAAgF;IAChF,YAAY,CAAC,EAAE,gBAAgB,CAAC;IAChC;;;;OAIG;IACH,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,2DAA2D;IAC3D,SAAS,CAAC,EAAE,OAAO,KAAK,CAAC;IACzB,6DAA6D;IAC7D,OAAO,CAAC,EAAE,MAAM,MAAM,CAAC;IACvB,6EAA6E;IAC7E,UAAU,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,IAAI,CAAC;CACpC;AAED,MAAM,WAAW,aAAa;IAC5B,+HAA+H;IAC/H,KAAK,EAAE,CAAC,KAAK,EAAE,MAAM,GAAG,GAAG,GAAG,OAAO,EAAE,IAAI,CAAC,EAAE,WAAW,KAAK,OAAO,CAAC,QAAQ,CAAC,CAAC;IAChF,kFAAkF;IAClF,UAAU,EAAE,MAAM,MAAM,GAAG,IAAI,CAAC;IAChC,iFAAiF;IACjF,KAAK,EAAE,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAAC;IAC9B,kEAAkE;IAClE,OAAO,EAAE,MAAM,OAAO,CAAC,MAAM,CAAC,CAAC;IAC/B,6CAA6C;IAC7C,OAAO,EAAE,MAAM,IAAI,CAAC;CACrB;AAeD,gEAAgE;AAChE,wBAAgB,eAAe,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,GAAE,MAA2B,GAAG,MAAM,GAAG,IAAI,CAO/F;AAED;;;;GAIG;AACH,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,GAAE,MAA2B,GAAG,MAAM,GAAG,IAAI,CAWhG;AAED,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,gBAAgB,GAAG,aAAa,CAqNzE"}