twzrd-x402-gate 0.11.1 → 0.11.2

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 (76) hide show
  1. package/CHANGELOG.md +57 -3
  2. package/LICENSE +21 -0
  3. package/QUICKSTART.md +3 -3
  4. package/README.md +115 -9
  5. package/dist/all-offers.d.ts +29 -0
  6. package/dist/all-offers.d.ts.map +1 -0
  7. package/dist/all-offers.js +66 -0
  8. package/dist/all-offers.js.map +1 -0
  9. package/dist/attempt-echo.d.ts +1 -1
  10. package/dist/attempt-echo.js +1 -1
  11. package/dist/auto-gate.d.ts +1 -1
  12. package/dist/auto-gate.js +1 -1
  13. package/dist/cloudflare-base.d.ts +24 -2
  14. package/dist/cloudflare-base.d.ts.map +1 -1
  15. package/dist/cloudflare-base.js +110 -11
  16. package/dist/cloudflare-base.js.map +1 -1
  17. package/dist/config.d.ts +2 -0
  18. package/dist/config.d.ts.map +1 -1
  19. package/dist/config.js +25 -8
  20. package/dist/config.js.map +1 -1
  21. package/dist/deadline.d.ts +9 -0
  22. package/dist/deadline.d.ts.map +1 -0
  23. package/dist/deadline.js +25 -0
  24. package/dist/deadline.js.map +1 -0
  25. package/dist/doctor.js +6 -6
  26. package/dist/evaluate.d.ts.map +1 -1
  27. package/dist/evaluate.js +15 -7
  28. package/dist/evaluate.js.map +1 -1
  29. package/dist/index.d.ts +2 -2
  30. package/dist/index.d.ts.map +1 -1
  31. package/dist/index.js +5 -4
  32. package/dist/index.js.map +1 -1
  33. package/dist/mcp-hook.d.ts.map +1 -1
  34. package/dist/mcp-hook.js +18 -27
  35. package/dist/mcp-hook.js.map +1 -1
  36. package/dist/merchant-card.d.ts +1 -21
  37. package/dist/merchant-card.d.ts.map +1 -1
  38. package/dist/merchant-card.js +15 -0
  39. package/dist/merchant-card.js.map +1 -1
  40. package/dist/network.d.ts +12 -0
  41. package/dist/network.d.ts.map +1 -1
  42. package/dist/network.js +42 -7
  43. package/dist/network.js.map +1 -1
  44. package/dist/paying-fetch.d.ts.map +1 -1
  45. package/dist/paying-fetch.js +7 -1
  46. package/dist/paying-fetch.js.map +1 -1
  47. package/dist/payto.d.ts +18 -3
  48. package/dist/payto.d.ts.map +1 -1
  49. package/dist/payto.js +91 -53
  50. package/dist/payto.js.map +1 -1
  51. package/dist/policy-fetch.d.ts.map +1 -1
  52. package/dist/policy-fetch.js +7 -1
  53. package/dist/policy-fetch.js.map +1 -1
  54. package/dist/policy.d.ts.map +1 -1
  55. package/dist/policy.js +63 -16
  56. package/dist/policy.js.map +1 -1
  57. package/dist/spend-control.d.ts +1 -1
  58. package/dist/spend-control.d.ts.map +1 -1
  59. package/dist/spend-control.js +4 -2
  60. package/dist/spend-control.js.map +1 -1
  61. package/dist/types.d.ts +12 -0
  62. package/dist/types.d.ts.map +1 -1
  63. package/dist/with-guard.d.ts.map +1 -1
  64. package/dist/with-guard.js +18 -1
  65. package/dist/with-guard.js.map +1 -1
  66. package/dist/wrap-fetch.d.ts.map +1 -1
  67. package/dist/wrap-fetch.js +14 -16
  68. package/dist/wrap-fetch.js.map +1 -1
  69. package/dist/x402-client-hook.d.ts.map +1 -1
  70. package/dist/x402-client-hook.js +8 -5
  71. package/dist/x402-client-hook.js.map +1 -1
  72. package/package.json +3 -3
  73. package/dist/unsafe.d.ts +0 -11
  74. package/dist/unsafe.d.ts.map +0 -1
  75. package/dist/unsafe.js +0 -11
  76. package/dist/unsafe.js.map +0 -1
package/CHANGELOG.md CHANGED
@@ -28,7 +28,59 @@ All notable changes to `twzrd-x402-gate`. Dates are npm publish dates (UTC).
28
28
  - **Seller side** (`createTwzrdSettleGuard`): fail-open by default. A screen that throws
29
29
  returns without aborting settlement unless `failOpen: false`.
30
30
 
31
- ## 0.11.1 — unreleased (security fix)
31
+ ## 0.11.2 — 2026-09-28 (security fix)
32
+
33
+ Fixes from a line-by-line audit of the published 0.11.1. Every change adds a
34
+ refusal or makes an existing one reliable; none loosens one.
35
+
36
+ - **Malformed amounts are refused on every entry point** (`amount_malformed`,
37
+ before intel). An amount must be an ASCII base-unit integer: no sign, decimal
38
+ point, exponent, whitespace or non-ASCII digit. Signing schemes build the
39
+ transfer from this string, so there is no safe reading of anything else.
40
+ `twzrd.safeFetch` keeps reporting it as `malformed_amount`. A computed
41
+ `priceUsdc` that is negative or not finite is refused as `twzrd_invalid_price`.
42
+ - **Fetch wrappers and the MCP hook check every offer.** `withTwzrdGuard`,
43
+ `wrapFetchWithTwzrdGate`, `installTwzrdAutoGate(payWrap)` and
44
+ `twzrdOnPaymentRequested` scored one `accepts[]` entry while the paying client
45
+ could choose another. Every distinct entry now gets the free approval (one
46
+ preflight each; paid hops run once), and more than 8 distinct offers are
47
+ refused (`too_many_payment_options`). The x402 client hooks already scored
48
+ the selected entry and are unchanged.
49
+ - **`./cloudflare-base` applies the package's signing rules** to the Base USDC
50
+ entry: asset, amount, block, wash, never-evaluated cap, score floor and
51
+ recommended cap. It used to sign on any non-block verdict. The price is read
52
+ from the entry's own `amount`; the `priceUsdc` option no longer affects the
53
+ decision. New options `preflightMinScore` and `refuseUnevaluated`.
54
+ - **Genuine USDC is no longer refused as `twzrd_non_usdc_asset`** when the 402
55
+ omits the network or names Solana mainnet as `mainnet-beta` or by its bare
56
+ genesis id. One Solana cluster reading (`solanaCluster`) now serves both the
57
+ network classifier and the USDC table; `solana:devnet` uses the devnet mints.
58
+ Solana mints are compared exactly (base58 is case-sensitive).
59
+ - **Intel calls have a deadline.** New option `intelTimeoutMs` (env
60
+ `TWZRD_INTEL_TIMEOUT_MS`, default 2000). A free preflight or merchant-card call
61
+ that misses it is an outage, decided by `failOpen` as before. Paid hops are
62
+ not cut off mid-payment.
63
+ - **Callbacks cannot change a decision.** A throwing or rejecting `onWarnUpsell`
64
+ no longer crashes the host or turns into `twzrd_fail_open`; a throwing
65
+ `onReceipt` no longer turns a paid receipt into a deny.
66
+ - A merchant-card outage allowed under `failOpen` is marked
67
+ (`cardUnreachable: true` and a warning) instead of looking like a clean card.
68
+ - No paid `/trust` receipt and no `onWarnUpsell` for a seller intel has never
69
+ evaluated (the same rule as the `/quick` hop since 0.11.0).
70
+ - `refuseUnevaluated` and `gateOnCanSpend` accept `true`, `1`, `"true"`,
71
+ `"yes"`, `"on"` in any case; a typo no longer leaves strict mode silently off.
72
+ - A non-list `accepts` or a null entry is no offer, never a TypeError.
73
+ - Two spellings of the same 0x address in `payTo` / `pay_to` are one recipient.
74
+ - `createTwzrdPayingFetch` and `createTwzrdPolicyFetch` name the missing
75
+ `@x402/fetch` peer instead of throwing a bare module error.
76
+ - The unreachable `dist/unsafe.js` is no longer shipped, and the README no
77
+ longer documents a `twzrd-x402-gate/unsafe` import. LICENSE ships in the
78
+ package.
79
+
80
+ Deliberately unchanged: a Solana devnet payment named only by its CAIP-2 id is
81
+ still scored (integration harnesses rely on it reaching the preflight).
82
+
83
+ ## 0.11.1 — 2026-09-28 (security fix)
32
84
 
33
85
  **A requirement that names an asset other than USDC is refused on Solana and Base.**
34
86
 
@@ -51,8 +103,10 @@ All notable changes to `twzrd-x402-gate`. Dates are npm publish dates (UTC).
51
103
  micro-USDC, so another asset was counted in the wrong units.
52
104
  - New exports: `isUsdcRequirement`, `requirementAsset`. `TwzrdApproveContext` gains
53
105
  `asset`.
54
- - Unchanged: a requirement that names no asset (x402 schemes default it to USDC), USDC
55
- itself, and unscored networks (their observe policy never priced anything).
106
+ - Unchanged: a requirement that names no asset, USDC itself, and unscored networks.
107
+ (Corrected in 0.11.2: the schemes do not default an unnamed asset to USDC.
108
+ x402-solana refuses a requirement with no mint and @x402/svm fetches the mint
109
+ before building the transfer, so an unnamed asset fails before signing.)
56
110
  - Who was exposed: clients on `@x402/core` ≥2.23 with default spend controls already
57
111
  refused an unrecognised asset before any TWZRD hook ran. The exposure was the PayAI
58
112
  `x402-solana` path, clients with spend controls turned off, and older core.
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 TWZRD
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/QUICKSTART.md CHANGED
@@ -6,13 +6,13 @@ is unreachable the gate never *invents* a wash flag. A failed preflight, or a me
6
6
  outage on a scored path, blocks by default (`TWZRD_FAIL_OPEN=true` to allow). A reachable
7
7
  card with no wash signal still proceeds.
8
8
 
9
- **Pin:** `twzrd-x402-gate@0.11.1` + stock PayAI client `x402-solana@3.0.0` (official
9
+ **Pin:** `twzrd-x402-gate@0.11.2` + stock PayAI client `x402-solana@3.0.0` (official
10
10
  `beforePayment` seat). `@x402/core` Path E remains supported; refuse script is fallback.
11
11
 
12
12
  ## 1. Stock PayAI client (default seat — copy-paste)
13
13
 
14
14
  ```bash
15
- npm install twzrd-x402-gate@0.11.1 x402-solana@3.0.0
15
+ npm install twzrd-x402-gate@0.11.2 x402-solana@3.0.0
16
16
  ```
17
17
 
18
18
  > **ESM-only.** The package ships `import` conditions only — a CommonJS
@@ -37,7 +37,7 @@ Then: `await client.fetch("https://merchant.example/paid");`
37
37
  ## 1b. Official `@x402/core` client (Path E)
38
38
 
39
39
  ```bash
40
- npm install twzrd-x402-gate@0.11.1 @x402/core @x402/fetch @x402/svm
40
+ npm install twzrd-x402-gate@0.11.2 @x402/core @x402/fetch @x402/svm
41
41
  ```
42
42
 
43
43
  ```typescript
package/README.md CHANGED
@@ -41,7 +41,7 @@ refuse. Protects the **payer** from a risky **merchant** (`payTo`). Chain-neutra
41
41
  ### Default-on AutoGate (5 lines)
42
42
 
43
43
  ```bash
44
- npm install twzrd-x402-gate@0.11.1 @x402/core @x402/fetch @x402/svm
44
+ npm install twzrd-x402-gate@0.11.2 @x402/core @x402/fetch @x402/svm
45
45
  ```
46
46
 
47
47
  ```typescript
@@ -80,7 +80,7 @@ transfer on-chain. Wash/sybil edges are primarily discounted in TWZRD scoring, n
80
80
  revenue refusal.
81
81
 
82
82
  ```bash
83
- npm install twzrd-x402-gate@0.11.1
83
+ npm install twzrd-x402-gate@0.11.2
84
84
  ```
85
85
 
86
86
  ```typescript
@@ -125,7 +125,7 @@ Fixture-backed SVM extract tests live in `test/seller-hook.test.ts` +
125
125
  Install the published gate and run against wash fixtures:
126
126
 
127
127
  ```bash
128
- npm install twzrd-x402-gate@0.11.1
128
+ npm install twzrd-x402-gate@0.11.2
129
129
  # from package root after install, or from a checkout:
130
130
  npm run wash-dogfood
131
131
  ```
@@ -299,7 +299,7 @@ Dogfood (one public live proof path):
299
299
  ## Install
300
300
 
301
301
  ```bash
302
- npm install twzrd-x402-gate@0.11.1
302
+ npm install twzrd-x402-gate@0.11.2
303
303
  ```
304
304
 
305
305
  Do not hardcode a version in this doc — every past pin here (**0.5.4**, **0.7.1**, **0.8.5**,
@@ -348,9 +348,9 @@ assertIntentApproved(intentBeingSigned, token, {
348
348
  // throws MISSING_VERIFIER_KEY | BAD_SIGNATURE | INTENT_HASH_MISMATCH |
349
349
  // DECISION_EXPIRED | DECISION_NOT_ALLOW | DECISION_REPLAYED
350
350
  // -> the signer is never invoked
351
- // In-process matching without a key is unsafeAssertIntentApprovedWithoutSignature,
352
- // exported only from the "twzrd-x402-gate/unsafe" subpath — never the root:
353
- // import { unsafeAssertIntentApprovedWithoutSignature } from "twzrd-x402-gate/unsafe";
351
+ // There is no published way to match an intent without verifying the decision
352
+ // signature: the old "twzrd-x402-gate/unsafe" subpath was removed in 0.9.4 and
353
+ // its module in 0.11.2. Always verify with a key.
354
354
  ```
355
355
 
356
356
  - `PaymentIntent` v1 (frozen): protocol `x402 | ap2 | ucp | mpp | direct` +
@@ -960,7 +960,7 @@ An approval here carries `unevaluated: true` and `score: null`, never a trust sc
960
960
 
961
961
  A price above `recommended_cap_usdc` returns a reason that starts with `twzrd_over_recommended_cap_`. A direct `createTwzrdBeforePaymentHook` abort of a block card returns reason `twzrd_decision_block`. That reason string is not `block` and is not `twzrd_fail_closed`. A missing `payTo` returns reason `twzrd_unidentifiable_payment_recipient` from `twzrdApprovePayment`. That reason is not `twzrd_missing_payTo`. When the buyer preflight fetch throws and `TWZRD_FAIL_OPEN` is unset, `twzrdApprovePayment` returns reason `twzrd_fail_closed`. That reason is not `twzrd_preflight_fetch_error`.
962
962
 
963
- An evaluated `warn` (no `null_reason`, score present) is allowed unless overridden. When the buyer preflight fetch throws and `TWZRD_FAIL_OPEN` is unset, `twzrdApprovePayment` returns `approved: false` with reason `twzrd_fail_closed` and the wallet does not sign. An omitted `failOpen` on `createTwzrdSettleGuard` is a different default: a thrown screen returns without abort. 0.11.1 is not uniformly fail-closed.
963
+ An evaluated `warn` (no `null_reason`, score present) is allowed unless overridden. When the buyer preflight fetch throws and `TWZRD_FAIL_OPEN` is unset, `twzrdApprovePayment` returns `approved: false` with reason `twzrd_fail_closed` and the wallet does not sign. An omitted `failOpen` on `createTwzrdSettleGuard` is a different default: a thrown screen returns without abort. 0.11.2 is not uniformly fail-closed.
964
964
 
965
965
  A 402 whose payment requirements yield **no identifiable seller wallet** (missing/empty `payTo`, or an unparseable `accepts[]`) is a different case from "unknown seller" — it always **blocks** with `reason: twzrd_unidentifiable_payment_recipient`, without ever calling the preflight network. The wallet does not sign. This is unconditional (not affected by buyer `failOpen`): that switch governs a buyer preflight outage, not a missing payTo. An omitted `failOpen` on `createTwzrdSettleGuard` is a different default: a thrown screen returns without abort.
966
966
 
@@ -968,6 +968,111 @@ A 402 whose payment requirements yield **no identifiable seller wallet** (missin
968
968
  > not yet in the TWZRD corpus, including legitimate ones. `can_spend: false` alone does not block (`gateOnCanSpend` defaults false). That is separate from `null_reason: unknown_subject`, which signs only within its card's cap.
969
969
  > Set `gateOnCanSpend: true` to also block on `can_spend: false`.
970
970
 
971
+ ## Refusals
972
+
973
+ Every reason the gate returns, by entry point. A refusal means the wallet was not asked
974
+ to sign (`signerInvocations = 0`). `test/readme-refusal-codes.test.ts` fails if a reason
975
+ string in the source is missing here, so this table cannot drift from the code.
976
+ `<...>` marks a value filled in at runtime.
977
+
978
+ ### Buyer approval (`twzrdApprovePayment`, used by every buyer entry point)
979
+
980
+ On the x402 client hooks (`createTwzrdBeforePaymentHook`, `installTwzrdAutoGate`,
981
+ `createTwzrdPayKitBeforePaymentHook`, `createGuardedX402Fetch`) the abort reason is
982
+ `[twzrd] <reason> payTo=<payTo> network=<network>`.
983
+
984
+ | Reason | When | Default |
985
+ |---|---|---|
986
+ | `twzrd_unidentifiable_payment_recipient` | The requirement names no `payTo`. Intel is not called. | always |
987
+ | `twzrd_invalid_price` | A caller passed a `priceUsdc` that is negative or not finite. Intel is not called. | always (0.11.2+) |
988
+ | `twzrd_non_usdc_asset` | On Solana or Base, the requirement names an asset that is not USDC on that network. Intel is not called; `failOpen` does not apply. | always (0.11.1+) |
989
+ | `network_not_scored`, `network_missing` | The network is not scored (not Solana or Base mainnet). | refused only with `unsupportedNetworkMode: "strict"`; the default `observe` allows |
990
+ | `twzrd_decision_<decision>` | Intel's card decision is in `blockDecisions`. | `twzrd_decision_block` |
991
+ | `twzrd_unevaluated_subject_<null_reason>` | Intel has never evaluated the seller, and `refuseUnevaluated` is set or the decision is not `allow`/`warn`. | strict mode off |
992
+ | `twzrd_unevaluated_no_cap_<null_reason>` | Never evaluated, and the card has no finite `recommended_cap_usdc`. | always |
993
+ | `twzrd_unevaluated_unknown_price_<null_reason>` | Never evaluated, and the price is unknown. | always |
994
+ | `twzrd_unevaluated_over_cap_<price>_gt_<cap>` | Never evaluated, and the price is above the card's cap (live: min($0.10, price)). | always |
995
+ | `twzrd_can_spend_false` | The card says `can_spend: false`. | only with `gateOnCanSpend: true` |
996
+ | `twzrd_score_<score>_below_<min>` | An evaluated seller scores below `preflightMinScore`. | min 40 |
997
+ | `twzrd_over_recommended_cap_<price>_gt_<cap>` | An evaluated seller, and the price is above the card's `recommended_cap_usdc`. | always |
998
+ | `twzrd_wash_flagged` | The free merchant card says `wash_flagged: true`. | on (`refuseWashFlagged` defaults true on every entry point) |
999
+ | `twzrd_wash_flagged_above_cap_<price>_gt_<cap>`, `twzrd_wash_flagged_above_cap_unknown_price_max_<cap>` | Wash-flagged, `washMaxUsdc` is set, and the price is above it or unknown. | only with `washMaxUsdc` |
1000
+ | `twzrd_fail_closed (<error>)` | The preflight did not answer (non-2xx, non-JSON, network error, or no answer within `intelTimeoutMs`). | fail-closed unless `failOpen` |
1001
+ | `twzrd_card_unreachable_fail_closed (<error>)` | The merchant card did not answer (5xx, 429, non-JSON, network error, or no answer within `intelTimeoutMs`). A 4xx is an answer, not an outage. With `failOpen` the payment is allowed and the result carries `cardUnreachable: true` (the wash check did not run). | fail-closed unless `failOpen` |
1002
+
1003
+ Approval reasons, for `onDecision` consumers: `twzrd_allow`, `twzrd_warn_allowed`,
1004
+ `twzrd_unevaluated_within_cap_<price>_le_<cap>`, `twzrd_wash_capped_<price>_le_<cap>`,
1005
+ `twzrd_fail_open` (an outage allowed because `failOpen` is set).
1006
+
1007
+ ### x402 client hook only
1008
+
1009
+ | Reason | When |
1010
+ |---|---|
1011
+ | `amount_field_conflict`, `payto_field_conflict` | The requirement's v1 and v2 price fields (`maxAmountRequired` / `amount`) or recipient fields (`payTo` / `pay_to`) disagree. Two spellings of the same 0x address are one recipient. |
1012
+ | `amount_malformed` | The amount is present but is not an ASCII base-unit integer (a sign, decimal point, exponent, whitespace or non-ASCII digit). Refused before intel on every entry point (0.11.2+); `twzrd.safeFetch` reports it as `malformed_amount`. |
1013
+ | `payment_control_unevaluable: missing <field>` | Payment Control is on and the requirement has no amount or `payTo`. |
1014
+ | `payment_control_block:<reason codes>` | Payment Control (`paymentControl` option) refused the intent. |
1015
+ | `twzrd_escalated_warn_block (paid quick score <score> < <floor>)` | `escalateOnWarn` bought the $0.001 `/quick` score and it is below the floor. |
1016
+ | `twzrd_receipt_required_missing_x402Fetch` | `requireReceipt` needs a paid receipt and no `x402Fetch` is wired. |
1017
+ | `twzrd_receipt_required_failed (HTTP <status>)`, `twzrd_receipt_required_error (<error>)` | The required paid receipt could not be bought. |
1018
+ | `aborted_before_payment: signal already aborted` | The caller's abort signal fired before the hook ran. |
1019
+
1020
+ ### Fetch wrappers and the MCP hook
1021
+
1022
+ `withTwzrdGuard`, `wrapFetchWithTwzrdGate`, `installTwzrdAutoGate(payWrap)` and
1023
+ `twzrdOnPaymentRequested` see the whole 402 but not which `accepts[]` entry the
1024
+ paying client will choose, so every distinct entry must pass the buyer approval
1025
+ (one free preflight each; paid hops run once, for the preferred entry). The
1026
+ first refusal is reported with that entry's `payTo` (0.11.2+).
1027
+
1028
+ | Reason | When |
1029
+ |---|---|
1030
+ | `too_many_payment_options` | The 402 lists more than 8 distinct offers. |
1031
+
1032
+ ### `./cloudflare-base` (edge Worker seat)
1033
+
1034
+ `withTwzrdBasePreflight` and `createTwzrdCloudflareBaseApproval` apply the same
1035
+ rules to the Base USDC entry, restated in the module so it imports nothing:
1036
+ `twzrd_unidentifiable_payment_recipient`, `amount_field_conflict`,
1037
+ `amount_malformed`, `twzrd_non_usdc_asset`, `invalid_base_offer` (before
1038
+ intel; `failOpen` never signs these), then `twzrd_decision_block`, `twzrd_wash_flagged`,
1039
+ `twzrd_unevaluated_subject_*`, `twzrd_unevaluated_no_cap_*`,
1040
+ `twzrd_unevaluated_over_cap_*`, `twzrd_score_*_below_*` and
1041
+ `twzrd_over_recommended_cap_*`. The price comes from the entry's own `amount`;
1042
+ the `priceUsdc` option is ignored for the decision. Before 0.11.2 this seat
1043
+ signed on any non-block verdict.
1044
+
1045
+ ### `createGuardedX402Fetch` local caps
1046
+
1047
+ Abort reason `[twzrd-guarded-fetch] <reason>`; these run before the buyer approval above.
1048
+
1049
+ | Reason | When |
1050
+ |---|---|
1051
+ | `price_cap_exceeded` | The price is above `maxPricePerCall`. |
1052
+ | `hourly_budget_exceeded` | The payment would take spend in the last hour above `hourlyBudgetCap`. |
1053
+ | `amount_field_conflict`, `payto_field_conflict` | As in the client hook table. |
1054
+ | `recipient_missing` | `allowedRecipients` is set and the requirement names no recipient. |
1055
+ | `unauthorized_recipient` | `allowedRecipients` is set and `payTo` is not in it. |
1056
+ | `amount_missing_or_malformed` | A spend rule is set and the amount is not a base-unit integer. |
1057
+ | `unsupported_or_non_usdc_asset` | A spend rule is set and the asset is not USDC on that network. |
1058
+
1059
+ ### `twzrd.safeFetch` verdicts
1060
+
1061
+ `{ verdict: "block", reason }`:
1062
+
1063
+ | Reason | When |
1064
+ |---|---|
1065
+ | `unparseable_402` | The 402 has no readable payment requirements. |
1066
+ | `network_not_allowed` | No offer is on an `allowNetworks` network. |
1067
+ | `amount_field_conflict`, `payto_field_conflict` | As above. |
1068
+ | `no_payable_requirement` | No offer names both a recipient and an amount. |
1069
+ | `malformed_amount` | The amount is not a base-unit integer. |
1070
+ | `non_usdc_asset` | On Solana or Base, the offer names an asset that is not USDC (the budget counts micro-USDC). |
1071
+ | `over_max_spend`, `over_cumulative_spend` | The payment, or the running total, would pass `maxSpend`. |
1072
+ | `intel_block` | The injected preflight answered `block`. |
1073
+ | `decision_bind_required` | A signed decision is required and none was bound. |
1074
+ | `bind_required_no_compose`, `bind_required_no_settlement`, `bind_required_no_leaf_hash`, `bind_mismatch` | A resource bind was required and could not be built or did not match. |
1075
+
971
1076
  ## Config
972
1077
 
973
1078
  | Option | Env | Default | Description |
@@ -977,7 +1082,8 @@ A 402 whose payment requirements yield **no identifiable seller wallet** (missin
977
1082
  | `blockDecisions` | `TWZRD_BLOCK_DECISIONS` | `block` | Decisions that throw |
978
1083
  | `failOpen` (buyer preflight only) | `TWZRD_FAIL_OPEN` | `false` | Buyer outage only: default does not sign. `createTwzrdSettleGuard` omitted `failOpen` is the other default — a thrown screen returns without abort |
979
1084
  | `gateOnCanSpend` | `TWZRD_GATE_ON_CAN_SPEND` | `false` | Also block when `can_spend=false` |
980
- | `refuseUnevaluated` | `TWZRD_REFUSE_UNEVALUATED` | `false` | Refuse every seller intel has not evaluated, instead of allowing it up to the card's `recommended_cap_usdc` |
1085
+ | `refuseUnevaluated` | `TWZRD_REFUSE_UNEVALUATED` | `false` | Refuse every seller intel has not evaluated, instead of allowing it up to the card's `recommended_cap_usdc`. `true`, `1`, `"yes"`, `"on"` in any case turn it on. |
1086
+ | `intelTimeoutMs` | `TWZRD_INTEL_TIMEOUT_MS` | `2000` | Deadline for each free intel call (preflight, merchant card). A miss is an outage, decided by `failOpen`. Paid hops are not cut off mid-payment. |
981
1087
  | `autoReceipt` | — | `false` | Optional V7: auto-buy $0.05 `/trust` when `/quick` did not already settle |
982
1088
  | `x402Fetch` | — | — | x402-capable fetch for `autoReceipt` |
983
1089
  | `onReceipt` | — | — | Callback after receipt is captured |
@@ -0,0 +1,29 @@
1
+ import type { ResolvedTwzrdGateConfig } from "./config.js";
2
+ /**
3
+ * A fetch wrapper or MCP hook sees the whole 402 but not which accepts[] entry
4
+ * the paying client will choose: @x402/core takes the first entry its schemes
5
+ * can pay, x402-solana the first Solana entry, a fee-payer preference another.
6
+ * So every distinct entry must pass before the payer gets the 402. Scoring one
7
+ * entry let a seller list a clean wallet next to a refused one and be paid on
8
+ * the refused one (0.11.2).
9
+ */
10
+ export declare const MAX_DISTINCT_OFFERS = 8;
11
+ export declare const TOO_MANY_PAYMENT_OPTIONS = "too_many_payment_options";
12
+ /** The distinct offer objects in a seller-supplied accepts value. */
13
+ export declare function distinctOffers(accepts: unknown): Array<Record<string, unknown>>;
14
+ export declare function sameOffer(a: Record<string, unknown>, b: Record<string, unknown>): boolean;
15
+ /**
16
+ * Free approval of every offer except `skip` (already evaluated by the caller).
17
+ * Returns the first refusal, or undefined when all pass. No paid hops.
18
+ */
19
+ export declare function firstRefusedOffer(offers: Array<Record<string, unknown>>, opts: {
20
+ config?: ResolvedTwzrdGateConfig;
21
+ resourceUrl?: string;
22
+ agentIntent: string;
23
+ skip?: Record<string, unknown>;
24
+ }): Promise<{
25
+ offer: Record<string, unknown>;
26
+ payTo?: string;
27
+ reason: string;
28
+ } | undefined>;
29
+ //# sourceMappingURL=all-offers.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"all-offers.d.ts","sourceRoot":"","sources":["../src/all-offers.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,aAAa,CAAC;AAS3D;;;;;;;GAOG;AACH,eAAO,MAAM,mBAAmB,IAAI,CAAC;AACrC,eAAO,MAAM,wBAAwB,6BAA6B,CAAC;AAanE,qEAAqE;AACrE,wBAAgB,cAAc,CAAC,OAAO,EAAE,OAAO,GAAG,KAAK,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAU/E;AAED,wBAAgB,SAAS,CAAC,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,OAAO,CAEzF;AAED;;;GAGG;AACH,wBAAsB,iBAAiB,CACrC,MAAM,EAAE,KAAK,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,EACtC,IAAI,EAAE;IACJ,MAAM,CAAC,EAAE,uBAAuB,CAAC;IACjC,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,WAAW,EAAE,MAAM,CAAC;IACpB,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CAChC,GACA,OAAO,CAAC;IAAE,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,GAAG,SAAS,CAAC,CAsBzF"}
@@ -0,0 +1,66 @@
1
+ import { offerObjects, priceUsdcFromAmountMicro, requirementAsset, resolveRequirementFields, } from "./payto.js";
2
+ import { twzrdApprovePayment } from "./policy.js";
3
+ /**
4
+ * A fetch wrapper or MCP hook sees the whole 402 but not which accepts[] entry
5
+ * the paying client will choose: @x402/core takes the first entry its schemes
6
+ * can pay, x402-solana the first Solana entry, a fee-payer preference another.
7
+ * So every distinct entry must pass before the payer gets the 402. Scoring one
8
+ * entry let a seller list a clean wallet next to a refused one and be paid on
9
+ * the refused one (0.11.2).
10
+ */
11
+ export const MAX_DISTINCT_OFFERS = 8;
12
+ export const TOO_MANY_PAYMENT_OPTIONS = "too_many_payment_options";
13
+ function offerKey(e) {
14
+ const f = resolveRequirementFields(e);
15
+ return [
16
+ f.payTo ?? String(e.payTo ?? e.pay_to ?? ""),
17
+ f.amount ?? String(e.amount ?? e.maxAmountRequired ?? ""),
18
+ String(e.asset ?? ""),
19
+ String(e.network ?? "").toLowerCase(),
20
+ f.conflict ?? "",
21
+ ].join("|");
22
+ }
23
+ /** The distinct offer objects in a seller-supplied accepts value. */
24
+ export function distinctOffers(accepts) {
25
+ const seen = new Set();
26
+ const out = [];
27
+ for (const e of offerObjects(accepts)) {
28
+ const k = offerKey(e);
29
+ if (seen.has(k))
30
+ continue;
31
+ seen.add(k);
32
+ out.push(e);
33
+ }
34
+ return out;
35
+ }
36
+ export function sameOffer(a, b) {
37
+ return offerKey(a) === offerKey(b);
38
+ }
39
+ /**
40
+ * Free approval of every offer except `skip` (already evaluated by the caller).
41
+ * Returns the first refusal, or undefined when all pass. No paid hops.
42
+ */
43
+ export async function firstRefusedOffer(offers, opts) {
44
+ if (offers.length > MAX_DISTINCT_OFFERS) {
45
+ return { offer: offers[0] ?? {}, reason: TOO_MANY_PAYMENT_OPTIONS };
46
+ }
47
+ for (const offer of offers) {
48
+ if (opts.skip && sameOffer(offer, opts.skip))
49
+ continue;
50
+ const f = resolveRequirementFields(offer);
51
+ if (f.conflict)
52
+ return { offer, payTo: f.payTo, reason: f.conflict };
53
+ const approval = await twzrdApprovePayment({
54
+ resourceUrl: offer.resource ?? opts.resourceUrl,
55
+ payTo: f.payTo,
56
+ priceUsdc: priceUsdcFromAmountMicro(f.amount, offer),
57
+ agentIntent: opts.agentIntent,
58
+ chain: offer.network,
59
+ asset: requirementAsset(offer),
60
+ }, opts.config);
61
+ if (!approval.approved)
62
+ return { offer, payTo: f.payTo, reason: approval.reason };
63
+ }
64
+ return undefined;
65
+ }
66
+ //# sourceMappingURL=all-offers.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"all-offers.js","sourceRoot":"","sources":["../src/all-offers.ts"],"names":[],"mappings":"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"}
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * Funnel join-key pass-through for paying clients.
3
3
  *
4
- * Server 402s (PR #2819) emit `extensions.twzrd_attempt` on PAYMENT-REQUIRED.
4
+ * TWZRD intel 402s emit `extensions.twzrd_attempt` on PAYMENT-REQUIRED.
5
5
  * `@x402/fetch` / `@x402/core` createPaymentPayload drops unknown extensions,
6
6
  * so every paid retry lands as a new singleton in `x402_funnel_events`.
7
7
  *
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * Funnel join-key pass-through for paying clients.
3
3
  *
4
- * Server 402s (PR #2819) emit `extensions.twzrd_attempt` on PAYMENT-REQUIRED.
4
+ * TWZRD intel 402s emit `extensions.twzrd_attempt` on PAYMENT-REQUIRED.
5
5
  * `@x402/fetch` / `@x402/core` createPaymentPayload drops unknown extensions,
6
6
  * so every paid retry lands as a new singleton in `x402_funnel_events`.
7
7
  *
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * installTwzrdAutoGate — canonical default trust checkpoint entry point.
3
3
  *
4
- * Design: docs/strategy/install-autogate-design.md (#1586).
4
+ * Design notes live with the TWZRD intel service.
5
5
  *
6
6
  * One name across five adapters:
7
7
  * 1. Fetch / payWrap — guard raw fetch, then hand to x402 payer
package/dist/auto-gate.js CHANGED
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * installTwzrdAutoGate — canonical default trust checkpoint entry point.
3
3
  *
4
- * Design: docs/strategy/install-autogate-design.md (#1586).
4
+ * Design notes live with the TWZRD intel service.
5
5
  *
6
6
  * One name across five adapters:
7
7
  * 1. Fetch / payWrap — guard raw fetch, then hand to x402 payer
@@ -16,12 +16,27 @@ export type BasePreflightVerdict = {
16
16
  /** TWZRD's current preflight calls this trust_score; normalized here for callers. */
17
17
  riskScore: number | null;
18
18
  reasons: string[];
19
+ /** Free preflight fields the signing rules below read (0.11.2). */
20
+ nullReason?: string | null;
21
+ scoreIsNull?: boolean;
22
+ recommendedCapUsdc?: number | null;
23
+ washFlagged?: boolean | null;
19
24
  };
25
+ /** Base mainnet USDC. The only asset this module signs for. */
26
+ export declare const BASE_USDC = "0x833589fcd6edb6e08f4c7c32d4f71b54bda02913";
20
27
  export type CloudflareBaseGateOptions = {
21
28
  intelBase?: string;
22
29
  fetch?: typeof fetch;
23
- /** Explicit price context only; x402 atomic amounts are never treated as USD. */
30
+ /**
31
+ * Ignored for the signing decision since 0.11.2: the price is read from the
32
+ * Base USDC entry's own `amount`, so a caller cannot understate it.
33
+ * @deprecated
34
+ */
24
35
  priceUsdc?: number;
36
+ /** Refuse an evaluated seller scoring below this (default 40, same as the package). */
37
+ preflightMinScore?: number;
38
+ /** Refuse every seller intel has never evaluated (same as the package option). */
39
+ refuseUnevaluated?: boolean;
25
40
  resourceName?: string;
26
41
  agentIntent?: string;
27
42
  /** Default false: an unavailable or malformed preflight does not permit signing. */
@@ -43,7 +58,14 @@ export declare function twzrdBasePreflight(requirements: CloudflareBaseRequireme
43
58
  export declare function createTwzrdCloudflareBaseApproval(options?: CloudflareBaseGateOptions): (requirements: CloudflareBaseRequirements) => Promise<boolean>;
44
59
  /**
45
60
  * Minimal signing interceptor for a Worker or Viem account. The callback is
46
- * invoked only after the exact Base payTo received a non-block verdict.
61
+ * invoked only when the Base USDC offer passes the package's signing rules:
62
+ * not blocked, not wash-flagged, a never-evaluated seller within its cap, an
63
+ * evaluated seller at or above the score floor and within its cap (0.11.2).
47
64
  */
48
65
  export declare function withTwzrdBasePreflight<T>(requirements: CloudflareBaseRequirements, options: CloudflareBaseGateOptions, signOrSend: () => Promise<T>): Promise<T>;
66
+ /**
67
+ * The package's signing rules applied to a Base preflight card (0.11.2).
68
+ * Before 0.11.2 this module signed on any non-block verdict.
69
+ */
70
+ export declare function baseRefusal(verdict: BasePreflightVerdict, priceUsdc: number, options?: Pick<CloudflareBaseGateOptions, "preflightMinScore" | "refuseUnevaluated">): string | undefined;
49
71
  //# sourceMappingURL=cloudflare-base.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"cloudflare-base.d.ts","sourceRoot":"","sources":["../src/cloudflare-base.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,eAAO,MAAM,aAAa,OAAO,CAAC;AAClC,eAAO,MAAM,YAAY,gBAA4B,CAAC;AAEtD,MAAM,MAAM,0BAA0B,GAAG;IACvC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,OAAO,CAAC,EAAE,KAAK,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC;CAC1C,CAAC;AAEF,MAAM,MAAM,oBAAoB,GAAG;IACjC,QAAQ,EAAE,OAAO,GAAG,MAAM,GAAG,OAAO,CAAC;IACrC,qFAAqF;IACrF,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,OAAO,EAAE,MAAM,EAAE,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,yBAAyB,GAAG;IACtC,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,KAAK,CAAC,EAAE,OAAO,KAAK,CAAC;IACrB,iFAAiF;IACjF,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,oFAAoF;IACpF,QAAQ,CAAC,EAAE,OAAO,CAAC;CACpB,CAAC;AAEF,qBAAa,4BAA6B,SAAQ,KAAK;IACrD,QAAQ,CAAC,OAAO,EAAE,oBAAoB,CAAC;gBAE3B,OAAO,EAAE,oBAAoB;CAK1C;AAED;;;;;;GAMG;AACH,wBAAsB,kBAAkB,CACtC,YAAY,EAAE,0BAA0B,EACxC,OAAO,GAAE,yBAA8B,GACtC,OAAO,CAAC,oBAAoB,CAAC,CAqB/B;AAED,qFAAqF;AACrF,wBAAgB,iCAAiC,CAC/C,OAAO,GAAE,yBAA8B,GACtC,CAAC,YAAY,EAAE,0BAA0B,KAAK,OAAO,CAAC,OAAO,CAAC,CAQhE;AAED;;;GAGG;AACH,wBAAsB,sBAAsB,CAAC,CAAC,EAC5C,YAAY,EAAE,0BAA0B,EACxC,OAAO,EAAE,yBAAyB,EAClC,UAAU,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GAC3B,OAAO,CAAC,CAAC,CAAC,CAUZ"}
1
+ {"version":3,"file":"cloudflare-base.d.ts","sourceRoot":"","sources":["../src/cloudflare-base.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,eAAO,MAAM,aAAa,OAAO,CAAC;AAClC,eAAO,MAAM,YAAY,gBAA4B,CAAC;AAEtD,MAAM,MAAM,0BAA0B,GAAG;IACvC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,OAAO,CAAC,EAAE,KAAK,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC;CAC1C,CAAC;AAEF,MAAM,MAAM,oBAAoB,GAAG;IACjC,QAAQ,EAAE,OAAO,GAAG,MAAM,GAAG,OAAO,CAAC;IACrC,qFAAqF;IACrF,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,OAAO,EAAE,MAAM,EAAE,CAAC;IAClB,mEAAmE;IACnE,UAAU,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,kBAAkB,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACnC,WAAW,CAAC,EAAE,OAAO,GAAG,IAAI,CAAC;CAC9B,CAAC;AAEF,+DAA+D;AAC/D,eAAO,MAAM,SAAS,+CAA+C,CAAC;AAEtE,MAAM,MAAM,yBAAyB,GAAG;IACtC,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,KAAK,CAAC,EAAE,OAAO,KAAK,CAAC;IACrB;;;;OAIG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,uFAAuF;IACvF,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,kFAAkF;IAClF,iBAAiB,CAAC,EAAE,OAAO,CAAC;IAC5B,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,oFAAoF;IACpF,QAAQ,CAAC,EAAE,OAAO,CAAC;CACpB,CAAC;AAEF,qBAAa,4BAA6B,SAAQ,KAAK;IACrD,QAAQ,CAAC,OAAO,EAAE,oBAAoB,CAAC;gBAE3B,OAAO,EAAE,oBAAoB;CAK1C;AAED;;;;;;GAMG;AACH,wBAAsB,kBAAkB,CACtC,YAAY,EAAE,0BAA0B,EACxC,OAAO,GAAE,yBAA8B,GACtC,OAAO,CAAC,oBAAoB,CAAC,CAqB/B;AAED,qFAAqF;AACrF,wBAAgB,iCAAiC,CAC/C,OAAO,GAAE,yBAA8B,GACtC,CAAC,YAAY,EAAE,0BAA0B,KAAK,OAAO,CAAC,OAAO,CAAC,CAgBhE;AAED;;;;;GAKG;AACH,wBAAsB,sBAAsB,CAAC,CAAC,EAC5C,YAAY,EAAE,0BAA0B,EACxC,OAAO,EAAE,yBAAyB,EAClC,UAAU,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GAC3B,OAAO,CAAC,CAAC,CAAC,CAyBZ;AAgDD;;;GAGG;AACH,wBAAgB,WAAW,CACzB,OAAO,EAAE,oBAAoB,EAC7B,SAAS,EAAE,MAAM,EACjB,OAAO,GAAE,IAAI,CAAC,yBAAyB,EAAE,mBAAmB,GAAG,mBAAmB,CAAM,GACvF,MAAM,GAAG,SAAS,CAoBpB"}