@astrasyncai/verification-gateway 5.21.2 → 5.22.1

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 (87) hide show
  1. package/CHANGELOG.md +20 -0
  2. package/README.md +19 -7
  3. package/dist/adapters/express.js +60 -11
  4. package/dist/adapters/express.js.map +1 -1
  5. package/dist/adapters/express.mjs +60 -11
  6. package/dist/adapters/express.mjs.map +1 -1
  7. package/dist/adapters/mcp.js +34 -3
  8. package/dist/adapters/mcp.js.map +1 -1
  9. package/dist/adapters/mcp.mjs +34 -3
  10. package/dist/adapters/mcp.mjs.map +1 -1
  11. package/dist/adapters/nextjs.js +60 -11
  12. package/dist/adapters/nextjs.js.map +1 -1
  13. package/dist/adapters/nextjs.mjs +60 -11
  14. package/dist/adapters/nextjs.mjs.map +1 -1
  15. package/dist/adapters/sdk.js +1 -1
  16. package/dist/adapters/sdk.js.map +1 -1
  17. package/dist/adapters/sdk.mjs +1 -1
  18. package/dist/adapters/sdk.mjs.map +1 -1
  19. package/dist/agent/index.js +1 -1
  20. package/dist/agent/index.js.map +1 -1
  21. package/dist/agent/index.mjs +1 -1
  22. package/dist/agent/index.mjs.map +1 -1
  23. package/dist/bin/astrasync-claude-hook.js +1 -1
  24. package/dist/bin/astrasync-codex-hook.js +1 -1
  25. package/dist/bin/astrasync-guard.js +1 -1
  26. package/dist/bin/astrasync.js +1 -1
  27. package/dist/browser/background.js +1 -1
  28. package/dist/browser/background.js.map +1 -1
  29. package/dist/browser/background.mjs +1 -1
  30. package/dist/browser/background.mjs.map +1 -1
  31. package/dist/cli/index.js +1 -1
  32. package/dist/cli/index.js.map +1 -1
  33. package/dist/cli/index.mjs +1 -1
  34. package/dist/cli/index.mjs.map +1 -1
  35. package/dist/codex/index.js +1 -1
  36. package/dist/codex/index.js.map +1 -1
  37. package/dist/codex/index.mjs +1 -1
  38. package/dist/codex/index.mjs.map +1 -1
  39. package/dist/cursor/extension.js +1 -1
  40. package/dist/cursor/extension.js.map +1 -1
  41. package/dist/cursor/extension.mjs +1 -1
  42. package/dist/cursor/extension.mjs.map +1 -1
  43. package/dist/edge-config.js +1 -1
  44. package/dist/edge-config.js.map +1 -1
  45. package/dist/edge-config.mjs +1 -1
  46. package/dist/edge-config.mjs.map +1 -1
  47. package/dist/edge-core/index.d.mts +4 -1
  48. package/dist/edge-core/index.d.ts +4 -1
  49. package/dist/edge-core/index.js +45 -15
  50. package/dist/edge-core/index.js.map +1 -1
  51. package/dist/edge-core/index.mjs +45 -15
  52. package/dist/edge-core/index.mjs.map +1 -1
  53. package/dist/gateway/gateway.js +1 -1
  54. package/dist/gateway/gateway.js.map +1 -1
  55. package/dist/gateway/gateway.mjs +1 -1
  56. package/dist/gateway/gateway.mjs.map +1 -1
  57. package/dist/index.d.mts +44 -6
  58. package/dist/index.d.ts +44 -6
  59. package/dist/index.js +71 -14
  60. package/dist/index.js.map +1 -1
  61. package/dist/index.mjs +71 -14
  62. package/dist/index.mjs.map +1 -1
  63. package/dist/metadata-capture.d.mts +5 -3
  64. package/dist/metadata-capture.d.ts +5 -3
  65. package/dist/metadata-capture.js +33 -2
  66. package/dist/metadata-capture.js.map +1 -1
  67. package/dist/metadata-capture.mjs +33 -2
  68. package/dist/metadata-capture.mjs.map +1 -1
  69. package/dist/platform-signatures.d.mts +13 -0
  70. package/dist/platform-signatures.d.ts +13 -0
  71. package/dist/platform-signatures.js +26 -8
  72. package/dist/platform-signatures.js.map +1 -1
  73. package/dist/platform-signatures.mjs +26 -8
  74. package/dist/platform-signatures.mjs.map +1 -1
  75. package/dist/registration/index.js +1 -1
  76. package/dist/registration/index.js.map +1 -1
  77. package/dist/registration/index.mjs +1 -1
  78. package/dist/registration/index.mjs.map +1 -1
  79. package/dist/transport/index.js +1 -1
  80. package/dist/transport/index.js.map +1 -1
  81. package/dist/transport/index.mjs +1 -1
  82. package/dist/transport/index.mjs.map +1 -1
  83. package/dist/verify.js +1 -1
  84. package/dist/verify.js.map +1 -1
  85. package/dist/verify.mjs +1 -1
  86. package/dist/verify.mjs.map +1 -1
  87. package/package.json +3 -3
package/dist/index.mjs CHANGED
@@ -30,7 +30,7 @@ function getTrustLevel(score) {
30
30
  }
31
31
 
32
32
  // src/version.ts
33
- var SDK_VERSION = "5.21.2";
33
+ var SDK_VERSION = "5.22.1";
34
34
 
35
35
  // src/http.ts
36
36
  var SDK_USER_AGENT = `astrasync-sdk/${SDK_VERSION}`;
@@ -1205,7 +1205,11 @@ var PLATFORM_HEADER_NAMES = /* @__PURE__ */ new Set([
1205
1205
  "x-goog-api-client",
1206
1206
  "user-agent",
1207
1207
  "x-agent-card-url",
1208
- "x-agent-provider"
1208
+ "x-agent-provider",
1209
+ // Round 31 — Web Bot Auth's Signature-Agent names the signing agent's
1210
+ // directory host (a public URL, never a secret). It attributes a signed
1211
+ // agent even when its UA is stock Chrome.
1212
+ "signature-agent"
1209
1213
  ]);
1210
1214
  var PLATFORM_HEADER_PREFIXES = [
1211
1215
  "x-goog-",
@@ -1336,7 +1340,12 @@ function extractPlatformHeaders(sanitized) {
1336
1340
  return out;
1337
1341
  }
1338
1342
  var CONNECTION_HEADER_SOURCES = [
1339
- ["ip", ["cf-connecting-ip", "fastly-client-ip", "true-client-ip", "x-real-ip"]],
1343
+ // Round 31: `incap-client-ip` = Imperva Cloud WAF; `true-client-ip` is
1344
+ // also Akamai's client-IP header when the property enables it.
1345
+ [
1346
+ "ip",
1347
+ ["cf-connecting-ip", "fastly-client-ip", "incap-client-ip", "true-client-ip", "x-real-ip"]
1348
+ ],
1340
1349
  [
1341
1350
  "country",
1342
1351
  ["cf-ipcountry", "x-vercel-ip-country", "cloudfront-viewer-country", "fastly-geo-country"]
@@ -1387,6 +1396,28 @@ function deriveConnectionFromHeaders(headers) {
1387
1396
  if (portMatch) connection.sourcePort = portMatch[1];
1388
1397
  if (!connection.ip && addr) connection.ip = addr.replace(/:\d+$/, "");
1389
1398
  }
1399
+ {
1400
+ const edgescape = (lower["x-akamai-edgescape"] ?? lower["akamai-edgescape"])?.trim();
1401
+ if (edgescape) {
1402
+ const fields = /* @__PURE__ */ new Map();
1403
+ for (const pair of edgescape.split(",")) {
1404
+ const i = pair.indexOf("=");
1405
+ if (i > 0) fields.set(pair.slice(0, i).trim().toLowerCase(), pair.slice(i + 1).trim());
1406
+ }
1407
+ const fill = (key, field) => {
1408
+ const v = fields.get(field);
1409
+ if (v && !connection[key]) connection[key] = v.slice(0, MAX_CONNECTION_VALUE_CHARS);
1410
+ };
1411
+ fill("country", "country_code");
1412
+ fill("region", "region_code");
1413
+ fill("city", "city");
1414
+ fill("latitude", "lat");
1415
+ fill("longitude", "long");
1416
+ fill("timeZone", "timezone");
1417
+ fill("asn", "asnum");
1418
+ fill("continent", "continent");
1419
+ }
1420
+ }
1390
1421
  if (!connection.ip) {
1391
1422
  const xff = lower["x-forwarded-for"];
1392
1423
  const client = xff?.split(",")[0]?.trim();
@@ -2085,7 +2116,8 @@ var PLATFORM_AGENT_SIGNATURES = [
2085
2116
  uaPatterns: [/claude/i, /anthropic/i],
2086
2117
  agentCardPatterns: [/anthropic\.com/i, /claude\.ai/i],
2087
2118
  apiKeyFormatPatterns: [/^sk-ant/i],
2088
- headerPatterns: [/^anthropic-version/i, /^anthropic-beta/i, /^x-anthropic-/i]
2119
+ headerPatterns: [/^anthropic-version/i, /^anthropic-beta/i, /^x-anthropic-/i],
2120
+ wafLabelPatterns: [/\bclaude/i, /\banthropic/i]
2089
2121
  },
2090
2122
  {
2091
2123
  vendor: "chatgpt",
@@ -2096,7 +2128,14 @@ var PLATFORM_AGENT_SIGNATURES = [
2096
2128
  uaPatterns: [/chatgpt/i, /openai/i, /gpt-?\d/i, /\bGPTBot\b/i, /\bOAI-SearchBot\b/i],
2097
2129
  agentCardPatterns: [/openai\.com/i, /chatgpt\.com/i],
2098
2130
  apiKeyFormatPatterns: [/^sk-proj/i, /^sk-svcacct/i],
2099
- headerPatterns: [/^openai-organization/i, /^openai-project/i, /^openai-version/i]
2131
+ headerPatterns: [
2132
+ /^openai-organization/i,
2133
+ /^openai-project/i,
2134
+ /^openai-version/i,
2135
+ // ChatGPT agent signs with Web Bot Auth under this directory host.
2136
+ /^signature-agent: "?https:\/\/chatgpt\.com/i
2137
+ ],
2138
+ wafLabelPatterns: [/\bgptbot\b/i, /\bchatgpt/i, /\boai-searchbot\b/i, /\bopenai/i]
2100
2139
  },
2101
2140
  {
2102
2141
  vendor: "gemini",
@@ -2117,7 +2156,8 @@ var PLATFORM_AGENT_SIGNATURES = [
2117
2156
  ],
2118
2157
  agentCardPatterns: [/gemini\.google\.com/i, /ai\.google\.dev/i],
2119
2158
  apiKeyFormatPatterns: [/^aiza/i],
2120
- headerPatterns: [/^x-goog-user-project/i, /^x-goog-api-client/i]
2159
+ headerPatterns: [/^x-goog-user-project/i, /^x-goog-api-client/i],
2160
+ wafLabelPatterns: [/\bgoogle-extended\b/i, /\bgoogleother\b/i, /\bgemini/i]
2121
2161
  },
2122
2162
  {
2123
2163
  vendor: "cursor",
@@ -2136,7 +2176,8 @@ var PLATFORM_AGENT_SIGNATURES = [
2136
2176
  displayName: "Perplexity",
2137
2177
  uaPatterns: [/perplexity/i],
2138
2178
  agentCardPatterns: [/perplexity\.ai/i],
2139
- apiKeyFormatPatterns: [/^pplx-/i]
2179
+ apiKeyFormatPatterns: [/^pplx-/i],
2180
+ wafLabelPatterns: [/\bperplexity/i]
2140
2181
  },
2141
2182
  // Round 30.1: xAI's documented crawlers (GrokBot/1.0, xAI-Grok/1.0,
2142
2183
  // Grok-DeepSearch/1.0). Anchored, versioned tokens — never in a stock UA.
@@ -2145,7 +2186,8 @@ var PLATFORM_AGENT_SIGNATURES = [
2145
2186
  displayName: "xAI Grok",
2146
2187
  uaPatterns: [/\bGrokBot\//i, /\bxAI-Grok\//i, /\bGrok-DeepSearch\//i],
2147
2188
  agentCardPatterns: [/\bx\.ai\b/i, /grok\.com/i],
2148
- apiKeyFormatPatterns: [/^xai-/i]
2189
+ apiKeyFormatPatterns: [/^xai-/i],
2190
+ wafLabelPatterns: [/\bgrok/i, /\bxai\b/i]
2149
2191
  },
2150
2192
  // Round 30.1: Meta AI's index and fetch crawlers. facebookexternalhit
2151
2193
  // (link previews) is deliberately NOT here — it stays a generic crawler.
@@ -2153,7 +2195,12 @@ var PLATFORM_AGENT_SIGNATURES = [
2153
2195
  vendor: "meta-ai",
2154
2196
  displayName: "Meta AI",
2155
2197
  uaPatterns: [/\bMeta-WebIndexer\b/i, /\bMeta-ExternalFetcher\b/i],
2156
- agentCardPatterns: [/meta\.ai/i]
2198
+ agentCardPatterns: [/meta\.ai/i],
2199
+ wafLabelPatterns: [
2200
+ /\bmeta-webindexer\b/i,
2201
+ /\bmeta-externalfetcher\b/i,
2202
+ /\bmeta-externalagent\b/i
2203
+ ]
2157
2204
  },
2158
2205
  // Agentic browsers — versioned-token patterns ONLY (a stock Chrome UA must
2159
2206
  // never match). Distinct vendor keys (not 'chatgpt'/'perplexity'): the
@@ -2201,6 +2248,7 @@ function matchPlatformSignature(signatures, input) {
2201
2248
  const apiKeyFormat = input.apiKeyFormat ?? "";
2202
2249
  const ja4 = input.ja4 ?? "";
2203
2250
  const asn = input.asn ?? "";
2251
+ const wafLabels = input.wafLabels ?? [];
2204
2252
  const headerLines = [];
2205
2253
  if (input.platformHeaders) {
2206
2254
  for (const [name, value] of Object.entries(input.platformHeaders)) {
@@ -2214,7 +2262,8 @@ function matchPlatformSignature(signatures, input) {
2214
2262
  const headerMatch = headerLines.length > 0 && sig.headerPatterns?.some((p) => headerLines.some((line) => p.test(line)));
2215
2263
  const ja4Match = ja4.length > 0 && sig.ja4Patterns?.some((p) => p.test(ja4));
2216
2264
  const asnMatch = asn.length > 0 && sig.asnList?.includes(asn);
2217
- if (uaMatch || cardMatch || keyMatch || headerMatch || ja4Match || asnMatch) {
2265
+ const wafMatch = wafLabels.length > 0 && sig.wafLabelPatterns?.some((p) => wafLabels.some((label) => p.test(label)));
2266
+ if (uaMatch || cardMatch || keyMatch || headerMatch || ja4Match || asnMatch || wafMatch) {
2218
2267
  const uaBase = ua.split(/[\s/]/)[0]?.toLowerCase() ?? "";
2219
2268
  const cardHost = (() => {
2220
2269
  try {
@@ -2223,7 +2272,7 @@ function matchPlatformSignature(signatures, input) {
2223
2272
  return "";
2224
2273
  }
2225
2274
  })();
2226
- const keyBasis = uaBase || cardHost || apiKeyFormat || ja4 || asn && `asn${asn}` || "unknown";
2275
+ const keyBasis = uaBase || cardHost || apiKeyFormat || ja4 || asn && `asn${asn}` || wafMatch && `waf:${wafLabels[0]?.toLowerCase()}` || "unknown";
2227
2276
  return {
2228
2277
  vendor: sig.vendor,
2229
2278
  fingerprintKey: `${sig.vendor}:${keyBasis}`,
@@ -11567,7 +11616,11 @@ function createAgentCommerce(opts) {
11567
11616
  const headers = {
11568
11617
  Accept: "application/json",
11569
11618
  Authorization: `Bearer ${opts.apiKey}`,
11570
- "X-AstraSync-SDK-Version": SDK_VERSION
11619
+ "X-AstraSync-SDK-Version": SDK_VERSION,
11620
+ // 5.22.1: identifies the agent-commerce kit, so only a kit fetching
11621
+ // its rules marks the merchant as applying them (cardholder prices
11622
+ // are then shown to agents). A curl or another client never does.
11623
+ "X-AstraSync-Kit": "agent-commerce"
11571
11624
  };
11572
11625
  if (kitReport) {
11573
11626
  headers["X-AstraSync-Kit-Report"] = Buffer.from(JSON.stringify(kitReport)).toString(
@@ -11604,10 +11657,14 @@ function createAgentCommerce(opts) {
11604
11657
  }
11605
11658
  };
11606
11659
  }
11607
- function pricingContextFrom(headers) {
11660
+ function pricingContextFrom(headers, opts = {}) {
11608
11661
  const astraId = headers.get("x-astra-id");
11609
11662
  const hop = parseVerifiedHop(headers.get(MCP_VERIFIED_HOP_HEADER.toLowerCase()));
11610
- const verified = !!astraId && (!hop || hop.astraId === astraId && Date.now() - hop.checkedAt <= MCP_VERIFIED_HOP_MAX_AGE_MS);
11663
+ let verified = !!astraId && (!hop || hop.astraId === astraId && Date.now() - hop.checkedAt <= MCP_VERIFIED_HOP_MAX_AGE_MS);
11664
+ const v = opts.verification;
11665
+ if (verified && v) {
11666
+ verified = v.identityVerified === true && (!v.agent?.astraId || v.agent.astraId === astraId);
11667
+ }
11611
11668
  const program = headers.get(ISSUER_PROGRAM_HEADER.toLowerCase());
11612
11669
  return {
11613
11670
  verified,