@azeth/provider 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.
- package/LICENSE +21 -0
- package/README.md +70 -0
- package/dist/agreement-cache.d.ts +20 -0
- package/dist/agreement-cache.d.ts.map +1 -0
- package/dist/agreement-cache.js +133 -0
- package/dist/agreement-cache.js.map +1 -0
- package/dist/agreement-keeper.d.ts +43 -0
- package/dist/agreement-keeper.d.ts.map +1 -0
- package/dist/agreement-keeper.js +102 -0
- package/dist/agreement-keeper.js.map +1 -0
- package/dist/examples/index.d.ts +4 -0
- package/dist/examples/index.d.ts.map +1 -0
- package/dist/examples/index.js +3 -0
- package/dist/examples/index.js.map +1 -0
- package/dist/examples/price-feed.d.ts +22 -0
- package/dist/examples/price-feed.d.ts.map +1 -0
- package/dist/examples/price-feed.js +148 -0
- package/dist/examples/price-feed.js.map +1 -0
- package/dist/examples/pricing-routes.d.ts +15 -0
- package/dist/examples/pricing-routes.d.ts.map +1 -0
- package/dist/examples/pricing-routes.js +77 -0
- package/dist/examples/pricing-routes.js.map +1 -0
- package/dist/extensions/payment-agreement.d.ts +37 -0
- package/dist/extensions/payment-agreement.d.ts.map +1 -0
- package/dist/extensions/payment-agreement.js +39 -0
- package/dist/extensions/payment-agreement.js.map +1 -0
- package/dist/index.d.ts +12 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +15 -0
- package/dist/index.js.map +1 -0
- package/dist/middleware/pre-settled.d.ts +29 -0
- package/dist/middleware/pre-settled.d.ts.map +1 -0
- package/dist/middleware/pre-settled.js +80 -0
- package/dist/middleware/pre-settled.js.map +1 -0
- package/dist/stack.d.ts +75 -0
- package/dist/stack.d.ts.map +1 -0
- package/dist/stack.js +169 -0
- package/dist/stack.js.map +1 -0
- package/dist/storage.d.ts +48 -0
- package/dist/storage.d.ts.map +1 -0
- package/dist/storage.js +96 -0
- package/dist/storage.js.map +1 -0
- package/package.json +66 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"storage.d.ts","sourceRoot":"","sources":["../src/storage.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,KAAK,EAAE,SAAS,EAAE,MAAM,MAAM,CAAC;AAC3D,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,iCAAiC,CAAC;AAEnE,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAE7D,qDAAqD;AACrD,MAAM,WAAW,sBAAsB;IACrC,4CAA4C;IAC5C,YAAY,EAAE,YAAY,CAAC,SAAS,EAAE,KAAK,CAAC,CAAC;IAC7C,8CAA8C;IAC9C,YAAY,EAAE,KAAK,MAAM,EAAE,CAAC;IAC5B,qDAAqD;IACrD,YAAY,CAAC,EAAE,KAAK,MAAM,EAAE,CAAC;IAC7B,8CAA8C;IAC9C,aAAa,CAAC,EAAE,KAAK,MAAM,EAAE,CAAC;IAC9B,4CAA4C;IAC5C,kBAAkB,CAAC,EAAE,MAAM,CAAC;CAC7B;AAeD,qBAAa,gBAAiB,YAAW,WAAW;IAClD,OAAO,CAAC,QAAQ,CAAC,cAAc,CAAkC;IACjE,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAqB;IAChD,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAyB;IAChD,OAAO,CAAC,MAAM,CAAgC;gBAElC,MAAM,EAAE,sBAAsB;IAI1C;uEACmE;IACnE,SAAS,CAAC,MAAM,EAAE,eAAe,GAAG,IAAI;IAIxC;;;;;;;;;;;OAWG;IACG,OAAO,CAAC,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAkClE,qDAAqD;IACrD,aAAa,CAAC,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,IAAI;IAItD,yDAAyD;IACzD,YAAY,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO;IAIpC,6BAA6B;IAC7B,WAAW,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAUhC,wCAAwC;IACxC,OAAO,CAAC,iBAAiB;CAa1B"}
|
package/dist/storage.js
ADDED
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
import { findActiveAgreementForPayee } from './agreement-cache.js';
|
|
2
|
+
/** Agreement-aware SIWx storage.
|
|
3
|
+
*
|
|
4
|
+
* Implements the @x402/extensions SIWxStorage interface with two-tier lookup:
|
|
5
|
+
* 1. In-memory payment records (from x402 settlement — previously paid)
|
|
6
|
+
* 2. On-chain payment agreements (subscription — no per-request payment needed)
|
|
7
|
+
*
|
|
8
|
+
* This is the key integration point between x402 SIWx sessions and Azeth
|
|
9
|
+
* payment agreements. Both use SIWx for wallet identity — the difference
|
|
10
|
+
* is what hasPaid() checks.
|
|
11
|
+
*/
|
|
12
|
+
/** Max entries per resource in paymentRecords to prevent unbounded growth */
|
|
13
|
+
const MAX_PAYMENT_RECORDS_PER_RESOURCE = 100_000;
|
|
14
|
+
export class AzethSIWxStorage {
|
|
15
|
+
paymentRecords = new Map();
|
|
16
|
+
usedNonces = new Set();
|
|
17
|
+
config;
|
|
18
|
+
keeper = null;
|
|
19
|
+
constructor(config) {
|
|
20
|
+
this.config = config;
|
|
21
|
+
}
|
|
22
|
+
/** Inject the agreement keeper after construction.
|
|
23
|
+
* Called from server startup to avoid circular initialization. */
|
|
24
|
+
setKeeper(keeper) {
|
|
25
|
+
this.keeper = keeper;
|
|
26
|
+
}
|
|
27
|
+
/** Check if an address has paid for a resource.
|
|
28
|
+
*
|
|
29
|
+
* Two-tier lookup:
|
|
30
|
+
* 1. Check in-memory payment records (x402 settlement — permanent grant)
|
|
31
|
+
* 2. Check on-chain agreements (subscription — re-verified every ~60s via cache TTL)
|
|
32
|
+
*
|
|
33
|
+
* Settlement grants (recordPayment) are permanent for the session.
|
|
34
|
+
* Agreement grants are NOT cached permanently — they are re-verified on each
|
|
35
|
+
* call via findActiveAgreementForPayee (which uses a 60s TTL cache internally).
|
|
36
|
+
* This ensures that if a payer's balance drops to zero, their access is revoked
|
|
37
|
+
* within ~60s instead of being permanently granted.
|
|
38
|
+
*/
|
|
39
|
+
async hasPaid(resource, address) {
|
|
40
|
+
const normalized = address.toLowerCase();
|
|
41
|
+
// 1. Check in-memory payment records (fast path — settlement grants are permanent)
|
|
42
|
+
const set = this.paymentRecords.get(resource);
|
|
43
|
+
if (set?.has(normalized))
|
|
44
|
+
return true;
|
|
45
|
+
// 2. Check on-chain agreements (re-verified via agreementCache with 60s TTL)
|
|
46
|
+
if (this.config.moduleAddress) {
|
|
47
|
+
try {
|
|
48
|
+
const agreement = await findActiveAgreementForPayee(this.config.publicClient, this.config.moduleAddress, address, this.config.servicePayee, this.config.serviceToken, this.config.minAgreementAmount);
|
|
49
|
+
if (agreement) {
|
|
50
|
+
// Notify keeper to track this agreement for periodic execution
|
|
51
|
+
this.keeper?.trackAgreement(address, agreement.id);
|
|
52
|
+
return true;
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
catch {
|
|
56
|
+
// Agreement check failure is non-fatal — fall through to 402
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
return false;
|
|
60
|
+
}
|
|
61
|
+
/** Record that an address has paid for a resource */
|
|
62
|
+
recordPayment(resource, address) {
|
|
63
|
+
this.recordPaymentSync(resource, address.toLowerCase());
|
|
64
|
+
}
|
|
65
|
+
/** Check if a nonce has been used (replay prevention) */
|
|
66
|
+
hasUsedNonce(nonce) {
|
|
67
|
+
return this.usedNonces.has(nonce);
|
|
68
|
+
}
|
|
69
|
+
/** Record a nonce as used */
|
|
70
|
+
recordNonce(nonce) {
|
|
71
|
+
this.usedNonces.add(nonce);
|
|
72
|
+
// Limit nonce set size to prevent unbounded growth
|
|
73
|
+
if (this.usedNonces.size > 50_000) {
|
|
74
|
+
const iterator = this.usedNonces.values();
|
|
75
|
+
const oldest = iterator.next().value;
|
|
76
|
+
if (oldest !== undefined)
|
|
77
|
+
this.usedNonces.delete(oldest);
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
/** Synchronous payment record helper */
|
|
81
|
+
recordPaymentSync(resource, normalized) {
|
|
82
|
+
let set = this.paymentRecords.get(resource);
|
|
83
|
+
if (!set) {
|
|
84
|
+
set = new Set();
|
|
85
|
+
this.paymentRecords.set(resource, set);
|
|
86
|
+
}
|
|
87
|
+
set.add(normalized);
|
|
88
|
+
// Evict oldest entry when cap reached to prevent unbounded memory growth
|
|
89
|
+
if (set.size > MAX_PAYMENT_RECORDS_PER_RESOURCE) {
|
|
90
|
+
const oldest = set.values().next().value;
|
|
91
|
+
if (oldest !== undefined)
|
|
92
|
+
set.delete(oldest);
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
//# sourceMappingURL=storage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"storage.js","sourceRoot":"","sources":["../src/storage.ts"],"names":[],"mappings":"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"}
|
package/package.json
ADDED
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@azeth/provider",
|
|
3
|
+
"version": "0.2.0",
|
|
4
|
+
"type": "module",
|
|
5
|
+
"description": "x402 service provider tooling for Azeth — gate Hono endpoints behind x402 payments with payment-agreement support",
|
|
6
|
+
"license": "MIT",
|
|
7
|
+
"repository": {
|
|
8
|
+
"type": "git",
|
|
9
|
+
"url": "https://github.com/azeth-protocol/provider.git"
|
|
10
|
+
},
|
|
11
|
+
"homepage": "https://azeth.ai",
|
|
12
|
+
"keywords": [
|
|
13
|
+
"azeth",
|
|
14
|
+
"x402",
|
|
15
|
+
"provider",
|
|
16
|
+
"hono",
|
|
17
|
+
"payments",
|
|
18
|
+
"machine-economy",
|
|
19
|
+
"middleware"
|
|
20
|
+
],
|
|
21
|
+
"main": "dist/index.js",
|
|
22
|
+
"types": "dist/index.d.ts",
|
|
23
|
+
"exports": {
|
|
24
|
+
".": {
|
|
25
|
+
"types": "./dist/index.d.ts",
|
|
26
|
+
"import": "./dist/index.js"
|
|
27
|
+
},
|
|
28
|
+
"./examples": {
|
|
29
|
+
"types": "./dist/examples/index.d.ts",
|
|
30
|
+
"import": "./dist/examples/index.js"
|
|
31
|
+
}
|
|
32
|
+
},
|
|
33
|
+
"files": [
|
|
34
|
+
"dist/",
|
|
35
|
+
"README.md",
|
|
36
|
+
"LICENSE"
|
|
37
|
+
],
|
|
38
|
+
"dependencies": {
|
|
39
|
+
"@azeth/common": "^0.2.0",
|
|
40
|
+
"@x402/core": "^2.4.0",
|
|
41
|
+
"@x402/evm": "^2.4.0",
|
|
42
|
+
"@x402/extensions": "^2.4.0",
|
|
43
|
+
"@x402/hono": "^2.4.0",
|
|
44
|
+
"hono": "^4.7.0",
|
|
45
|
+
"viem": "^2.21.0"
|
|
46
|
+
},
|
|
47
|
+
"devDependencies": {
|
|
48
|
+
"@types/node": "^22.0.0",
|
|
49
|
+
"typescript": "^5.7.0",
|
|
50
|
+
"vitest": "^3.0.0",
|
|
51
|
+
"@changesets/cli": "^2.27.0"
|
|
52
|
+
},
|
|
53
|
+
"publishConfig": {
|
|
54
|
+
"access": "public"
|
|
55
|
+
},
|
|
56
|
+
"engines": {
|
|
57
|
+
"node": ">=20.0.0"
|
|
58
|
+
},
|
|
59
|
+
"scripts": {
|
|
60
|
+
"build": "tsc --project tsconfig.json",
|
|
61
|
+
"dev": "tsc -b --watch",
|
|
62
|
+
"test": "vitest run",
|
|
63
|
+
"typecheck": "tsc --noEmit",
|
|
64
|
+
"release": "pnpm build && changeset publish"
|
|
65
|
+
}
|
|
66
|
+
}
|