@agent-score/commerce 2.3.0 → 2.4.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 (66) hide show
  1. package/README.md +6 -6
  2. package/dist/challenge/index.d.mts +4 -4
  3. package/dist/challenge/index.d.ts +4 -4
  4. package/dist/challenge/index.js.map +1 -1
  5. package/dist/challenge/index.mjs.map +1 -1
  6. package/dist/{checkout-ChyOi7aU.d.ts → checkout-B-MIzYzW.d.ts} +8 -11
  7. package/dist/{checkout-Ceo1_rVJ.d.mts → checkout-Bn7ZKIBD.d.mts} +8 -11
  8. package/dist/core.d.mts +4 -6
  9. package/dist/core.d.ts +4 -6
  10. package/dist/core.js +1 -1
  11. package/dist/core.js.map +1 -1
  12. package/dist/core.mjs +1 -1
  13. package/dist/core.mjs.map +1 -1
  14. package/dist/discovery/index.d.mts +10 -9
  15. package/dist/discovery/index.d.ts +10 -9
  16. package/dist/discovery/index.js +44 -6
  17. package/dist/discovery/index.js.map +1 -1
  18. package/dist/discovery/index.mjs +44 -6
  19. package/dist/discovery/index.mjs.map +1 -1
  20. package/dist/identity/express.js +13 -13
  21. package/dist/identity/express.js.map +1 -1
  22. package/dist/identity/express.mjs +13 -13
  23. package/dist/identity/express.mjs.map +1 -1
  24. package/dist/identity/fastify.js +13 -13
  25. package/dist/identity/fastify.js.map +1 -1
  26. package/dist/identity/fastify.mjs +13 -13
  27. package/dist/identity/fastify.mjs.map +1 -1
  28. package/dist/identity/hono.js +13 -13
  29. package/dist/identity/hono.js.map +1 -1
  30. package/dist/identity/hono.mjs +13 -13
  31. package/dist/identity/hono.mjs.map +1 -1
  32. package/dist/identity/nextjs.js +13 -13
  33. package/dist/identity/nextjs.js.map +1 -1
  34. package/dist/identity/nextjs.mjs +13 -13
  35. package/dist/identity/nextjs.mjs.map +1 -1
  36. package/dist/identity/policy.js.map +1 -1
  37. package/dist/identity/policy.mjs.map +1 -1
  38. package/dist/identity/web.js +13 -13
  39. package/dist/identity/web.js.map +1 -1
  40. package/dist/identity/web.mjs +13 -13
  41. package/dist/identity/web.mjs.map +1 -1
  42. package/dist/index.d.mts +12 -13
  43. package/dist/index.d.ts +12 -13
  44. package/dist/index.js +86 -65
  45. package/dist/index.js.map +1 -1
  46. package/dist/index.mjs +84 -65
  47. package/dist/index.mjs.map +1 -1
  48. package/dist/{default_rails-DtR_E9N9.d.ts → network_kind-BIJM2peR.d.ts} +22 -8
  49. package/dist/{default_rails-K25PtWrL.d.mts → network_kind-C0EMkdzz.d.mts} +22 -8
  50. package/dist/payment/index.d.mts +16 -26
  51. package/dist/payment/index.d.ts +16 -26
  52. package/dist/payment/index.js +62 -57
  53. package/dist/payment/index.js.map +1 -1
  54. package/dist/payment/index.mjs +62 -57
  55. package/dist/payment/index.mjs.map +1 -1
  56. package/dist/{pricing-B3-aKxSz.d.ts → pricing-CytRwhC2.d.ts} +1 -1
  57. package/dist/{pricing-BReyZiqN.d.mts → pricing-KHDqMLd7.d.mts} +1 -1
  58. package/dist/{rail_spec-B1239jPp.d.mts → rail_spec-BFZmW9RN.d.mts} +3 -4
  59. package/dist/{rail_spec-B1239jPp.d.ts → rail_spec-BFZmW9RN.d.ts} +3 -4
  60. package/dist/stripe-multichain/index.d.mts +2 -9
  61. package/dist/stripe-multichain/index.d.ts +2 -9
  62. package/dist/stripe-multichain/index.js.map +1 -1
  63. package/dist/stripe-multichain/index.mjs.map +1 -1
  64. package/dist/{wwwauthenticate-D_FMnPgU.d.mts → wwwauthenticate-CVaGUMjU.d.mts} +8 -6
  65. package/dist/{wwwauthenticate-D_FMnPgU.d.ts → wwwauthenticate-CVaGUMjU.d.ts} +8 -6
  66. package/package.json +9 -8
package/dist/index.mjs CHANGED
@@ -329,19 +329,19 @@ function stableStringify(value) {
329
329
  }
330
330
  if (!Number.isInteger(value)) {
331
331
  throw new Error(
332
- `UCP profile canonicalization rejects non-integer Number ${value}. Use a decimal string (e.g. "9.99") for monetary or fractional fields to preserve cross-language byte-parity.`
332
+ `UCP profile canonicalization rejects non-integer Number ${value}. Use a decimal string (e.g. "9.99") for monetary or fractional fields so the signed canonical bytes stay stable for any verifier.`
333
333
  );
334
334
  }
335
335
  if (!Number.isSafeInteger(value)) {
336
336
  throw new Error(
337
- `stableStringify: integer ${value} exceeds Number.MAX_SAFE_INTEGER. For values >2^53, use a decimal string to preserve cross-language byte parity.`
337
+ `stableStringify: integer ${value} exceeds Number.MAX_SAFE_INTEGER. For values >2^53, use a decimal string to keep the signed bytes stable across implementations.`
338
338
  );
339
339
  }
340
340
  }
341
341
  if (typeof value === "string") {
342
342
  if (value.includes("\u2028") || value.includes("\u2029")) {
343
343
  throw new Error(
344
- "stableStringify: strings containing U+2028 (LINE SEPARATOR) or U+2029 (PARAGRAPH SEPARATOR) are not allowed; cross-language byte parity requires neither be present (Node JSON.stringify on older V8 escapes them; Python json.dumps with ensure_ascii=False does not)."
344
+ "stableStringify: strings containing U+2028 (LINE SEPARATOR) or U+2029 (PARAGRAPH SEPARATOR) are not allowed; stable canonical bytes require neither be present (some JSON encoders escape them, others emit them raw)."
345
345
  );
346
346
  }
347
347
  return JSON.stringify(value);
@@ -361,7 +361,7 @@ function stableStringify(value) {
361
361
  for (const k of keys) {
362
362
  if (k.includes("\u2028") || k.includes("\u2029")) {
363
363
  throw new Error(
364
- "stableStringify: object keys containing U+2028 (LINE SEPARATOR) or U+2029 (PARAGRAPH SEPARATOR) are not allowed; cross-language byte parity (Node JSON.stringify on older V8 escapes them; Python json.dumps with ensure_ascii=False does not)."
364
+ "stableStringify: object keys containing U+2028 (LINE SEPARATOR) or U+2029 (PARAGRAPH SEPARATOR) are not allowed; stable canonical bytes require neither be present (some JSON encoders escape them, others emit them raw)."
365
365
  );
366
366
  }
367
367
  }
@@ -20328,6 +20328,53 @@ var init_networks = __esm({
20328
20328
  }
20329
20329
  });
20330
20330
 
20331
+ // src/payment/amounts.ts
20332
+ function usdToAtomic(usd, opts) {
20333
+ const { decimals } = opts;
20334
+ if (!Number.isInteger(decimals) || decimals < 0) {
20335
+ throw new RangeError(`decimals must be a non-negative integer, got ${decimals}`);
20336
+ }
20337
+ if (typeof usd === "number") {
20338
+ if (!Number.isFinite(usd)) {
20339
+ throw new RangeError(`usd must be finite, got ${usd}`);
20340
+ }
20341
+ if (usd < 0) {
20342
+ throw new RangeError(`usd must be non-negative, got ${usd}`);
20343
+ }
20344
+ }
20345
+ const s = (typeof usd === "number" ? usd.toString() : usd).trim();
20346
+ if (s.startsWith("-")) {
20347
+ throw new RangeError(`usd must be non-negative, got ${s}`);
20348
+ }
20349
+ if (s === "NaN" || s === "Infinity") {
20350
+ throw new RangeError(`usd must be finite, got ${s}`);
20351
+ }
20352
+ const match = /^(\d*)(?:\.(\d*))?$/.exec(s);
20353
+ if (!match || match[1] === "" && (match[2] === void 0 || match[2] === "")) {
20354
+ throw new SyntaxError(`invalid usd value: ${JSON.stringify(usd)}`);
20355
+ }
20356
+ const intPart = match[1] || "0";
20357
+ const fracPart = match[2] ?? "";
20358
+ if (fracPart.length <= decimals) {
20359
+ return BigInt(intPart + fracPart.padEnd(decimals, "0"));
20360
+ }
20361
+ const kept = fracPart.slice(0, decimals);
20362
+ const roundDigit = fracPart[decimals];
20363
+ let result = BigInt(intPart + kept);
20364
+ if (roundDigit >= "5") {
20365
+ result += 1n;
20366
+ }
20367
+ return result;
20368
+ }
20369
+ function formatUsdCents(cents, decimals = 2) {
20370
+ return (cents / 100).toFixed(decimals);
20371
+ }
20372
+ var init_amounts = __esm({
20373
+ "src/payment/amounts.ts"() {
20374
+ "use strict";
20375
+ }
20376
+ });
20377
+
20331
20378
  // src/payment/rails.ts
20332
20379
  function lookupRail(name) {
20333
20380
  return rails[name];
@@ -20427,8 +20474,7 @@ function buildPaymentRequestBlob({
20427
20474
  const decimalsResolved = decimals ?? railDef?.decimals ?? 6;
20428
20475
  const currencyResolved = currency ?? railDef?.currency ?? "usd";
20429
20476
  const chainIdResolved = chainId ?? railDef?.chainId;
20430
- const amountNum = typeof amountUsd === "string" ? Number(amountUsd) : amountUsd;
20431
- const amountRaw = BigInt(Math.round(amountNum * 10 ** decimalsResolved)).toString();
20477
+ const amountRaw = usdToAtomic(amountUsd, { decimals: decimalsResolved }).toString();
20432
20478
  const blob = { amount: amountRaw, currency: currencyResolved, decimals: decimalsResolved };
20433
20479
  if (recipient) blob.recipient = recipient;
20434
20480
  const methodDetails = {};
@@ -20455,6 +20501,7 @@ function paymentDirective({
20455
20501
  var init_directive = __esm({
20456
20502
  "src/payment/directive.ts"() {
20457
20503
  "use strict";
20504
+ init_amounts();
20458
20505
  init_rails();
20459
20506
  }
20460
20507
  });
@@ -21162,7 +21209,7 @@ function createAgentScoreCore(options) {
21162
21209
  } = options;
21163
21210
  const baseUrl = stripTrailingSlashes(rawBaseUrl);
21164
21211
  const agentMemoryHint = buildAgentMemoryHint();
21165
- const defaultUa = `@agent-score/commerce@${"2.3.0"}`;
21212
+ const defaultUa = `@agent-score/commerce@${"2.4.0"}`;
21166
21213
  const userAgentHeader = userAgent ? `${userAgent} (${defaultUa})` : defaultUa;
21167
21214
  const sdk = new AgentScore({ apiKey, baseUrl, userAgent: userAgentHeader });
21168
21215
  const sessionSdkCache = /* @__PURE__ */ new Map();
@@ -21502,6 +21549,18 @@ async function extractSolanaSignerFromCredential(credential) {
21502
21549
  }
21503
21550
  }
21504
21551
  async function extractPaymentSigner(request, x402PaymentHeader) {
21552
+ if (x402PaymentHeader) {
21553
+ try {
21554
+ const decoded = atob(x402PaymentHeader);
21555
+ const parsed = JSON.parse(decoded);
21556
+ const from9 = parsed?.payload?.authorization?.from;
21557
+ if (typeof from9 === "string" && /^0x[0-9a-fA-F]{40}$/.test(from9)) {
21558
+ return { address: from9.toLowerCase(), network: "evm" };
21559
+ }
21560
+ } catch (err) {
21561
+ console.warn("[gate] x402 signer extraction failed:", err instanceof Error ? err.message : err);
21562
+ }
21563
+ }
21505
21564
  const authHeader = request.headers.get("authorization");
21506
21565
  if (authHeader) {
21507
21566
  try {
@@ -21521,18 +21580,6 @@ async function extractPaymentSigner(request, x402PaymentHeader) {
21521
21580
  console.warn("[gate] MPP signer extraction failed:", err instanceof Error ? err.message : err);
21522
21581
  }
21523
21582
  }
21524
- if (x402PaymentHeader) {
21525
- try {
21526
- const decoded = atob(x402PaymentHeader);
21527
- const parsed = JSON.parse(decoded);
21528
- const from9 = parsed?.payload?.authorization?.from;
21529
- if (typeof from9 === "string" && /^0x[0-9a-fA-F]{40}$/.test(from9)) {
21530
- return { address: from9.toLowerCase(), network: "evm" };
21531
- }
21532
- } catch (err) {
21533
- console.warn("[gate] x402 signer extraction failed:", err instanceof Error ? err.message : err);
21534
- }
21535
- }
21536
21583
  return null;
21537
21584
  }
21538
21585
  async function extractPaymentSignerFromAuth(authHeader, x402PaymentHeader) {
@@ -23305,10 +23352,9 @@ var Checkout = class {
23305
23352
  ...gate.cacheSeconds !== void 0 && { cacheSeconds: gate.cacheSeconds },
23306
23353
  ...gate.chain !== void 0 && { chain: gate.chain },
23307
23354
  // Auto-default `createSessionOnMissing` from gate config when the merchant
23308
- // didn't supply one. Matches python-commerce's behavior every gated route
23309
- // gets the bootstrap session-mint UX out of the box. Merchants who need
23310
- // custom session context or onBeforeSession side effects (goods merchants
23311
- // pre-minting an order_id) supply their own config instead.
23355
+ // didn't supply one, so every gated route gets the bootstrap session-mint UX
23356
+ // out of the box. Merchants who need custom session context or onBeforeSession
23357
+ // side effects (goods merchants pre-minting an order_id) supply their own config.
23312
23358
  createSessionOnMissing: gate.createSessionOnMissing ?? {
23313
23359
  apiKey: gate.apiKey,
23314
23360
  ...gate.baseUrl !== void 0 && { baseUrl: gate.baseUrl },
@@ -24045,47 +24091,8 @@ init_wwwauthenticate();
24045
24091
  init_directive();
24046
24092
  init_wwwauthenticate();
24047
24093
 
24048
- // src/payment/amounts.ts
24049
- function usdToAtomic(usd, opts) {
24050
- const { decimals } = opts;
24051
- if (!Number.isInteger(decimals) || decimals < 0) {
24052
- throw new RangeError(`decimals must be a non-negative integer, got ${decimals}`);
24053
- }
24054
- if (typeof usd === "number") {
24055
- if (!Number.isFinite(usd)) {
24056
- throw new RangeError(`usd must be finite, got ${usd}`);
24057
- }
24058
- if (usd < 0) {
24059
- throw new RangeError(`usd must be non-negative, got ${usd}`);
24060
- }
24061
- }
24062
- const s = (typeof usd === "number" ? usd.toString() : usd).trim();
24063
- if (s.startsWith("-")) {
24064
- throw new RangeError(`usd must be non-negative, got ${s}`);
24065
- }
24066
- if (s === "NaN" || s === "Infinity") {
24067
- throw new RangeError(`usd must be finite, got ${s}`);
24068
- }
24069
- const match = /^(\d*)(?:\.(\d*))?$/.exec(s);
24070
- if (!match || match[1] === "" && (match[2] === void 0 || match[2] === "")) {
24071
- throw new SyntaxError(`invalid usd value: ${JSON.stringify(usd)}`);
24072
- }
24073
- const intPart = match[1] || "0";
24074
- const fracPart = match[2] ?? "";
24075
- if (fracPart.length <= decimals) {
24076
- return BigInt(intPart + fracPart.padEnd(decimals, "0"));
24077
- }
24078
- const kept = fracPart.slice(0, decimals);
24079
- const roundDigit = fracPart[decimals];
24080
- let result = BigInt(intPart + kept);
24081
- if (roundDigit >= "5") {
24082
- result += 1n;
24083
- }
24084
- return result;
24085
- }
24086
- function formatUsdCents(cents, decimals = 2) {
24087
- return (cents / 100).toFixed(decimals);
24088
- }
24094
+ // src/payment/index.ts
24095
+ init_amounts();
24089
24096
 
24090
24097
  // src/payment/solana.ts
24091
24098
  async function loadSolanaFeePayer(opts) {
@@ -24109,6 +24116,7 @@ async function loadSolanaFeePayer(opts) {
24109
24116
  }
24110
24117
 
24111
24118
  // src/payment/compose_rails.ts
24119
+ init_amounts();
24112
24120
  init_usdc();
24113
24121
  var warnedStripeBelowMinimum = false;
24114
24122
  function buildMppxComposeRails(opts) {
@@ -24153,7 +24161,13 @@ init_usdc();
24153
24161
  function buildDefaultCheckoutRails(opts) {
24154
24162
  const out = {};
24155
24163
  if (opts.tempo) {
24156
- out.tempo = { recipient: "", ...RAIL_SPEC_DEFAULTS.tempo, ...opts.tempo };
24164
+ const merged = { recipient: "", ...RAIL_SPEC_DEFAULTS.tempo, ...opts.tempo };
24165
+ if (merged.testnet) {
24166
+ if (opts.tempo.network === void 0) merged.network = "tempo-testnet";
24167
+ if (opts.tempo.chainId === void 0) merged.chainId = 42431;
24168
+ if (opts.tempo.token === void 0) merged.token = USDC.tempo.testnet.address;
24169
+ }
24170
+ out.tempo = merged;
24157
24171
  }
24158
24172
  if (opts.x402Base) {
24159
24173
  const merged = { recipient: "", ...RAIL_SPEC_DEFAULTS.x402Base, ...opts.x402Base };
@@ -24208,6 +24222,9 @@ function buildSuccessNextSteps(opts) {
24208
24222
  // src/discovery/index.ts
24209
24223
  init_well_known();
24210
24224
 
24225
+ // src/checkout_compute_first.ts
24226
+ init_amounts();
24227
+
24211
24228
  // src/quote_cache.ts
24212
24229
  import { createHash as createHash2 } from "crypto";
24213
24230
 
@@ -24810,7 +24827,9 @@ export {
24810
24827
  hasPaymentHeader,
24811
24828
  hasX402Header,
24812
24829
  hashOperatorToken,
24830
+ isEvmNetwork,
24813
24831
  isFixableDenial,
24832
+ isSolanaNetwork,
24814
24833
  loadSolanaFeePayer,
24815
24834
  loadUCPSigningKeyFromEnv,
24816
24835
  makeMppxComposeHook,