@reapp-sdk/express-middleware 0.1.0 → 0.2.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.
@@ -0,0 +1,62 @@
1
+ function freezeResponse(response) {
2
+ return Object.freeze({ ...response });
3
+ }
4
+ function freezeExecuting(record, executionId, startedAt) {
5
+ return Object.freeze({
6
+ key: record.key,
7
+ proofDigest: record.proofDigest,
8
+ payment: Object.freeze({ ...record.payment }),
9
+ executionId,
10
+ startedAt,
11
+ state: "executing",
12
+ });
13
+ }
14
+ /** Process-local reference store. Production and restart drills need a durable shared store. */
15
+ export class InMemoryBoundRedemptionStore {
16
+ records = new Map();
17
+ lookup(key, proofDigest) {
18
+ const record = this.records.get(key);
19
+ if (!record)
20
+ return { kind: "missing" };
21
+ if (record.proofDigest !== proofDigest)
22
+ return { kind: "conflict" };
23
+ return { kind: record.state, record };
24
+ }
25
+ claim(record, executionId, startedAt) {
26
+ const existing = this.records.get(record.key);
27
+ if (existing) {
28
+ if (existing.proofDigest !== record.proofDigest)
29
+ return { kind: "conflict" };
30
+ return { kind: existing.state, record: existing };
31
+ }
32
+ const claimed = freezeExecuting(record, executionId, startedAt);
33
+ this.records.set(record.key, claimed);
34
+ return { kind: "claimed", record: claimed };
35
+ }
36
+ complete(completion) {
37
+ const existing = this.records.get(completion.key);
38
+ if (!existing
39
+ || existing.proofDigest !== completion.proofDigest
40
+ || existing.executionId !== completion.executionId) {
41
+ return { kind: "conflict" };
42
+ }
43
+ if (existing.state === "completed") {
44
+ const same = existing.response.status === completion.response.status
45
+ && existing.response.contentType === completion.response.contentType
46
+ && existing.response.bodyBase64 === completion.response.bodyBase64
47
+ && existing.response.bodySha256 === completion.response.bodySha256;
48
+ return same ? { kind: "completed", record: existing } : { kind: "conflict" };
49
+ }
50
+ const completed = Object.freeze({
51
+ ...existing,
52
+ state: "completed",
53
+ response: freezeResponse(completion.response),
54
+ });
55
+ this.records.set(completion.key, completed);
56
+ return { kind: "completed", record: completed };
57
+ }
58
+ get(key) {
59
+ return this.records.get(key);
60
+ }
61
+ }
62
+ //# sourceMappingURL=bound-store.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"bound-store.js","sourceRoot":"","sources":["../src/bound-store.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,66 @@
1
+ import { BOUND_PAYMENT_SCHEME, type BoundPaymentChallengeV2 } from "@reapp-sdk/core";
2
+ import { type NetworkConfig } from "@reapp-sdk/stellar";
3
+ import type { RequestHandler, Response } from "express";
4
+ import type { BoundDeliveryRecord, BoundRedemptionStore } from "./bound-store.js";
5
+ import type { PaymentVerifier, RequestValue } from "./types.js";
6
+ export interface BoundReappPaymentMiddlewareOptions {
7
+ /** Merchant address that must receive the contract-authorized transfer. */
8
+ merchant: string;
9
+ /** Price as a human decimal string, or a request-specific resolver. */
10
+ amount: RequestValue;
11
+ /** Exact public HTTP(S) origin configured by the merchant; never Host-derived. */
12
+ audience: RequestValue;
13
+ /** At least 32 bytes. Keep stable across restarts and never expose it to clients. */
14
+ challengeSecret: string | Uint8Array;
15
+ /** Atomic transaction-to-proof binding. Must be durable and shared in production. */
16
+ redemptionStore: BoundRedemptionStore;
17
+ /** Exact path + query resolver. Defaults to request.originalUrl. */
18
+ resource?: RequestValue;
19
+ /** SEP-41 asset contract. Defaults to networkConfig.nativeSac. */
20
+ asset?: string;
21
+ /** Contract/RPC configuration. Defaults to REAPP testnet. */
22
+ networkConfig?: NetworkConfig;
23
+ /** x402 network label. Defaults to stellar-testnet. */
24
+ network?: string;
25
+ /** Asset decimals. Defaults to 7. */
26
+ decimals?: number;
27
+ /** Funded G-address used only for read-only contract simulations. */
28
+ sourceAccount?: string;
29
+ /** Optional verifier injection for tests or alternate trusted RPC infrastructure. */
30
+ verifier?: PaymentVerifier;
31
+ pollAttempts?: number;
32
+ pollIntervalMs?: number;
33
+ maxProofAgeLedgers?: number;
34
+ maxHeaderBytes?: number;
35
+ allowHttpRpc?: boolean;
36
+ /** Bound challenge lifetime in seconds. Defaults to 900. */
37
+ challengeTtlSeconds?: number;
38
+ /** Deterministic test hook. Must return safe whole Unix seconds. */
39
+ now?: () => number;
40
+ /** Deterministic test hook. Production uses node:crypto randomBytes. */
41
+ randomBytes?: (size: number) => Uint8Array;
42
+ }
43
+ export interface BoundX402Challenge {
44
+ x402Version: 1;
45
+ accepts: Array<{
46
+ scheme: typeof BOUND_PAYMENT_SCHEME;
47
+ network: string;
48
+ maxAmountRequired: string;
49
+ asset: string;
50
+ payTo: string;
51
+ resource: string;
52
+ extra: {
53
+ contract: string;
54
+ reappProofVersion: 2;
55
+ challenge: BoundPaymentChallengeV2;
56
+ };
57
+ }>;
58
+ }
59
+ export declare const REAPP_BOUND_DELIVERY_LOCALS_KEY = "reappBoundDelivery";
60
+ export interface BoundDeliveryContext {
61
+ kind: "claimed" | "completed";
62
+ record: Readonly<BoundDeliveryRecord>;
63
+ }
64
+ export declare function getBoundDeliveryContext(response: Response): BoundDeliveryContext | undefined;
65
+ export declare function createBoundReappPaymentMiddleware(options: BoundReappPaymentMiddlewareOptions): RequestHandler;
66
+ //# sourceMappingURL=bound.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"bound.d.ts","sourceRoot":"","sources":["../src/bound.ts"],"names":[],"mappings":"AASA,OAAO,EAEL,oBAAoB,EASpB,KAAK,uBAAuB,EAE7B,MAAM,iBAAiB,CAAC;AACzB,OAAO,EAAW,KAAK,aAAa,EAAE,MAAM,oBAAoB,CAAC;AACjE,OAAO,KAAK,EAAyB,cAAc,EAAE,QAAQ,EAAE,MAAM,SAAS,CAAC;AAM/E,OAAO,KAAK,EACV,mBAAmB,EAInB,oBAAoB,EACrB,MAAM,kBAAkB,CAAC;AAC1B,OAAO,KAAK,EAEV,eAAe,EACf,YAAY,EAEb,MAAM,YAAY,CAAC;AAEpB,MAAM,WAAW,kCAAkC;IACjD,2EAA2E;IAC3E,QAAQ,EAAE,MAAM,CAAC;IACjB,uEAAuE;IACvE,MAAM,EAAE,YAAY,CAAC;IACrB,kFAAkF;IAClF,QAAQ,EAAE,YAAY,CAAC;IACvB,qFAAqF;IACrF,eAAe,EAAE,MAAM,GAAG,UAAU,CAAC;IACrC,qFAAqF;IACrF,eAAe,EAAE,oBAAoB,CAAC;IACtC,oEAAoE;IACpE,QAAQ,CAAC,EAAE,YAAY,CAAC;IACxB,kEAAkE;IAClE,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,6DAA6D;IAC7D,aAAa,CAAC,EAAE,aAAa,CAAC;IAC9B,uDAAuD;IACvD,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,qCAAqC;IACrC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,qEAAqE;IACrE,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,qFAAqF;IACrF,QAAQ,CAAC,EAAE,eAAe,CAAC;IAC3B,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,4DAA4D;IAC5D,mBAAmB,CAAC,EAAE,MAAM,CAAC;IAC7B,oEAAoE;IACpE,GAAG,CAAC,EAAE,MAAM,MAAM,CAAC;IACnB,wEAAwE;IACxE,WAAW,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,UAAU,CAAC;CAC5C;AAED,MAAM,WAAW,kBAAkB;IACjC,WAAW,EAAE,CAAC,CAAC;IACf,OAAO,EAAE,KAAK,CAAC;QACb,MAAM,EAAE,OAAO,oBAAoB,CAAC;QACpC,OAAO,EAAE,MAAM,CAAC;QAChB,iBAAiB,EAAE,MAAM,CAAC;QAC1B,KAAK,EAAE,MAAM,CAAC;QACd,KAAK,EAAE,MAAM,CAAC;QACd,QAAQ,EAAE,MAAM,CAAC;QACjB,KAAK,EAAE;YACL,QAAQ,EAAE,MAAM,CAAC;YACjB,iBAAiB,EAAE,CAAC,CAAC;YACrB,SAAS,EAAE,uBAAuB,CAAC;SACpC,CAAC;KACH,CAAC,CAAC;CACJ;AAED,eAAO,MAAM,+BAA+B,uBAAuB,CAAC;AAEpE,MAAM,WAAW,oBAAoB;IACnC,IAAI,EAAE,SAAS,GAAG,WAAW,CAAC;IAC9B,MAAM,EAAE,QAAQ,CAAC,mBAAmB,CAAC,CAAC;CACvC;AAED,wBAAgB,uBAAuB,CAAC,QAAQ,EAAE,QAAQ,GAAG,oBAAoB,GAAG,SAAS,CAE5F;AAmGD,wBAAgB,iCAAiC,CAC/C,OAAO,EAAE,kCAAkC,GAC1C,cAAc,CAwXhB"}
package/dist/bound.js ADDED
@@ -0,0 +1,447 @@
1
+ import { createHash, createHmac, randomBytes as secureRandomBytes, randomUUID, timingSafeEqual, } from "node:crypto";
2
+ import { Buffer } from "buffer";
3
+ import { Address, StrKey } from "@stellar/stellar-sdk";
4
+ import { BOUND_PAYMENT_CAPABILITY, BOUND_PAYMENT_SCHEME, REAPP_PAYMENT_CAPABILITIES_HEADER, X_PAYMENT_HEADER, boundChallengeAuthorizationBytes, canonicalPaymentOrigin, decodePaymentProof, isBoundPaymentProof, toStroops, verifyBoundPaymentProofSignature, } from "@reapp-sdk/core";
5
+ import { TESTNET } from "@reapp-sdk/stellar";
6
+ import { createStellarPaymentVerifier } from "./verification.js";
7
+ import { REAPP_PAYMENT_LOCALS_KEY, createRedemptionKey, } from "./middleware.js";
8
+ export const REAPP_BOUND_DELIVERY_LOCALS_KEY = "reappBoundDelivery";
9
+ export function getBoundDeliveryContext(response) {
10
+ return response.locals[REAPP_BOUND_DELIVERY_LOCALS_KEY];
11
+ }
12
+ const DEFAULT_MAX_HEADER_BYTES = 8_192;
13
+ const DEFAULT_MAX_PROOF_AGE_LEDGERS = 120;
14
+ const DEFAULT_CHALLENGE_TTL_SECONDS = 900;
15
+ function exactText(label, value) {
16
+ if (typeof value !== "string" || value.length === 0 || value.trim() !== value) {
17
+ throw new Error(`${label} must be a non-empty exact string.`);
18
+ }
19
+ return value;
20
+ }
21
+ function stellarAddress(label, value) {
22
+ const address = exactText(label, value);
23
+ try {
24
+ Address.fromString(address);
25
+ }
26
+ catch {
27
+ throw new Error(`${label} must be a valid Stellar address.`);
28
+ }
29
+ return address;
30
+ }
31
+ function resolveRequestValue(label, value, request) {
32
+ return exactText(label, typeof value === "function" ? value(request) : value);
33
+ }
34
+ function setPrivateResponseHeaders(response) {
35
+ response.set("cache-control", "private, no-store");
36
+ response.vary("X-PAYMENT");
37
+ response.vary("REAPP-PAYMENT-CAPABILITIES");
38
+ }
39
+ function json(response, status, body, retryAfter) {
40
+ setPrivateResponseHeaders(response);
41
+ response.status(status);
42
+ if (retryAfter)
43
+ response.set("retry-after", retryAfter);
44
+ response.json(body);
45
+ }
46
+ function oneRawHeader(request, name, maxBytes) {
47
+ const values = [];
48
+ for (let index = 0; index < request.rawHeaders.length; index += 2) {
49
+ const headerName = request.rawHeaders[index];
50
+ const value = request.rawHeaders[index + 1];
51
+ if (headerName?.toLowerCase() === name && value !== undefined)
52
+ values.push(value);
53
+ }
54
+ if (values.length === 0)
55
+ return undefined;
56
+ if (values.length !== 1)
57
+ throw new Error(`multiple ${name} headers are not allowed`);
58
+ const header = values[0];
59
+ if (Buffer.byteLength(header, "utf8") > maxBytes) {
60
+ throw new Error(`${name} header exceeds the configured size limit`);
61
+ }
62
+ return header;
63
+ }
64
+ function canonicalPaymentHeader(request, maxBytes) {
65
+ const header = oneRawHeader(request, X_PAYMENT_HEADER, maxBytes);
66
+ if (header === undefined)
67
+ return undefined;
68
+ if (header.length === 0
69
+ || header.includes(",")
70
+ || !/^(?:[A-Za-z0-9+/]{4})*(?:[A-Za-z0-9+/]{2}==|[A-Za-z0-9+/]{3}=)?$/.test(header)
71
+ || Buffer.from(header, "base64").toString("base64") !== header) {
72
+ throw new Error("X-PAYMENT header is not canonical base64");
73
+ }
74
+ return header;
75
+ }
76
+ function captureNow(now) {
77
+ const value = now();
78
+ if (!Number.isSafeInteger(value) || value <= 0) {
79
+ throw new Error("payment middleware clock must return safe whole Unix seconds");
80
+ }
81
+ return value;
82
+ }
83
+ function authenticateChallenge(unsigned, secret) {
84
+ const mac = createHmac("sha256", secret)
85
+ .update(boundChallengeAuthorizationBytes(unsigned))
86
+ .digest("base64");
87
+ return Object.freeze({
88
+ ...unsigned,
89
+ authorization: Object.freeze({ algorithm: "hmac-sha256", mac }),
90
+ });
91
+ }
92
+ function challengeMacIsValid(challenge, secret) {
93
+ const expected = createHmac("sha256", secret)
94
+ .update(boundChallengeAuthorizationBytes(challenge))
95
+ .digest();
96
+ const actual = Buffer.from(challenge.authorization.mac, "base64");
97
+ return actual.length === expected.length && timingSafeEqual(actual, expected);
98
+ }
99
+ export function createBoundReappPaymentMiddleware(options) {
100
+ if (!options || typeof options !== "object") {
101
+ throw new Error("REAPP bound payment middleware options are required.");
102
+ }
103
+ if (!options.redemptionStore
104
+ || typeof options.redemptionStore.lookup !== "function"
105
+ || typeof options.redemptionStore.claim !== "function"
106
+ || typeof options.redemptionStore.complete !== "function") {
107
+ throw new Error("redemptionStore with atomic lookup, claim, and complete operations is required.");
108
+ }
109
+ const networkConfig = options.networkConfig ?? TESTNET;
110
+ const merchant = stellarAddress("merchant", options.merchant);
111
+ const registryId = exactText("networkConfig.mandateRegistryId", networkConfig.mandateRegistryId);
112
+ if (!StrKey.isValidContract(registryId)) {
113
+ throw new Error("networkConfig.mandateRegistryId must be a valid Stellar contract address.");
114
+ }
115
+ const asset = exactText("asset", options.asset ?? networkConfig.nativeSac);
116
+ if (!StrKey.isValidContract(asset))
117
+ throw new Error("asset must be a valid Stellar contract address.");
118
+ if (typeof options.audience === "string")
119
+ canonicalPaymentOrigin(options.audience, "audience");
120
+ const network = exactText("network", options.network ?? "stellar-testnet");
121
+ const decimals = options.decimals ?? 7;
122
+ const maxHeaderBytes = options.maxHeaderBytes ?? DEFAULT_MAX_HEADER_BYTES;
123
+ const maxProofAgeLedgers = options.maxProofAgeLedgers ?? DEFAULT_MAX_PROOF_AGE_LEDGERS;
124
+ const challengeTtlSeconds = options.challengeTtlSeconds ?? DEFAULT_CHALLENGE_TTL_SECONDS;
125
+ const now = options.now ?? (() => Math.floor(Date.now() / 1_000));
126
+ const randomBytes = options.randomBytes ?? secureRandomBytes;
127
+ const challengeSecret = Buffer.from(typeof options.challengeSecret === "string"
128
+ ? Buffer.from(options.challengeSecret, "utf8")
129
+ : options.challengeSecret);
130
+ if (challengeSecret.length < 32 || challengeSecret.length > 4_096) {
131
+ throw new Error("challengeSecret must contain 32 through 4096 bytes.");
132
+ }
133
+ if (!Number.isInteger(decimals) || decimals < 0 || decimals > 38) {
134
+ throw new Error("decimals must be an integer from 0 through 38.");
135
+ }
136
+ if (!Number.isInteger(maxHeaderBytes) || maxHeaderBytes < 256 || maxHeaderBytes > 65_536) {
137
+ throw new Error("maxHeaderBytes must be an integer from 256 through 65536.");
138
+ }
139
+ if (!Number.isInteger(maxProofAgeLedgers) || maxProofAgeLedgers < 0 || maxProofAgeLedgers > 1_000_000) {
140
+ throw new Error("maxProofAgeLedgers must be an integer from 0 through 1000000.");
141
+ }
142
+ if (!Number.isInteger(challengeTtlSeconds) || challengeTtlSeconds < 30 || challengeTtlSeconds > 3_600) {
143
+ throw new Error("challengeTtlSeconds must be an integer from 30 through 3600.");
144
+ }
145
+ if (typeof options.amount === "string") {
146
+ const staticAmount = toStroops(exactText("amount", options.amount), decimals);
147
+ if (staticAmount <= 0n)
148
+ throw new Error("amount must be greater than zero.");
149
+ }
150
+ if (typeof options.resource === "string")
151
+ exactText("resource", options.resource);
152
+ const networkId = createHash("sha256")
153
+ .update(networkConfig.networkPassphrase, "utf8")
154
+ .digest("hex");
155
+ const verifier = options.verifier ?? createStellarPaymentVerifier({
156
+ networkConfig,
157
+ sourceAccount: options.sourceAccount ?? merchant,
158
+ pollAttempts: options.pollAttempts,
159
+ pollIntervalMs: options.pollIntervalMs,
160
+ maxProofAgeLedgers,
161
+ allowHttpRpc: options.allowHttpRpc,
162
+ });
163
+ function requirementFor(request) {
164
+ const amount = resolveRequestValue("amount", options.amount, request);
165
+ const amountStroops = toStroops(amount, decimals);
166
+ if (amountStroops <= 0n)
167
+ throw new Error("amount must be greater than zero.");
168
+ const resource = options.resource === undefined
169
+ ? exactText("resource", request.originalUrl || request.url)
170
+ : resolveRequestValue("resource", options.resource, request);
171
+ return Object.freeze({
172
+ scheme: BOUND_PAYMENT_SCHEME,
173
+ network,
174
+ resource,
175
+ merchant,
176
+ asset,
177
+ amount,
178
+ amountStroops,
179
+ registryId,
180
+ decimals,
181
+ });
182
+ }
183
+ function challengeFor(request, requirement, capturedNow, audience) {
184
+ const entropy = Buffer.from(randomBytes(32));
185
+ if (entropy.length !== 32)
186
+ throw new Error("randomBytes must return exactly the requested bytes");
187
+ const unsigned = {
188
+ proofVersion: 2,
189
+ challengeId: entropy.toString("base64url"),
190
+ audience,
191
+ scheme: BOUND_PAYMENT_SCHEME,
192
+ method: request.method.toUpperCase(),
193
+ resource: requirement.resource,
194
+ bodySha256: null,
195
+ network,
196
+ networkId,
197
+ registryId,
198
+ merchant,
199
+ asset,
200
+ amountStroops: requirement.amountStroops.toString(),
201
+ decimals,
202
+ issuedAt: capturedNow,
203
+ expiresAt: capturedNow + challengeTtlSeconds,
204
+ };
205
+ const challenge = authenticateChallenge(unsigned, challengeSecret);
206
+ return {
207
+ x402Version: 1,
208
+ accepts: [{
209
+ scheme: BOUND_PAYMENT_SCHEME,
210
+ network,
211
+ maxAmountRequired: requirement.amount,
212
+ asset,
213
+ payTo: merchant,
214
+ resource: requirement.resource,
215
+ extra: { contract: registryId, reappProofVersion: 2, challenge },
216
+ }],
217
+ };
218
+ }
219
+ const handle = async (request, response, next) => {
220
+ const method = request.method.toUpperCase();
221
+ if (method !== "GET") {
222
+ response.set("allow", "GET");
223
+ json(response, 405, { error: "bound payment routes permit only GET requests" });
224
+ return;
225
+ }
226
+ let requirement;
227
+ let audience;
228
+ let capturedNow;
229
+ try {
230
+ requirement = requirementFor(request);
231
+ audience = canonicalPaymentOrigin(resolveRequestValue("audience", options.audience, request), "audience");
232
+ capturedNow = captureNow(now);
233
+ }
234
+ catch {
235
+ json(response, 500, { error: "payment middleware configuration failed closed" });
236
+ return;
237
+ }
238
+ let capability;
239
+ try {
240
+ capability = oneRawHeader(request, REAPP_PAYMENT_CAPABILITIES_HEADER, 256);
241
+ }
242
+ catch {
243
+ json(response, 426, {
244
+ error: "a single canonical REAPP payment capability is required",
245
+ requiredCapability: BOUND_PAYMENT_CAPABILITY,
246
+ });
247
+ return;
248
+ }
249
+ if (capability !== BOUND_PAYMENT_CAPABILITY) {
250
+ response.set("upgrade", BOUND_PAYMENT_CAPABILITY);
251
+ json(response, 426, {
252
+ error: "this route requires an agent-bound payment proof",
253
+ requiredCapability: BOUND_PAYMENT_CAPABILITY,
254
+ });
255
+ return;
256
+ }
257
+ let challengeBody;
258
+ try {
259
+ challengeBody = challengeFor(request, requirement, capturedNow, audience);
260
+ }
261
+ catch {
262
+ json(response, 500, { error: "payment challenge generation failed closed" });
263
+ return;
264
+ }
265
+ let header;
266
+ try {
267
+ header = canonicalPaymentHeader(request, maxHeaderBytes);
268
+ }
269
+ catch {
270
+ json(response, 402, { error: "malformed X-PAYMENT proof", ...challengeBody });
271
+ return;
272
+ }
273
+ if (!header) {
274
+ json(response, 402, challengeBody);
275
+ return;
276
+ }
277
+ let proof;
278
+ try {
279
+ proof = decodePaymentProof(header);
280
+ }
281
+ catch {
282
+ json(response, 402, { error: "malformed X-PAYMENT proof", ...challengeBody });
283
+ return;
284
+ }
285
+ if (!isBoundPaymentProof(proof)) {
286
+ json(response, 402, { error: "a bound-v2 proof is required", ...challengeBody });
287
+ return;
288
+ }
289
+ const challenge = proof.challenge;
290
+ const exactChallenge = challenge.proofVersion === 2
291
+ && challenge.audience === audience
292
+ && challenge.scheme === BOUND_PAYMENT_SCHEME
293
+ && challenge.method === method
294
+ && challenge.resource === requirement.resource
295
+ && challenge.bodySha256 === null
296
+ && challenge.network === network
297
+ && challenge.networkId === networkId
298
+ && challenge.registryId === registryId
299
+ && challenge.merchant === merchant
300
+ && challenge.asset === asset
301
+ && challenge.amountStroops === requirement.amountStroops.toString()
302
+ && challenge.decimals === decimals
303
+ && challenge.expiresAt - challenge.issuedAt === challengeTtlSeconds
304
+ && challenge.authorization.algorithm === "hmac-sha256"
305
+ && challengeMacIsValid(challenge, challengeSecret)
306
+ && proof.scheme === BOUND_PAYMENT_SCHEME
307
+ && proof.network === network;
308
+ if (!exactChallenge) {
309
+ json(response, 402, { error: "payment proof is not bound to this exact request", ...challengeBody });
310
+ return;
311
+ }
312
+ const proofDigest = createHash("sha256")
313
+ .update(JSON.stringify(proof), "utf8")
314
+ .digest("hex");
315
+ const redemptionKey = createRedemptionKey(networkConfig.networkPassphrase, registryId, proof.txHash);
316
+ const paymentMatchesProof = (payment) => payment.txHash === proof.txHash
317
+ && payment.mandateId === proof.mandateId
318
+ && payment.amountStroops === requirement.amountStroops
319
+ && payment.merchant === merchant
320
+ && payment.asset === asset
321
+ && payment.registryId === registryId
322
+ && payment.scheme === BOUND_PAYMENT_SCHEME
323
+ && payment.network === network
324
+ && verifyBoundPaymentProofSignature(proof, payment.agent);
325
+ let existing;
326
+ try {
327
+ existing = await options.redemptionStore.lookup(redemptionKey, proofDigest);
328
+ if (!existing || !["missing", "executing", "completed", "conflict"].includes(existing.kind)) {
329
+ throw new Error("redemption store returned an unsupported lookup result");
330
+ }
331
+ }
332
+ catch {
333
+ json(response, 503, {
334
+ error: "payment redemption store is unavailable; retry with the same proof",
335
+ retryable: true,
336
+ }, "1");
337
+ return;
338
+ }
339
+ if (existing.kind === "conflict") {
340
+ json(response, 409, { error: "this settlement transaction is already bound to another request" });
341
+ return;
342
+ }
343
+ if (existing.kind === "executing") {
344
+ json(response, 503, {
345
+ error: "paid fulfillment is still pending; retry the same proof",
346
+ retryable: true,
347
+ }, "1");
348
+ return;
349
+ }
350
+ if (existing.kind === "completed") {
351
+ if (existing.record.key !== redemptionKey
352
+ || existing.record.proofDigest !== proofDigest
353
+ || !paymentMatchesProof(existing.record.payment)) {
354
+ json(response, 503, { error: "stored payment recovery evidence failed closed" }, "1");
355
+ return;
356
+ }
357
+ response.locals[REAPP_PAYMENT_LOCALS_KEY] = existing.record.payment;
358
+ response.locals[REAPP_BOUND_DELIVERY_LOCALS_KEY] = Object.freeze({
359
+ kind: "completed",
360
+ record: existing.record,
361
+ });
362
+ setPrivateResponseHeaders(response);
363
+ next();
364
+ return;
365
+ }
366
+ if (challenge.issuedAt > capturedNow + 60 || challenge.expiresAt <= capturedNow) {
367
+ json(response, 402, { error: "payment challenge is expired or not yet valid", ...challengeBody });
368
+ return;
369
+ }
370
+ let verdict;
371
+ try {
372
+ verdict = await verifier.verify(proof.txHash, requirement);
373
+ }
374
+ catch {
375
+ json(response, 503, {
376
+ error: "payment verification is temporarily unavailable; retry with the same proof",
377
+ retryable: true,
378
+ }, "1");
379
+ return;
380
+ }
381
+ if (!verdict.ok) {
382
+ if (verdict.kind === "unavailable") {
383
+ json(response, 503, {
384
+ error: `payment verification unavailable: ${verdict.reason}`,
385
+ retryable: true,
386
+ }, "1");
387
+ }
388
+ else {
389
+ json(response, 402, { error: `payment not verified on-chain: ${verdict.reason}`, ...challengeBody });
390
+ }
391
+ return;
392
+ }
393
+ const payment = verdict.payment;
394
+ if (!paymentMatchesProof(payment)) {
395
+ json(response, 402, { error: "payment authorization did not match verified chain evidence", ...challengeBody });
396
+ return;
397
+ }
398
+ const record = Object.freeze({
399
+ key: redemptionKey,
400
+ proofDigest,
401
+ payment: Object.freeze({ ...payment }),
402
+ });
403
+ let claimed;
404
+ try {
405
+ claimed = await options.redemptionStore.claim(record, randomUUID(), capturedNow);
406
+ if (!claimed
407
+ || !["claimed", "executing", "completed", "conflict"].includes(claimed.kind)) {
408
+ throw new Error("redemption store returned an unsupported claim result");
409
+ }
410
+ }
411
+ catch {
412
+ json(response, 503, {
413
+ error: "payment redemption store is unavailable; retry with the same proof",
414
+ retryable: true,
415
+ }, "1");
416
+ return;
417
+ }
418
+ if (claimed.kind === "conflict") {
419
+ json(response, 409, { error: "this settlement transaction is already bound to another request" });
420
+ return;
421
+ }
422
+ if (claimed.kind === "executing") {
423
+ json(response, 503, {
424
+ error: "paid fulfillment is still pending; retry the same proof",
425
+ retryable: true,
426
+ }, "1");
427
+ return;
428
+ }
429
+ if (claimed.record.key !== redemptionKey
430
+ || claimed.record.proofDigest !== proofDigest
431
+ || !paymentMatchesProof(claimed.record.payment)) {
432
+ json(response, 503, { error: "stored payment redemption evidence failed closed" }, "1");
433
+ return;
434
+ }
435
+ response.locals[REAPP_PAYMENT_LOCALS_KEY] = claimed.record.payment;
436
+ response.locals[REAPP_BOUND_DELIVERY_LOCALS_KEY] = Object.freeze({
437
+ kind: claimed.kind,
438
+ record: claimed.record,
439
+ });
440
+ setPrivateResponseHeaders(response);
441
+ next();
442
+ };
443
+ return (request, response, next) => {
444
+ void handle(request, response, next).catch(next);
445
+ };
446
+ }
447
+ //# sourceMappingURL=bound.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"bound.js","sourceRoot":"","sources":["../src/bound.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,UAAU,EACV,UAAU,EACV,WAAW,IAAI,iBAAiB,EAChC,UAAU,EACV,eAAe,GAChB,MAAM,aAAa,CAAC;AACrB,OAAO,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAC;AAChC,OAAO,EAAE,OAAO,EAAE,MAAM,EAAE,MAAM,sBAAsB,CAAC;AACvD,OAAO,EACL,wBAAwB,EACxB,oBAAoB,EACpB,iCAAiC,EACjC,gBAAgB,EAChB,gCAAgC,EAChC,sBAAsB,EACtB,kBAAkB,EAClB,mBAAmB,EACnB,SAAS,EACT,gCAAgC,GAGjC,MAAM,iBAAiB,CAAC;AACzB,OAAO,EAAE,OAAO,EAAsB,MAAM,oBAAoB,CAAC;AAEjE,OAAO,EAAE,4BAA4B,EAAE,MAAM,mBAAmB,CAAC;AACjE,OAAO,EACL,wBAAwB,EACxB,mBAAmB,GACpB,MAAM,iBAAiB,CAAC;AAsEzB,MAAM,CAAC,MAAM,+BAA+B,GAAG,oBAAoB,CAAC;AAOpE,MAAM,UAAU,uBAAuB,CAAC,QAAkB;IACxD,OAAO,QAAQ,CAAC,MAAM,CAAC,+BAA+B,CAAqC,CAAC;AAC9F,CAAC;AAED,MAAM,wBAAwB,GAAG,KAAK,CAAC;AACvC,MAAM,6BAA6B,GAAG,GAAG,CAAC;AAC1C,MAAM,6BAA6B,GAAG,GAAG,CAAC;AAE1C,SAAS,SAAS,CAAC,KAAa,EAAE,KAAc;IAC9C,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,IAAI,KAAK,CAAC,IAAI,EAAE,KAAK,KAAK,EAAE,CAAC;QAC9E,MAAM,IAAI,KAAK,CAAC,GAAG,KAAK,oCAAoC,CAAC,CAAC;IAChE,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC;AAED,SAAS,cAAc,CAAC,KAAa,EAAE,KAAc;IACnD,MAAM,OAAO,GAAG,SAAS,CAAC,KAAK,EAAE,KAAK,CAAC,CAAC;IACxC,IAAI,CAAC;QACH,OAAO,CAAC,UAAU,CAAC,OAAO,CAAC,CAAC;IAC9B,CAAC;IAAC,MAAM,CAAC;QACP,MAAM,IAAI,KAAK,CAAC,GAAG,KAAK,mCAAmC,CAAC,CAAC;IAC/D,CAAC;IACD,OAAO,OAAO,CAAC;AACjB,CAAC;AAED,SAAS,mBAAmB,CAAC,KAAa,EAAE,KAAmB,EAAE,OAAgB;IAC/E,OAAO,SAAS,CAAC,KAAK,EAAE,OAAO,KAAK,KAAK,UAAU,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC;AAChF,CAAC;AAED,SAAS,yBAAyB,CAAC,QAAkB;IACnD,QAAQ,CAAC,GAAG,CAAC,eAAe,EAAE,mBAAmB,CAAC,CAAC;IACnD,QAAQ,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC;IAC3B,QAAQ,CAAC,IAAI,CAAC,4BAA4B,CAAC,CAAC;AAC9C,CAAC;AAED,SAAS,IAAI,CAAC,QAAkB,EAAE,MAAc,EAAE,IAAa,EAAE,UAAmB;IAClF,yBAAyB,CAAC,QAAQ,CAAC,CAAC;IACpC,QAAQ,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;IACxB,IAAI,UAAU;QAAE,QAAQ,CAAC,GAAG,CAAC,aAAa,EAAE,UAAU,CAAC,CAAC;IACxD,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AACtB,CAAC;AAED,SAAS,YAAY,CAAC,OAAgB,EAAE,IAAY,EAAE,QAAgB;IACpE,MAAM,MAAM,GAAa,EAAE,CAAC;IAC5B,KAAK,IAAI,KAAK,GAAG,CAAC,EAAE,KAAK,GAAG,OAAO,CAAC,UAAU,CAAC,MAAM,EAAE,KAAK,IAAI,CAAC,EAAE,CAAC;QAClE,MAAM,UAAU,GAAG,OAAO,CAAC,UAAU,CAAC,KAAK,CAAC,CAAC;QAC7C,MAAM,KAAK,GAAG,OAAO,CAAC,UAAU,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;QAC5C,IAAI,UAAU,EAAE,WAAW,EAAE,KAAK,IAAI,IAAI,KAAK,KAAK,SAAS;YAAE,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IACpF,CAAC;IACD,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,SAAS,CAAC;IAC1C,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC;QAAE,MAAM,IAAI,KAAK,CAAC,YAAY,IAAI,0BAA0B,CAAC,CAAC;IACrF,MAAM,MAAM,GAAG,MAAM,CAAC,CAAC,CAAW,CAAC;IACnC,IAAI,MAAM,CAAC,UAAU,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,QAAQ,EAAE,CAAC;QACjD,MAAM,IAAI,KAAK,CAAC,GAAG,IAAI,2CAA2C,CAAC,CAAC;IACtE,CAAC;IACD,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,SAAS,sBAAsB,CAAC,OAAgB,EAAE,QAAgB;IAChE,MAAM,MAAM,GAAG,YAAY,CAAC,OAAO,EAAE,gBAAgB,EAAE,QAAQ,CAAC,CAAC;IACjE,IAAI,MAAM,KAAK,SAAS;QAAE,OAAO,SAAS,CAAC;IAC3C,IACE,MAAM,CAAC,MAAM,KAAK,CAAC;WAChB,MAAM,CAAC,QAAQ,CAAC,GAAG,CAAC;WACpB,CAAC,kEAAkE,CAAC,IAAI,CAAC,MAAM,CAAC;WAChF,MAAM,CAAC,IAAI,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC,KAAK,MAAM,EAC9D,CAAC;QACD,MAAM,IAAI,KAAK,CAAC,0CAA0C,CAAC,CAAC;IAC9D,CAAC;IACD,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,SAAS,UAAU,CAAC,GAAiB;IACnC,MAAM,KAAK,GAAG,GAAG,EAAE,CAAC;IACpB,IAAI,CAAC,MAAM,CAAC,aAAa,CAAC,KAAK,CAAC,IAAI,KAAK,IAAI,CAAC,EAAE,CAAC;QAC/C,MAAM,IAAI,KAAK,CAAC,8DAA8D,CAAC,CAAC;IAClF,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC;AAED,SAAS,qBAAqB,CAC5B,QAAyC,EACzC,MAAc;IAEd,MAAM,GAAG,GAAG,UAAU,CAAC,QAAQ,EAAE,MAAM,CAAC;SACrC,MAAM,CAAC,gCAAgC,CAAC,QAAQ,CAAC,CAAC;SAClD,MAAM,CAAC,QAAQ,CAAC,CAAC;IACpB,OAAO,MAAM,CAAC,MAAM,CAAC;QACnB,GAAG,QAAQ;QACX,aAAa,EAAE,MAAM,CAAC,MAAM,CAAC,EAAE,SAAS,EAAE,aAAsB,EAAE,GAAG,EAAE,CAAC;KACzE,CAAC,CAAC;AACL,CAAC;AAED,SAAS,mBAAmB,CAAC,SAAkC,EAAE,MAAc;IAC7E,MAAM,QAAQ,GAAG,UAAU,CAAC,QAAQ,EAAE,MAAM,CAAC;SAC1C,MAAM,CAAC,gCAAgC,CAAC,SAAS,CAAC,CAAC;SACnD,MAAM,EAAE,CAAC;IACZ,MAAM,MAAM,GAAG,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC,aAAa,CAAC,GAAG,EAAE,QAAQ,CAAC,CAAC;IAClE,OAAO,MAAM,CAAC,MAAM,KAAK,QAAQ,CAAC,MAAM,IAAI,eAAe,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC;AAChF,CAAC;AAED,MAAM,UAAU,iCAAiC,CAC/C,OAA2C;IAE3C,IAAI,CAAC,OAAO,IAAI,OAAO,OAAO,KAAK,QAAQ,EAAE,CAAC;QAC5C,MAAM,IAAI,KAAK,CAAC,sDAAsD,CAAC,CAAC;IAC1E,CAAC;IACD,IACE,CAAC,OAAO,CAAC,eAAe;WACrB,OAAO,OAAO,CAAC,eAAe,CAAC,MAAM,KAAK,UAAU;WACpD,OAAO,OAAO,CAAC,eAAe,CAAC,KAAK,KAAK,UAAU;WACnD,OAAO,OAAO,CAAC,eAAe,CAAC,QAAQ,KAAK,UAAU,EACzD,CAAC;QACD,MAAM,IAAI,KAAK,CAAC,iFAAiF,CAAC,CAAC;IACrG,CAAC;IACD,MAAM,aAAa,GAAG,OAAO,CAAC,aAAa,IAAI,OAAO,CAAC;IACvD,MAAM,QAAQ,GAAG,cAAc,CAAC,UAAU,EAAE,OAAO,CAAC,QAAQ,CAAC,CAAC;IAC9D,MAAM,UAAU,GAAG,SAAS,CAAC,iCAAiC,EAAE,aAAa,CAAC,iBAAiB,CAAC,CAAC;IACjG,IAAI,CAAC,MAAM,CAAC,eAAe,CAAC,UAAU,CAAC,EAAE,CAAC;QACxC,MAAM,IAAI,KAAK,CAAC,2EAA2E,CAAC,CAAC;IAC/F,CAAC;IACD,MAAM,KAAK,GAAG,SAAS,CAAC,OAAO,EAAE,OAAO,CAAC,KAAK,IAAI,aAAa,CAAC,SAAS,CAAC,CAAC;IAC3E,IAAI,CAAC,MAAM,CAAC,eAAe,CAAC,KAAK,CAAC;QAAE,MAAM,IAAI,KAAK,CAAC,iDAAiD,CAAC,CAAC;IACvG,IAAI,OAAO,OAAO,CAAC,QAAQ,KAAK,QAAQ;QAAE,sBAAsB,CAAC,OAAO,CAAC,QAAQ,EAAE,UAAU,CAAC,CAAC;IAC/F,MAAM,OAAO,GAAG,SAAS,CAAC,SAAS,EAAE,OAAO,CAAC,OAAO,IAAI,iBAAiB,CAAC,CAAC;IAC3E,MAAM,QAAQ,GAAG,OAAO,CAAC,QAAQ,IAAI,CAAC,CAAC;IACvC,MAAM,cAAc,GAAG,OAAO,CAAC,cAAc,IAAI,wBAAwB,CAAC;IAC1E,MAAM,kBAAkB,GAAG,OAAO,CAAC,kBAAkB,IAAI,6BAA6B,CAAC;IACvF,MAAM,mBAAmB,GAAG,OAAO,CAAC,mBAAmB,IAAI,6BAA6B,CAAC;IACzF,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,CAAC,CAAC,CAAC;IAClE,MAAM,WAAW,GAAG,OAAO,CAAC,WAAW,IAAI,iBAAiB,CAAC;IAC7D,MAAM,eAAe,GAAG,MAAM,CAAC,IAAI,CACjC,OAAO,OAAO,CAAC,eAAe,KAAK,QAAQ;QACzC,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,OAAO,CAAC,eAAe,EAAE,MAAM,CAAC;QAC9C,CAAC,CAAC,OAAO,CAAC,eAAe,CAC5B,CAAC;IACF,IAAI,eAAe,CAAC,MAAM,GAAG,EAAE,IAAI,eAAe,CAAC,MAAM,GAAG,KAAK,EAAE,CAAC;QAClE,MAAM,IAAI,KAAK,CAAC,qDAAqD,CAAC,CAAC;IACzE,CAAC;IACD,IAAI,CAAC,MAAM,CAAC,SAAS,CAAC,QAAQ,CAAC,IAAI,QAAQ,GAAG,CAAC,IAAI,QAAQ,GAAG,EAAE,EAAE,CAAC;QACjE,MAAM,IAAI,KAAK,CAAC,gDAAgD,CAAC,CAAC;IACpE,CAAC;IACD,IAAI,CAAC,MAAM,CAAC,SAAS,CAAC,cAAc,CAAC,IAAI,cAAc,GAAG,GAAG,IAAI,cAAc,GAAG,MAAM,EAAE,CAAC;QACzF,MAAM,IAAI,KAAK,CAAC,2DAA2D,CAAC,CAAC;IAC/E,CAAC;IACD,IAAI,CAAC,MAAM,CAAC,SAAS,CAAC,kBAAkB,CAAC,IAAI,kBAAkB,GAAG,CAAC,IAAI,kBAAkB,GAAG,SAAS,EAAE,CAAC;QACtG,MAAM,IAAI,KAAK,CAAC,+DAA+D,CAAC,CAAC;IACnF,CAAC;IACD,IAAI,CAAC,MAAM,CAAC,SAAS,CAAC,mBAAmB,CAAC,IAAI,mBAAmB,GAAG,EAAE,IAAI,mBAAmB,GAAG,KAAK,EAAE,CAAC;QACtG,MAAM,IAAI,KAAK,CAAC,8DAA8D,CAAC,CAAC;IAClF,CAAC;IACD,IAAI,OAAO,OAAO,CAAC,MAAM,KAAK,QAAQ,EAAE,CAAC;QACvC,MAAM,YAAY,GAAG,SAAS,CAAC,SAAS,CAAC,QAAQ,EAAE,OAAO,CAAC,MAAM,CAAC,EAAE,QAAQ,CAAC,CAAC;QAC9E,IAAI,YAAY,IAAI,EAAE;YAAE,MAAM,IAAI,KAAK,CAAC,mCAAmC,CAAC,CAAC;IAC/E,CAAC;IACD,IAAI,OAAO,OAAO,CAAC,QAAQ,KAAK,QAAQ;QAAE,SAAS,CAAC,UAAU,EAAE,OAAO,CAAC,QAAQ,CAAC,CAAC;IAElF,MAAM,SAAS,GAAG,UAAU,CAAC,QAAQ,CAAC;SACnC,MAAM,CAAC,aAAa,CAAC,iBAAiB,EAAE,MAAM,CAAC;SAC/C,MAAM,CAAC,KAAK,CAAC,CAAC;IACjB,MAAM,QAAQ,GAAG,OAAO,CAAC,QAAQ,IAAI,4BAA4B,CAAC;QAChE,aAAa;QACb,aAAa,EAAE,OAAO,CAAC,aAAa,IAAI,QAAQ;QAChD,YAAY,EAAE,OAAO,CAAC,YAAY;QAClC,cAAc,EAAE,OAAO,CAAC,cAAc;QACtC,kBAAkB;QAClB,YAAY,EAAE,OAAO,CAAC,YAAY;KACnC,CAAC,CAAC;IAEH,SAAS,cAAc,CAAC,OAAgB;QACtC,MAAM,MAAM,GAAG,mBAAmB,CAAC,QAAQ,EAAE,OAAO,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;QACtE,MAAM,aAAa,GAAG,SAAS,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC;QAClD,IAAI,aAAa,IAAI,EAAE;YAAE,MAAM,IAAI,KAAK,CAAC,mCAAmC,CAAC,CAAC;QAC9E,MAAM,QAAQ,GAAG,OAAO,CAAC,QAAQ,KAAK,SAAS;YAC7C,CAAC,CAAC,SAAS,CAAC,UAAU,EAAE,OAAO,CAAC,WAAW,IAAI,OAAO,CAAC,GAAG,CAAC;YAC3D,CAAC,CAAC,mBAAmB,CAAC,UAAU,EAAE,OAAO,CAAC,QAAQ,EAAE,OAAO,CAAC,CAAC;QAC/D,OAAO,MAAM,CAAC,MAAM,CAAC;YACnB,MAAM,EAAE,oBAAoB;YAC5B,OAAO;YACP,QAAQ;YACR,QAAQ;YACR,KAAK;YACL,MAAM;YACN,aAAa;YACb,UAAU;YACV,QAAQ;SACT,CAAC,CAAC;IACL,CAAC;IAED,SAAS,YAAY,CACnB,OAAgB,EAChB,WAA+B,EAC/B,WAAmB,EACnB,QAAgB;QAEhB,MAAM,OAAO,GAAG,MAAM,CAAC,IAAI,CAAC,WAAW,CAAC,EAAE,CAAC,CAAC,CAAC;QAC7C,IAAI,OAAO,CAAC,MAAM,KAAK,EAAE;YAAE,MAAM,IAAI,KAAK,CAAC,qDAAqD,CAAC,CAAC;QAClG,MAAM,QAAQ,GAAoC;YAChD,YAAY,EAAE,CAAC;YACf,WAAW,EAAE,OAAO,CAAC,QAAQ,CAAC,WAAW,CAAC;YAC1C,QAAQ;YACR,MAAM,EAAE,oBAAoB;YAC5B,MAAM,EAAE,OAAO,CAAC,MAAM,CAAC,WAAW,EAAE;YACpC,QAAQ,EAAE,WAAW,CAAC,QAAQ;YAC9B,UAAU,EAAE,IAAI;YAChB,OAAO;YACP,SAAS;YACT,UAAU;YACV,QAAQ;YACR,KAAK;YACL,aAAa,EAAE,WAAW,CAAC,aAAa,CAAC,QAAQ,EAAE;YACnD,QAAQ;YACR,QAAQ,EAAE,WAAW;YACrB,SAAS,EAAE,WAAW,GAAG,mBAAmB;SAC7C,CAAC;QACF,MAAM,SAAS,GAAG,qBAAqB,CAAC,QAAQ,EAAE,eAAe,CAAC,CAAC;QACnE,OAAO;YACL,WAAW,EAAE,CAAC;YACd,OAAO,EAAE,CAAC;oBACR,MAAM,EAAE,oBAAoB;oBAC5B,OAAO;oBACP,iBAAiB,EAAE,WAAW,CAAC,MAAM;oBACrC,KAAK;oBACL,KAAK,EAAE,QAAQ;oBACf,QAAQ,EAAE,WAAW,CAAC,QAAQ;oBAC9B,KAAK,EAAE,EAAE,QAAQ,EAAE,UAAU,EAAE,iBAAiB,EAAE,CAAC,EAAE,SAAS,EAAE;iBACjE,CAAC;SACH,CAAC;IACJ,CAAC;IAED,MAAM,MAAM,GAAG,KAAK,EAAE,OAAgB,EAAE,QAAkB,EAAE,IAAkB,EAAiB,EAAE;QAC/F,MAAM,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,WAAW,EAAE,CAAC;QAC5C,IAAI,MAAM,KAAK,KAAK,EAAE,CAAC;YACrB,QAAQ,CAAC,GAAG,CAAC,OAAO,EAAE,KAAK,CAAC,CAAC;YAC7B,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,+CAA+C,EAAE,CAAC,CAAC;YAChF,OAAO;QACT,CAAC;QAED,IAAI,WAA+B,CAAC;QACpC,IAAI,QAAgB,CAAC;QACrB,IAAI,WAAmB,CAAC;QACxB,IAAI,CAAC;YACH,WAAW,GAAG,cAAc,CAAC,OAAO,CAAC,CAAC;YACtC,QAAQ,GAAG,sBAAsB,CAC/B,mBAAmB,CAAC,UAAU,EAAE,OAAO,CAAC,QAAQ,EAAE,OAAO,CAAC,EAC1D,UAAU,CACX,CAAC;YACF,WAAW,GAAG,UAAU,CAAC,GAAG,CAAC,CAAC;QAChC,CAAC;QAAC,MAAM,CAAC;YACP,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,gDAAgD,EAAE,CAAC,CAAC;YACjF,OAAO;QACT,CAAC;QAED,IAAI,UAA8B,CAAC;QACnC,IAAI,CAAC;YACH,UAAU,GAAG,YAAY,CAAC,OAAO,EAAE,iCAAiC,EAAE,GAAG,CAAC,CAAC;QAC7E,CAAC;QAAC,MAAM,CAAC;YACP,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE;gBAClB,KAAK,EAAE,yDAAyD;gBAChE,kBAAkB,EAAE,wBAAwB;aAC7C,CAAC,CAAC;YACH,OAAO;QACT,CAAC;QACD,IAAI,UAAU,KAAK,wBAAwB,EAAE,CAAC;YAC5C,QAAQ,CAAC,GAAG,CAAC,SAAS,EAAE,wBAAwB,CAAC,CAAC;YAClD,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE;gBAClB,KAAK,EAAE,kDAAkD;gBACzD,kBAAkB,EAAE,wBAAwB;aAC7C,CAAC,CAAC;YACH,OAAO;QACT,CAAC;QAED,IAAI,aAAiC,CAAC;QACtC,IAAI,CAAC;YACH,aAAa,GAAG,YAAY,CAAC,OAAO,EAAE,WAAW,EAAE,WAAW,EAAE,QAAQ,CAAC,CAAC;QAC5E,CAAC;QAAC,MAAM,CAAC;YACP,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,4CAA4C,EAAE,CAAC,CAAC;YAC7E,OAAO;QACT,CAAC;QAED,IAAI,MAA0B,CAAC;QAC/B,IAAI,CAAC;YACH,MAAM,GAAG,sBAAsB,CAAC,OAAO,EAAE,cAAc,CAAC,CAAC;QAC3D,CAAC;QAAC,MAAM,CAAC;YACP,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,2BAA2B,EAAE,GAAG,aAAa,EAAE,CAAC,CAAC;YAC9E,OAAO;QACT,CAAC;QACD,IAAI,CAAC,MAAM,EAAE,CAAC;YACZ,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,aAAa,CAAC,CAAC;YACnC,OAAO;QACT,CAAC;QAED,IAAI,KAAK,CAAC;QACV,IAAI,CAAC;YACH,KAAK,GAAG,kBAAkB,CAAC,MAAM,CAAC,CAAC;QACrC,CAAC;QAAC,MAAM,CAAC;YACP,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,2BAA2B,EAAE,GAAG,aAAa,EAAE,CAAC,CAAC;YAC9E,OAAO;QACT,CAAC;QACD,IAAI,CAAC,mBAAmB,CAAC,KAAK,CAAC,EAAE,CAAC;YAChC,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,8BAA8B,EAAE,GAAG,aAAa,EAAE,CAAC,CAAC;YACjF,OAAO;QACT,CAAC;QACD,MAAM,SAAS,GAAG,KAAK,CAAC,SAAS,CAAC;QAClC,MAAM,cAAc,GAClB,SAAS,CAAC,YAAY,KAAK,CAAC;eACzB,SAAS,CAAC,QAAQ,KAAK,QAAQ;eAC/B,SAAS,CAAC,MAAM,KAAK,oBAAoB;eACzC,SAAS,CAAC,MAAM,KAAK,MAAM;eAC3B,SAAS,CAAC,QAAQ,KAAK,WAAW,CAAC,QAAQ;eAC3C,SAAS,CAAC,UAAU,KAAK,IAAI;eAC7B,SAAS,CAAC,OAAO,KAAK,OAAO;eAC7B,SAAS,CAAC,SAAS,KAAK,SAAS;eACjC,SAAS,CAAC,UAAU,KAAK,UAAU;eACnC,SAAS,CAAC,QAAQ,KAAK,QAAQ;eAC/B,SAAS,CAAC,KAAK,KAAK,KAAK;eACzB,SAAS,CAAC,aAAa,KAAK,WAAW,CAAC,aAAa,CAAC,QAAQ,EAAE;eAChE,SAAS,CAAC,QAAQ,KAAK,QAAQ;eAC/B,SAAS,CAAC,SAAS,GAAG,SAAS,CAAC,QAAQ,KAAK,mBAAmB;eAChE,SAAS,CAAC,aAAa,CAAC,SAAS,KAAK,aAAa;eACnD,mBAAmB,CAAC,SAAS,EAAE,eAAe,CAAC;eAC/C,KAAK,CAAC,MAAM,KAAK,oBAAoB;eACrC,KAAK,CAAC,OAAO,KAAK,OAAO,CAAC;QAC/B,IAAI,CAAC,cAAc,EAAE,CAAC;YACpB,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,kDAAkD,EAAE,GAAG,aAAa,EAAE,CAAC,CAAC;YACrG,OAAO;QACT,CAAC;QAED,MAAM,WAAW,GAAG,UAAU,CAAC,QAAQ,CAAC;aACrC,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,EAAE,MAAM,CAAC;aACrC,MAAM,CAAC,KAAK,CAAC,CAAC;QACjB,MAAM,aAAa,GAAG,mBAAmB,CACvC,aAAa,CAAC,iBAAiB,EAC/B,UAAU,EACV,KAAK,CAAC,MAAM,CACb,CAAC;QACF,MAAM,mBAAmB,GAAG,CAAC,OAAkC,EAAW,EAAE,CAC1E,OAAO,CAAC,MAAM,KAAK,KAAK,CAAC,MAAM;eAC5B,OAAO,CAAC,SAAS,KAAK,KAAK,CAAC,SAAS;eACrC,OAAO,CAAC,aAAa,KAAK,WAAW,CAAC,aAAa;eACnD,OAAO,CAAC,QAAQ,KAAK,QAAQ;eAC7B,OAAO,CAAC,KAAK,KAAK,KAAK;eACvB,OAAO,CAAC,UAAU,KAAK,UAAU;eACjC,OAAO,CAAC,MAAM,KAAK,oBAAoB;eACvC,OAAO,CAAC,OAAO,KAAK,OAAO;eAC3B,gCAAgC,CAAC,KAAK,EAAE,OAAO,CAAC,KAAK,CAAC,CAAC;QAE5D,IAAI,QAA+B,CAAC;QACpC,IAAI,CAAC;YACH,QAAQ,GAAG,MAAM,OAAO,CAAC,eAAe,CAAC,MAAM,CAAC,aAAa,EAAE,WAAW,CAAC,CAAC;YAC5E,IAAI,CAAC,QAAQ,IAAI,CAAC,CAAC,SAAS,EAAE,WAAW,EAAE,WAAW,EAAE,UAAU,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE,CAAC;gBAC5F,MAAM,IAAI,KAAK,CAAC,wDAAwD,CAAC,CAAC;YAC5E,CAAC;QACH,CAAC;QAAC,MAAM,CAAC;YACP,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE;gBAClB,KAAK,EAAE,oEAAoE;gBAC3E,SAAS,EAAE,IAAI;aAChB,EAAE,GAAG,CAAC,CAAC;YACR,OAAO;QACT,CAAC;QACD,IAAI,QAAQ,CAAC,IAAI,KAAK,UAAU,EAAE,CAAC;YACjC,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,iEAAiE,EAAE,CAAC,CAAC;YAClG,OAAO;QACT,CAAC;QACD,IAAI,QAAQ,CAAC,IAAI,KAAK,WAAW,EAAE,CAAC;YAClC,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE;gBAClB,KAAK,EAAE,yDAAyD;gBAChE,SAAS,EAAE,IAAI;aAChB,EAAE,GAAG,CAAC,CAAC;YACR,OAAO;QACT,CAAC;QACD,IAAI,QAAQ,CAAC,IAAI,KAAK,WAAW,EAAE,CAAC;YAClC,IACE,QAAQ,CAAC,MAAM,CAAC,GAAG,KAAK,aAAa;mBAClC,QAAQ,CAAC,MAAM,CAAC,WAAW,KAAK,WAAW;mBAC3C,CAAC,mBAAmB,CAAC,QAAQ,CAAC,MAAM,CAAC,OAAO,CAAC,EAChD,CAAC;gBACD,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,gDAAgD,EAAE,EAAE,GAAG,CAAC,CAAC;gBACtF,OAAO;YACT,CAAC;YACD,QAAQ,CAAC,MAAM,CAAC,wBAAwB,CAAC,GAAG,QAAQ,CAAC,MAAM,CAAC,OAAO,CAAC;YACpE,QAAQ,CAAC,MAAM,CAAC,+BAA+B,CAAC,GAAG,MAAM,CAAC,MAAM,CAAC;gBAC/D,IAAI,EAAE,WAAoB;gBAC1B,MAAM,EAAE,QAAQ,CAAC,MAAM;aACxB,CAAC,CAAC;YACH,yBAAyB,CAAC,QAAQ,CAAC,CAAC;YACpC,IAAI,EAAE,CAAC;YACP,OAAO;QACT,CAAC;QAED,IAAI,SAAS,CAAC,QAAQ,GAAG,WAAW,GAAG,EAAE,IAAI,SAAS,CAAC,SAAS,IAAI,WAAW,EAAE,CAAC;YAChF,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,+CAA+C,EAAE,GAAG,aAAa,EAAE,CAAC,CAAC;YAClG,OAAO;QACT,CAAC;QAED,IAAI,OAAO,CAAC;QACZ,IAAI,CAAC;YACH,OAAO,GAAG,MAAM,QAAQ,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,EAAE,WAAW,CAAC,CAAC;QAC7D,CAAC;QAAC,MAAM,CAAC;YACP,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE;gBAClB,KAAK,EAAE,4EAA4E;gBACnF,SAAS,EAAE,IAAI;aAChB,EAAE,GAAG,CAAC,CAAC;YACR,OAAO;QACT,CAAC;QACD,IAAI,CAAC,OAAO,CAAC,EAAE,EAAE,CAAC;YAChB,IAAI,OAAO,CAAC,IAAI,KAAK,aAAa,EAAE,CAAC;gBACnC,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE;oBAClB,KAAK,EAAE,qCAAqC,OAAO,CAAC,MAAM,EAAE;oBAC5D,SAAS,EAAE,IAAI;iBAChB,EAAE,GAAG,CAAC,CAAC;YACV,CAAC;iBAAM,CAAC;gBACN,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,kCAAkC,OAAO,CAAC,MAAM,EAAE,EAAE,GAAG,aAAa,EAAE,CAAC,CAAC;YACvG,CAAC;YACD,OAAO;QACT,CAAC;QACD,MAAM,OAAO,GAAG,OAAO,CAAC,OAAO,CAAC;QAChC,IAAI,CAAC,mBAAmB,CAAC,OAAO,CAAC,EAAE,CAAC;YAClC,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,6DAA6D,EAAE,GAAG,aAAa,EAAE,CAAC,CAAC;YAChH,OAAO;QACT,CAAC;QAED,MAAM,MAAM,GAAoC,MAAM,CAAC,MAAM,CAAC;YAC5D,GAAG,EAAE,aAAa;YAClB,WAAW;YACX,OAAO,EAAE,MAAM,CAAC,MAAM,CAAC,EAAE,GAAG,OAAO,EAAE,CAAC;SACvC,CAAC,CAAC;QACH,IAAI,OAA6B,CAAC;QAClC,IAAI,CAAC;YACH,OAAO,GAAG,MAAM,OAAO,CAAC,eAAe,CAAC,KAAK,CAC3C,MAAM,EACN,UAAU,EAAE,EACZ,WAAW,CACZ,CAAC;YACF,IACE,CAAC,OAAO;mBACL,CAAC,CAAC,SAAS,EAAE,WAAW,EAAE,WAAW,EAAE,UAAU,CAAC,CAAC,QAAQ,CAAC,OAAO,CAAC,IAAI,CAAC,EAC5E,CAAC;gBACD,MAAM,IAAI,KAAK,CAAC,uDAAuD,CAAC,CAAC;YAC3E,CAAC;QACH,CAAC;QAAC,MAAM,CAAC;YACP,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE;gBAClB,KAAK,EAAE,oEAAoE;gBAC3E,SAAS,EAAE,IAAI;aAChB,EAAE,GAAG,CAAC,CAAC;YACR,OAAO;QACT,CAAC;QACD,IAAI,OAAO,CAAC,IAAI,KAAK,UAAU,EAAE,CAAC;YAChC,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,iEAAiE,EAAE,CAAC,CAAC;YAClG,OAAO;QACT,CAAC;QACD,IAAI,OAAO,CAAC,IAAI,KAAK,WAAW,EAAE,CAAC;YACjC,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE;gBAClB,KAAK,EAAE,yDAAyD;gBAChE,SAAS,EAAE,IAAI;aAChB,EAAE,GAAG,CAAC,CAAC;YACR,OAAO;QACT,CAAC;QACD,IACE,OAAO,CAAC,MAAM,CAAC,GAAG,KAAK,aAAa;eACjC,OAAO,CAAC,MAAM,CAAC,WAAW,KAAK,WAAW;eAC1C,CAAC,mBAAmB,CAAC,OAAO,CAAC,MAAM,CAAC,OAAO,CAAC,EAC/C,CAAC;YACD,IAAI,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,kDAAkD,EAAE,EAAE,GAAG,CAAC,CAAC;YACxF,OAAO;QACT,CAAC;QAED,QAAQ,CAAC,MAAM,CAAC,wBAAwB,CAAC,GAAG,OAAO,CAAC,MAAM,CAAC,OAAO,CAAC;QACnE,QAAQ,CAAC,MAAM,CAAC,+BAA+B,CAAC,GAAG,MAAM,CAAC,MAAM,CAAC;YAC/D,IAAI,EAAE,OAAO,CAAC,IAAI;YAClB,MAAM,EAAE,OAAO,CAAC,MAAM;SACvB,CAAC,CAAC;QACH,yBAAyB,CAAC,QAAQ,CAAC,CAAC;QACpC,IAAI,EAAE,CAAC;IACT,CAAC,CAAC;IAEF,OAAO,CAAC,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAQ,EAAE;QACvC,KAAK,MAAM,CAAC,OAAO,EAAE,QAAQ,EAAE,IAAI,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;IACnD,CAAC,CAAC;AACJ,CAAC"}
package/dist/index.d.ts CHANGED
@@ -2,4 +2,7 @@ export * from "./types.js";
2
2
  export * from "./proof-store.js";
3
3
  export * from "./verification.js";
4
4
  export * from "./middleware.js";
5
+ export type { BoundReappPaymentMiddlewareOptions, BoundX402Challenge, } from "./bound.js";
6
+ export * from "./bound-route.js";
7
+ export * from "./bound-store.js";
5
8
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,YAAY,CAAC;AAC3B,cAAc,kBAAkB,CAAC;AACjC,cAAc,mBAAmB,CAAC;AAClC,cAAc,iBAAiB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,YAAY,CAAC;AAC3B,cAAc,kBAAkB,CAAC;AACjC,cAAc,mBAAmB,CAAC;AAClC,cAAc,iBAAiB,CAAC;AAChC,YAAY,EACV,kCAAkC,EAClC,kBAAkB,GACnB,MAAM,YAAY,CAAC;AACpB,cAAc,kBAAkB,CAAC;AACjC,cAAc,kBAAkB,CAAC"}
package/dist/index.js CHANGED
@@ -2,4 +2,6 @@ export * from "./types.js";
2
2
  export * from "./proof-store.js";
3
3
  export * from "./verification.js";
4
4
  export * from "./middleware.js";
5
+ export * from "./bound-route.js";
6
+ export * from "./bound-store.js";
5
7
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,YAAY,CAAC;AAC3B,cAAc,kBAAkB,CAAC;AACjC,cAAc,mBAAmB,CAAC;AAClC,cAAc,iBAAiB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,YAAY,CAAC;AAC3B,cAAc,kBAAkB,CAAC;AACjC,cAAc,mBAAmB,CAAC;AAClC,cAAc,iBAAiB,CAAC;AAKhC,cAAc,kBAAkB,CAAC;AACjC,cAAc,kBAAkB,CAAC"}