@apicity/cost 0.2.0-alpha.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.
- package/README.md +255 -0
- package/dist/src/cost.d.ts +1 -1
- package/dist/src/cost.d.ts.map +1 -1
- package/dist/src/cost.js +1 -1
- package/dist/src/cost.js.map +1 -1
- package/dist/src/index.d.ts +7 -1
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +4 -1
- package/dist/src/index.js.map +1 -1
- package/dist/src/paid-endpoints.d.ts +46 -0
- package/dist/src/paid-endpoints.d.ts.map +1 -0
- package/dist/src/paid-endpoints.js +53 -0
- package/dist/src/paid-endpoints.js.map +1 -0
- package/dist/src/paygate-cli.d.ts +3 -0
- package/dist/src/paygate-cli.d.ts.map +1 -0
- package/dist/src/paygate-cli.js +97 -0
- package/dist/src/paygate-cli.js.map +1 -0
- package/dist/src/paygate.d.ts +160 -0
- package/dist/src/paygate.d.ts.map +1 -0
- package/dist/src/paygate.js +336 -0
- package/dist/src/paygate.js.map +1 -0
- package/dist/src/pricing/kie.d.ts.map +1 -1
- package/dist/src/pricing/kie.js +22 -8
- package/dist/src/pricing/kie.js.map +1 -1
- package/dist/src/with-paid-gate.d.ts +27 -0
- package/dist/src/with-paid-gate.d.ts.map +1 -0
- package/dist/src/with-paid-gate.js +91 -0
- package/dist/src/with-paid-gate.js.map +1 -0
- package/package.json +4 -1
|
@@ -0,0 +1,160 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* OTP payload schema. An OTP commits to an exact
|
|
3
|
+
* `(provider, method, dotPath, requestHash)` tuple with an expiry, and is
|
|
4
|
+
* single-use via its `jti`.
|
|
5
|
+
*/
|
|
6
|
+
export interface PayGateOtpPayload {
|
|
7
|
+
v: 1;
|
|
8
|
+
jti: string;
|
|
9
|
+
provider: string;
|
|
10
|
+
method: string;
|
|
11
|
+
dotPath: string;
|
|
12
|
+
requestHash: `sha256:${string}`;
|
|
13
|
+
iat: number;
|
|
14
|
+
exp: number;
|
|
15
|
+
}
|
|
16
|
+
/**
|
|
17
|
+
* Caller-supplied approval object.
|
|
18
|
+
*/
|
|
19
|
+
export interface PayGateApproval {
|
|
20
|
+
otp: string;
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* Single-use replay ledger. The default is an in-process Set scoped to one
|
|
24
|
+
* provider instance (see `createReplayStore`). Pass a custom store for
|
|
25
|
+
* cross-process or persistent replay protection.
|
|
26
|
+
*/
|
|
27
|
+
export interface ReplayStore {
|
|
28
|
+
has(jti: string): boolean;
|
|
29
|
+
add(jti: string): void;
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Pay-gate configuration supplied by the code client at construction time
|
|
33
|
+
* (never by the autonomous caller). Holds the shared HMAC secret used to mint
|
|
34
|
+
* and verify OTPs. No environment variables, no key files.
|
|
35
|
+
*/
|
|
36
|
+
export interface PayGateConfig {
|
|
37
|
+
/** Shared HMAC secret. The code client holds it; the AI never sees it. */
|
|
38
|
+
secret: string;
|
|
39
|
+
/** Replay ledger. Defaults to an in-process Set, per provider instance. */
|
|
40
|
+
replayStore?: ReplayStore;
|
|
41
|
+
/** Clock injection for testing. Defaults to `Date.now`. */
|
|
42
|
+
now?: () => number;
|
|
43
|
+
}
|
|
44
|
+
/**
|
|
45
|
+
* Error thrown when the pay gate blocks a request.
|
|
46
|
+
*/
|
|
47
|
+
export declare class PayGateError extends Error {
|
|
48
|
+
readonly provider: string;
|
|
49
|
+
readonly method: string;
|
|
50
|
+
readonly dotPath: string;
|
|
51
|
+
readonly code: "paygate-not-configured" | "otp-missing" | "otp-malformed" | "otp-invalid-signature" | "otp-expired" | "otp-mismatched-request" | "otp-replayed";
|
|
52
|
+
constructor(provider: string, method: string, dotPath: string, code: PayGateError["code"], message: string);
|
|
53
|
+
}
|
|
54
|
+
/**
|
|
55
|
+
* Verification-only error codes — the subset of PayGateError codes that the
|
|
56
|
+
* pure `verifyOtp` can emit. The shell layer ("paygate-not-configured",
|
|
57
|
+
* "otp-missing") is handled separately in `dispatchWithPaidGate`.
|
|
58
|
+
*/
|
|
59
|
+
export type VerifyFailureCode = "otp-malformed" | "otp-invalid-signature" | "otp-expired" | "otp-mismatched-request" | "otp-replayed";
|
|
60
|
+
/**
|
|
61
|
+
* Tagged-union result from the pure `verifyOtp` function.
|
|
62
|
+
*/
|
|
63
|
+
export type VerifyResult = {
|
|
64
|
+
ok: true;
|
|
65
|
+
jti: string;
|
|
66
|
+
} | {
|
|
67
|
+
ok: false;
|
|
68
|
+
code: VerifyFailureCode;
|
|
69
|
+
message: string;
|
|
70
|
+
};
|
|
71
|
+
/**
|
|
72
|
+
* Pure inputs to `verifyOtp`. Every dependency is explicit — no env vars,
|
|
73
|
+
* no `Date.now()`, no filesystem reads.
|
|
74
|
+
*/
|
|
75
|
+
export interface VerifyOtpInput {
|
|
76
|
+
nowSeconds: number;
|
|
77
|
+
secret: string;
|
|
78
|
+
expected: {
|
|
79
|
+
provider: string;
|
|
80
|
+
method: string;
|
|
81
|
+
dotPath: string;
|
|
82
|
+
};
|
|
83
|
+
payloadHash: `sha256:${string}`;
|
|
84
|
+
otp: string;
|
|
85
|
+
isJtiConsumed: (jti: string) => boolean;
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Canonicalize a JSON value by sorting object keys recursively.
|
|
89
|
+
* Arrays preserve order. Non-JSON values (undefined, functions, symbols,
|
|
90
|
+
* circular references) cause a TypeError so the caller can fail closed.
|
|
91
|
+
*/
|
|
92
|
+
export declare function canonicalizeJson(value: unknown): string;
|
|
93
|
+
/**
|
|
94
|
+
* Compute SHA-256 of canonical JSON, prefixed with `sha256:`.
|
|
95
|
+
*/
|
|
96
|
+
export declare function canonicalHash(value: unknown): `sha256:${string}`;
|
|
97
|
+
/**
|
|
98
|
+
* Parse a TTL string like "10m", "1h", "30s", "1d" into seconds.
|
|
99
|
+
*/
|
|
100
|
+
export declare function parseTtl(ttl: string): number;
|
|
101
|
+
/**
|
|
102
|
+
* Parse an OTP envelope: `<base64url(payloadJson)>.<base64url(signature)>`.
|
|
103
|
+
* Returns the payload object and raw signature bytes.
|
|
104
|
+
*/
|
|
105
|
+
export declare function parseOtp(otp: string): {
|
|
106
|
+
payload: PayGateOtpPayload;
|
|
107
|
+
signature: Buffer;
|
|
108
|
+
};
|
|
109
|
+
/**
|
|
110
|
+
* Create an in-process, single-use replay store backed by a `Set`.
|
|
111
|
+
* Scoped to whatever holds the reference (typically one provider instance).
|
|
112
|
+
*/
|
|
113
|
+
export declare function createReplayStore(): ReplayStore;
|
|
114
|
+
/**
|
|
115
|
+
* The exact endpoint an OTP authorizes, plus the request it is bound to.
|
|
116
|
+
* `provider`/`method` may be omitted when `dotPath` uniquely identifies a
|
|
117
|
+
* single paid endpoint (it is resolved from `PAID_ENDPOINTS`).
|
|
118
|
+
*/
|
|
119
|
+
export interface OtpCall {
|
|
120
|
+
provider?: string;
|
|
121
|
+
method?: string;
|
|
122
|
+
dotPath: string;
|
|
123
|
+
request: Record<string, unknown>;
|
|
124
|
+
/** Time-to-live as seconds or a string like "10m". Defaults to 10m. */
|
|
125
|
+
ttl?: string | number;
|
|
126
|
+
}
|
|
127
|
+
/**
|
|
128
|
+
* Mint an OTP for a specific request, signed with the shared HMAC secret.
|
|
129
|
+
*
|
|
130
|
+
* Pure and env-free: the secret is passed explicitly. The OTP binds to the
|
|
131
|
+
* exact request via its canonical hash, so changing any byte of the request
|
|
132
|
+
* invalidates the token.
|
|
133
|
+
*/
|
|
134
|
+
export declare function mintOtp(secret: string, call: OtpCall): string;
|
|
135
|
+
/**
|
|
136
|
+
* Pure verification of an OTP against expected request context.
|
|
137
|
+
*
|
|
138
|
+
* Returns a tagged-union `VerifyResult` — never throws. The caller is
|
|
139
|
+
* responsible for converting `{ ok: false }` into a `PayGateError` at the
|
|
140
|
+
* boundary.
|
|
141
|
+
*/
|
|
142
|
+
export declare function verifyOtp(input: VerifyOtpInput): VerifyResult;
|
|
143
|
+
/**
|
|
144
|
+
* Wrap a provider network dispatch with the OTP-based paid-endpoint gate.
|
|
145
|
+
*
|
|
146
|
+
* Free/unlisted endpoints return `dispatch()` immediately without OTP or
|
|
147
|
+
* pay-gate configuration.
|
|
148
|
+
*
|
|
149
|
+
* Paid endpoints fail closed: if the pay gate is not configured, or the OTP
|
|
150
|
+
* is missing, invalid, expired, replayed, or mismatched, the call throws
|
|
151
|
+
* before dispatch runs. This is the "no bypass" guarantee — a paid call cannot
|
|
152
|
+
* fire without a configured secret and a valid, human/code-client-minted OTP.
|
|
153
|
+
*
|
|
154
|
+
* The OTP jti is consumed BEFORE dispatch. If dispatch later fails for any
|
|
155
|
+
* reason, the jti remains consumed and the caller must mint a fresh OTP to
|
|
156
|
+
* retry. This is intentional — without it, a hostile caller could replay an
|
|
157
|
+
* OTP on every transient failure.
|
|
158
|
+
*/
|
|
159
|
+
export declare function dispatchWithPaidGate<T>(provider: string, method: string, dotPath: string, payload: Record<string, unknown>, approval: PayGateApproval | undefined, dispatch: () => Promise<T>, config?: PayGateConfig): Promise<T>;
|
|
160
|
+
//# sourceMappingURL=paygate.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"paygate.d.ts","sourceRoot":"","sources":["../../src/paygate.ts"],"names":[],"mappings":"AASA;;;;GAIG;AACH,MAAM,WAAW,iBAAiB;IAChC,CAAC,EAAE,CAAC,CAAC;IACL,GAAG,EAAE,MAAM,CAAC;IACZ,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,EAAE,MAAM,CAAC;IACf,OAAO,EAAE,MAAM,CAAC;IAChB,WAAW,EAAE,UAAU,MAAM,EAAE,CAAC;IAChC,GAAG,EAAE,MAAM,CAAC;IACZ,GAAG,EAAE,MAAM,CAAC;CACb;AAED;;GAEG;AACH,MAAM,WAAW,eAAe;IAC9B,GAAG,EAAE,MAAM,CAAC;CACb;AAED;;;;GAIG;AACH,MAAM,WAAW,WAAW;IAC1B,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;IAC1B,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,IAAI,CAAC;CACxB;AAED;;;;GAIG;AACH,MAAM,WAAW,aAAa;IAC5B,0EAA0E;IAC1E,MAAM,EAAE,MAAM,CAAC;IACf,2EAA2E;IAC3E,WAAW,CAAC,EAAE,WAAW,CAAC;IAC1B,2DAA2D;IAC3D,GAAG,CAAC,EAAE,MAAM,MAAM,CAAC;CACpB;AAED;;GAEG;AACH,qBAAa,YAAa,SAAQ,KAAK;IACrC,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,IAAI,EACT,wBAAwB,GACxB,aAAa,GACb,eAAe,GACf,uBAAuB,GACvB,aAAa,GACb,wBAAwB,GACxB,cAAc,CAAC;gBAGjB,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,MAAM,EACd,OAAO,EAAE,MAAM,EACf,IAAI,EAAE,YAAY,CAAC,MAAM,CAAC,EAC1B,OAAO,EAAE,MAAM;CASlB;AAED;;;;GAIG;AACH,MAAM,MAAM,iBAAiB,GACzB,eAAe,GACf,uBAAuB,GACvB,aAAa,GACb,wBAAwB,GACxB,cAAc,CAAC;AAEnB;;GAEG;AACH,MAAM,MAAM,YAAY,GACpB;IAAE,EAAE,EAAE,IAAI,CAAC;IAAC,GAAG,EAAE,MAAM,CAAA;CAAE,GACzB;IAAE,EAAE,EAAE,KAAK,CAAC;IAAC,IAAI,EAAE,iBAAiB,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAE,CAAC;AAE5D;;;GAGG;AACH,MAAM,WAAW,cAAc;IAC7B,UAAU,EAAE,MAAM,CAAC;IACnB,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE;QAAE,QAAQ,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,MAAM,CAAC;QAAC,OAAO,EAAE,MAAM,CAAA;KAAE,CAAC;IAChE,WAAW,EAAE,UAAU,MAAM,EAAE,CAAC;IAChC,GAAG,EAAE,MAAM,CAAC;IACZ,aAAa,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,OAAO,CAAC;CACzC;AAED;;;;GAIG;AACH,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,CAsCvD;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,KAAK,EAAE,OAAO,GAAG,UAAU,MAAM,EAAE,CAIhE;AAuBD;;GAEG;AACH,wBAAgB,QAAQ,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAqB5C;AAED;;;GAGG;AACH,wBAAgB,QAAQ,CAAC,GAAG,EAAE,MAAM,GAAG;IACrC,OAAO,EAAE,iBAAiB,CAAC;IAC3B,SAAS,EAAE,MAAM,CAAC;CACnB,CA+BA;AAwBD;;;GAGG;AACH,wBAAgB,iBAAiB,IAAI,WAAW,CAQ/C;AAED;;;;GAIG;AACH,MAAM,WAAW,OAAO;IACtB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IACjC,uEAAuE;IACvE,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;CACvB;AAyCD;;;;;;GAMG;AACH,wBAAgB,OAAO,CAAC,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,OAAO,GAAG,MAAM,CA6B7D;AAED;;;;;;GAMG;AACH,wBAAgB,SAAS,CAAC,KAAK,EAAE,cAAc,GAAG,YAAY,CA8D7D;AAED;;;;;;;;;;;;;;;GAeG;AACH,wBAAsB,oBAAoB,CAAC,CAAC,EAC1C,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,MAAM,EACd,OAAO,EAAE,MAAM,EACf,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAChC,QAAQ,EAAE,eAAe,GAAG,SAAS,EACrC,QAAQ,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,EAC1B,MAAM,CAAC,EAAE,aAAa,GACrB,OAAO,CAAC,CAAC,CAAC,CAkDZ"}
|
|
@@ -0,0 +1,336 @@
|
|
|
1
|
+
import { createHash, createHmac, randomBytes, timingSafeEqual, } from "node:crypto";
|
|
2
|
+
import { isPaidEndpoint, PAID_ENDPOINTS } from "./paid-endpoints.js";
|
|
3
|
+
/**
|
|
4
|
+
* Error thrown when the pay gate blocks a request.
|
|
5
|
+
*/
|
|
6
|
+
export class PayGateError extends Error {
|
|
7
|
+
provider;
|
|
8
|
+
method;
|
|
9
|
+
dotPath;
|
|
10
|
+
code;
|
|
11
|
+
constructor(provider, method, dotPath, code, message) {
|
|
12
|
+
super(message);
|
|
13
|
+
this.name = "PayGateError";
|
|
14
|
+
this.provider = provider;
|
|
15
|
+
this.method = method;
|
|
16
|
+
this.dotPath = dotPath;
|
|
17
|
+
this.code = code;
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Canonicalize a JSON value by sorting object keys recursively.
|
|
22
|
+
* Arrays preserve order. Non-JSON values (undefined, functions, symbols,
|
|
23
|
+
* circular references) cause a TypeError so the caller can fail closed.
|
|
24
|
+
*/
|
|
25
|
+
export function canonicalizeJson(value) {
|
|
26
|
+
const seen = new WeakSet();
|
|
27
|
+
function walk(v) {
|
|
28
|
+
if (v === null ||
|
|
29
|
+
typeof v === "boolean" ||
|
|
30
|
+
typeof v === "number" ||
|
|
31
|
+
typeof v === "string") {
|
|
32
|
+
return v;
|
|
33
|
+
}
|
|
34
|
+
if (typeof v === "undefined" ||
|
|
35
|
+
typeof v === "function" ||
|
|
36
|
+
typeof v === "symbol") {
|
|
37
|
+
throw new TypeError("Cannot canonicalize non-JSON value: " + typeof v);
|
|
38
|
+
}
|
|
39
|
+
if (Array.isArray(v)) {
|
|
40
|
+
return v.map(walk);
|
|
41
|
+
}
|
|
42
|
+
if (typeof v === "object") {
|
|
43
|
+
if (seen.has(v)) {
|
|
44
|
+
throw new TypeError("Cannot canonicalize circular reference");
|
|
45
|
+
}
|
|
46
|
+
seen.add(v);
|
|
47
|
+
const sortedKeys = Object.keys(v).sort();
|
|
48
|
+
const out = {};
|
|
49
|
+
for (const k of sortedKeys) {
|
|
50
|
+
out[k] = walk(v[k]);
|
|
51
|
+
}
|
|
52
|
+
return out;
|
|
53
|
+
}
|
|
54
|
+
throw new TypeError("Cannot canonicalize unexpected type: " + typeof v);
|
|
55
|
+
}
|
|
56
|
+
return JSON.stringify(walk(value));
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* Compute SHA-256 of canonical JSON, prefixed with `sha256:`.
|
|
60
|
+
*/
|
|
61
|
+
export function canonicalHash(value) {
|
|
62
|
+
const canonical = canonicalizeJson(value);
|
|
63
|
+
const hash = createHash("sha256").update(canonical, "utf8").digest("hex");
|
|
64
|
+
return `sha256:${hash}`;
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* Encode a buffer to unpadded base64url.
|
|
68
|
+
*/
|
|
69
|
+
function base64urlEncode(data) {
|
|
70
|
+
return data
|
|
71
|
+
.toString("base64")
|
|
72
|
+
.replace(/\+/g, "-")
|
|
73
|
+
.replace(/\//g, "_")
|
|
74
|
+
.replace(/=+$/g, "");
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Decode base64url (no padding required).
|
|
78
|
+
*/
|
|
79
|
+
function base64urlDecode(str) {
|
|
80
|
+
const base64 = str.replace(/-/g, "+").replace(/_/g, "/");
|
|
81
|
+
const padLen = (4 - (base64.length % 4)) % 4;
|
|
82
|
+
const padded = base64 + "=".repeat(padLen);
|
|
83
|
+
return Buffer.from(padded, "base64");
|
|
84
|
+
}
|
|
85
|
+
/**
|
|
86
|
+
* Parse a TTL string like "10m", "1h", "30s", "1d" into seconds.
|
|
87
|
+
*/
|
|
88
|
+
export function parseTtl(ttl) {
|
|
89
|
+
const match = ttl.match(/^(\d+)([smhd])$/i);
|
|
90
|
+
if (!match) {
|
|
91
|
+
throw new Error(`Invalid TTL format: ${ttl}. Expected format like 10m, 1h, 30s.`);
|
|
92
|
+
}
|
|
93
|
+
const value = parseInt(match[1], 10);
|
|
94
|
+
const unit = match[2].toLowerCase();
|
|
95
|
+
switch (unit) {
|
|
96
|
+
case "s":
|
|
97
|
+
return value;
|
|
98
|
+
case "m":
|
|
99
|
+
return value * 60;
|
|
100
|
+
case "h":
|
|
101
|
+
return value * 60 * 60;
|
|
102
|
+
case "d":
|
|
103
|
+
return value * 60 * 60 * 24;
|
|
104
|
+
default:
|
|
105
|
+
throw new Error(`Unknown TTL unit: ${unit}`);
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
/**
|
|
109
|
+
* Parse an OTP envelope: `<base64url(payloadJson)>.<base64url(signature)>`.
|
|
110
|
+
* Returns the payload object and raw signature bytes.
|
|
111
|
+
*/
|
|
112
|
+
export function parseOtp(otp) {
|
|
113
|
+
const parts = otp.split(".");
|
|
114
|
+
if (parts.length !== 2) {
|
|
115
|
+
throw new Error("OTP must contain exactly one '.' separator");
|
|
116
|
+
}
|
|
117
|
+
const payloadJson = base64urlDecode(parts[0]).toString("utf8");
|
|
118
|
+
const signature = base64urlDecode(parts[1]);
|
|
119
|
+
let payload;
|
|
120
|
+
try {
|
|
121
|
+
payload = JSON.parse(payloadJson);
|
|
122
|
+
}
|
|
123
|
+
catch {
|
|
124
|
+
throw new Error("OTP payload is not valid JSON");
|
|
125
|
+
}
|
|
126
|
+
if (typeof payload !== "object" ||
|
|
127
|
+
payload === null ||
|
|
128
|
+
payload.v !== 1 ||
|
|
129
|
+
typeof payload.jti !== "string" ||
|
|
130
|
+
typeof payload.provider !== "string" ||
|
|
131
|
+
typeof payload.method !== "string" ||
|
|
132
|
+
typeof payload.dotPath !== "string" ||
|
|
133
|
+
typeof payload.requestHash !== "string" ||
|
|
134
|
+
typeof payload.iat !== "number" ||
|
|
135
|
+
typeof payload.exp !== "number") {
|
|
136
|
+
throw new Error("OTP payload missing required fields");
|
|
137
|
+
}
|
|
138
|
+
return {
|
|
139
|
+
payload: payload,
|
|
140
|
+
signature,
|
|
141
|
+
};
|
|
142
|
+
}
|
|
143
|
+
/**
|
|
144
|
+
* Compute the HMAC-SHA256 of an OTP payload segment with the shared secret.
|
|
145
|
+
*/
|
|
146
|
+
function signPayloadSegment(payloadSegment, secret) {
|
|
147
|
+
return createHmac("sha256", secret).update(payloadSegment, "utf8").digest();
|
|
148
|
+
}
|
|
149
|
+
/**
|
|
150
|
+
* Constant-time verification of an OTP payload segment's HMAC signature.
|
|
151
|
+
*/
|
|
152
|
+
function verifyPayloadSignature(payloadSegment, signature, secret) {
|
|
153
|
+
const expected = signPayloadSegment(payloadSegment, secret);
|
|
154
|
+
if (expected.length !== signature.length) {
|
|
155
|
+
return false;
|
|
156
|
+
}
|
|
157
|
+
return timingSafeEqual(expected, signature);
|
|
158
|
+
}
|
|
159
|
+
/**
|
|
160
|
+
* Create an in-process, single-use replay store backed by a `Set`.
|
|
161
|
+
* Scoped to whatever holds the reference (typically one provider instance).
|
|
162
|
+
*/
|
|
163
|
+
export function createReplayStore() {
|
|
164
|
+
const seen = new Set();
|
|
165
|
+
return {
|
|
166
|
+
has: (jti) => seen.has(jti),
|
|
167
|
+
add: (jti) => {
|
|
168
|
+
seen.add(jti);
|
|
169
|
+
},
|
|
170
|
+
};
|
|
171
|
+
}
|
|
172
|
+
const DEFAULT_TTL_SECONDS = 600;
|
|
173
|
+
/**
|
|
174
|
+
* Resolve `(provider, method, dotPath)` for a mint call. When the caller omits
|
|
175
|
+
* provider/method, the dotPath must match exactly one entry in
|
|
176
|
+
* `PAID_ENDPOINTS`.
|
|
177
|
+
*/
|
|
178
|
+
function resolveCallKey(call) {
|
|
179
|
+
if (call.provider && call.method) {
|
|
180
|
+
return {
|
|
181
|
+
provider: call.provider,
|
|
182
|
+
method: call.method,
|
|
183
|
+
dotPath: call.dotPath,
|
|
184
|
+
};
|
|
185
|
+
}
|
|
186
|
+
const matches = PAID_ENDPOINTS.filter((e) => e.key.dotPath === call.dotPath &&
|
|
187
|
+
(call.method === undefined || e.key.method === call.method) &&
|
|
188
|
+
(call.provider === undefined || e.key.provider === call.provider));
|
|
189
|
+
if (matches.length === 1) {
|
|
190
|
+
const key = matches[0].key;
|
|
191
|
+
return {
|
|
192
|
+
provider: call.provider ?? key.provider,
|
|
193
|
+
method: call.method ?? key.method,
|
|
194
|
+
dotPath: call.dotPath,
|
|
195
|
+
};
|
|
196
|
+
}
|
|
197
|
+
throw new Error(`Cannot resolve provider/method for dotPath "${call.dotPath}". ` +
|
|
198
|
+
`Pass { provider, method } explicitly.`);
|
|
199
|
+
}
|
|
200
|
+
/**
|
|
201
|
+
* Mint an OTP for a specific request, signed with the shared HMAC secret.
|
|
202
|
+
*
|
|
203
|
+
* Pure and env-free: the secret is passed explicitly. The OTP binds to the
|
|
204
|
+
* exact request via its canonical hash, so changing any byte of the request
|
|
205
|
+
* invalidates the token.
|
|
206
|
+
*/
|
|
207
|
+
export function mintOtp(secret, call) {
|
|
208
|
+
if (!secret) {
|
|
209
|
+
throw new Error("mintOtp requires a non-empty secret");
|
|
210
|
+
}
|
|
211
|
+
const key = resolveCallKey(call);
|
|
212
|
+
const ttlSeconds = call.ttl === undefined
|
|
213
|
+
? DEFAULT_TTL_SECONDS
|
|
214
|
+
: typeof call.ttl === "number"
|
|
215
|
+
? call.ttl
|
|
216
|
+
: parseTtl(call.ttl);
|
|
217
|
+
const iat = Math.floor(Date.now() / 1000);
|
|
218
|
+
const payload = {
|
|
219
|
+
v: 1,
|
|
220
|
+
jti: randomBytes(16).toString("hex"),
|
|
221
|
+
provider: key.provider,
|
|
222
|
+
method: key.method,
|
|
223
|
+
dotPath: key.dotPath,
|
|
224
|
+
requestHash: canonicalHash(call.request),
|
|
225
|
+
iat,
|
|
226
|
+
exp: iat + ttlSeconds,
|
|
227
|
+
};
|
|
228
|
+
const payloadSegment = base64urlEncode(Buffer.from(JSON.stringify(payload), "utf8"));
|
|
229
|
+
const signatureSegment = base64urlEncode(signPayloadSegment(payloadSegment, secret));
|
|
230
|
+
return `${payloadSegment}.${signatureSegment}`;
|
|
231
|
+
}
|
|
232
|
+
/**
|
|
233
|
+
* Pure verification of an OTP against expected request context.
|
|
234
|
+
*
|
|
235
|
+
* Returns a tagged-union `VerifyResult` — never throws. The caller is
|
|
236
|
+
* responsible for converting `{ ok: false }` into a `PayGateError` at the
|
|
237
|
+
* boundary.
|
|
238
|
+
*/
|
|
239
|
+
export function verifyOtp(input) {
|
|
240
|
+
let parsed;
|
|
241
|
+
try {
|
|
242
|
+
parsed = parseOtp(input.otp);
|
|
243
|
+
}
|
|
244
|
+
catch (e) {
|
|
245
|
+
return {
|
|
246
|
+
ok: false,
|
|
247
|
+
code: "otp-malformed",
|
|
248
|
+
message: e instanceof Error ? e.message : "OTP is malformed",
|
|
249
|
+
};
|
|
250
|
+
}
|
|
251
|
+
const { payload, signature } = parsed;
|
|
252
|
+
const payloadSegment = input.otp.split(".")[0];
|
|
253
|
+
if (!verifyPayloadSignature(payloadSegment, signature, input.secret)) {
|
|
254
|
+
return {
|
|
255
|
+
ok: false,
|
|
256
|
+
code: "otp-invalid-signature",
|
|
257
|
+
message: "OTP signature is invalid",
|
|
258
|
+
};
|
|
259
|
+
}
|
|
260
|
+
if (payload.exp < input.nowSeconds) {
|
|
261
|
+
return {
|
|
262
|
+
ok: false,
|
|
263
|
+
code: "otp-expired",
|
|
264
|
+
message: `OTP expired at ${payload.exp} (now is ${input.nowSeconds})`,
|
|
265
|
+
};
|
|
266
|
+
}
|
|
267
|
+
if (payload.provider !== input.expected.provider ||
|
|
268
|
+
payload.method !== input.expected.method ||
|
|
269
|
+
payload.dotPath !== input.expected.dotPath) {
|
|
270
|
+
return {
|
|
271
|
+
ok: false,
|
|
272
|
+
code: "otp-mismatched-request",
|
|
273
|
+
message: `OTP bound to ${payload.provider} ${payload.method} ${payload.dotPath}, ` +
|
|
274
|
+
`but call is ${input.expected.provider} ${input.expected.method} ${input.expected.dotPath}`,
|
|
275
|
+
};
|
|
276
|
+
}
|
|
277
|
+
if (payload.requestHash !== input.payloadHash) {
|
|
278
|
+
return {
|
|
279
|
+
ok: false,
|
|
280
|
+
code: "otp-mismatched-request",
|
|
281
|
+
message: `OTP request hash mismatch: expected ${input.payloadHash}, got ${payload.requestHash}`,
|
|
282
|
+
};
|
|
283
|
+
}
|
|
284
|
+
if (input.isJtiConsumed(payload.jti)) {
|
|
285
|
+
return {
|
|
286
|
+
ok: false,
|
|
287
|
+
code: "otp-replayed",
|
|
288
|
+
message: `OTP jti ${payload.jti} has already been consumed`,
|
|
289
|
+
};
|
|
290
|
+
}
|
|
291
|
+
return { ok: true, jti: payload.jti };
|
|
292
|
+
}
|
|
293
|
+
/**
|
|
294
|
+
* Wrap a provider network dispatch with the OTP-based paid-endpoint gate.
|
|
295
|
+
*
|
|
296
|
+
* Free/unlisted endpoints return `dispatch()` immediately without OTP or
|
|
297
|
+
* pay-gate configuration.
|
|
298
|
+
*
|
|
299
|
+
* Paid endpoints fail closed: if the pay gate is not configured, or the OTP
|
|
300
|
+
* is missing, invalid, expired, replayed, or mismatched, the call throws
|
|
301
|
+
* before dispatch runs. This is the "no bypass" guarantee — a paid call cannot
|
|
302
|
+
* fire without a configured secret and a valid, human/code-client-minted OTP.
|
|
303
|
+
*
|
|
304
|
+
* The OTP jti is consumed BEFORE dispatch. If dispatch later fails for any
|
|
305
|
+
* reason, the jti remains consumed and the caller must mint a fresh OTP to
|
|
306
|
+
* retry. This is intentional — without it, a hostile caller could replay an
|
|
307
|
+
* OTP on every transient failure.
|
|
308
|
+
*/
|
|
309
|
+
export async function dispatchWithPaidGate(provider, method, dotPath, payload, approval, dispatch, config) {
|
|
310
|
+
if (!isPaidEndpoint(provider, method, dotPath)) {
|
|
311
|
+
return dispatch();
|
|
312
|
+
}
|
|
313
|
+
if (!config || !config.secret) {
|
|
314
|
+
throw new PayGateError(provider, method, dotPath, "paygate-not-configured", `Paid endpoint ${provider} ${method} ${dotPath} requires a pay gate. ` +
|
|
315
|
+
`Construct the provider with { paygate: { secret } }.`);
|
|
316
|
+
}
|
|
317
|
+
if (!approval || !approval.otp) {
|
|
318
|
+
throw new PayGateError(provider, method, dotPath, "otp-missing", "Paid endpoint requires an OTP approval. Pass { otp: '...' }.");
|
|
319
|
+
}
|
|
320
|
+
const store = config.replayStore ?? createReplayStore();
|
|
321
|
+
const now = config.now ?? (() => Date.now());
|
|
322
|
+
const result = verifyOtp({
|
|
323
|
+
nowSeconds: Math.floor(now() / 1000),
|
|
324
|
+
secret: config.secret,
|
|
325
|
+
expected: { provider, method, dotPath },
|
|
326
|
+
payloadHash: canonicalHash(payload),
|
|
327
|
+
otp: approval.otp,
|
|
328
|
+
isJtiConsumed: (jti) => store.has(jti),
|
|
329
|
+
});
|
|
330
|
+
if (!result.ok) {
|
|
331
|
+
throw new PayGateError(provider, method, dotPath, result.code, result.message);
|
|
332
|
+
}
|
|
333
|
+
store.add(result.jti);
|
|
334
|
+
return dispatch();
|
|
335
|
+
}
|
|
336
|
+
//# sourceMappingURL=paygate.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"paygate.js","sourceRoot":"","sources":["../../src/paygate.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"kie.d.ts","sourceRoot":"","sources":["../../../src/pricing/kie.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;
|
|
1
|
+
{"version":3,"file":"kie.d.ts","sourceRoot":"","sources":["../../../src/pricing/kie.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AAiG5C,eAAO,MAAM,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAqQ5C,CAAC"}
|
package/dist/src/pricing/kie.js
CHANGED
|
@@ -40,20 +40,34 @@ const flatGen = (perUnit, slug) => ({
|
|
|
40
40
|
source: src(slug),
|
|
41
41
|
});
|
|
42
42
|
// Image entry tiered by input.resolution (e.g. "1K"|"2K"|"4K").
|
|
43
|
-
|
|
43
|
+
// Optional `defaultResolution` is applied when the payload omits
|
|
44
|
+
// input.resolution (matches the upstream schema default).
|
|
45
|
+
const tieredImage = (rates, slug, defaultResolution) => ({
|
|
44
46
|
kind: "perUnit",
|
|
45
47
|
unit: "images",
|
|
46
48
|
units: imageCount,
|
|
47
|
-
select: [
|
|
49
|
+
select: [
|
|
50
|
+
{
|
|
51
|
+
name: "resolution",
|
|
52
|
+
pick: (p) => asString(asObject(p.input)?.resolution) ?? defaultResolution,
|
|
53
|
+
},
|
|
54
|
+
],
|
|
48
55
|
rates,
|
|
49
56
|
source: src(slug),
|
|
50
57
|
});
|
|
51
58
|
// Video entry tiered by input.resolution (grok-imagine, happyhorse).
|
|
52
|
-
|
|
59
|
+
// Optional `defaultResolution` is applied when the payload omits
|
|
60
|
+
// input.resolution (matches the upstream schema default).
|
|
61
|
+
const tieredResolutionVideo = (rates, slug, defaultResolution) => ({
|
|
53
62
|
kind: "perUnit",
|
|
54
63
|
unit: "seconds",
|
|
55
64
|
units: seconds,
|
|
56
|
-
select: [
|
|
65
|
+
select: [
|
|
66
|
+
{
|
|
67
|
+
name: "resolution",
|
|
68
|
+
pick: (p) => asString(asObject(p.input)?.resolution) ?? defaultResolution,
|
|
69
|
+
},
|
|
70
|
+
],
|
|
57
71
|
rates,
|
|
58
72
|
source: src(slug),
|
|
59
73
|
});
|
|
@@ -221,12 +235,12 @@ export const kie = {
|
|
|
221
235
|
// (nano-banana-2, gpt-image-2) require input.resolution; flat-rate
|
|
222
236
|
// families (qwen2, seedream/5-lite) only need the model string.
|
|
223
237
|
// wan/2-7-image accepts an `n` field for batch generation.
|
|
224
|
-
"nano-banana-2": tieredImage({ "1K": 0.04, "2K": 0.06, "4K": 0.09 }, "google/nano-banana-2"),
|
|
238
|
+
"nano-banana-2": tieredImage({ "1K": 0.04, "2K": 0.06, "4K": 0.09 }, "google/nano-banana-2", "2K"),
|
|
225
239
|
// nano-banana-pro: 1K and 2K share the $0.09 rate per the marketplace
|
|
226
240
|
// ("1/2K"), 4K is $0.12.
|
|
227
|
-
"nano-banana-pro": tieredImage({ "1K": 0.09, "2K": 0.09, "4K": 0.12 }, "google/nano-banana-pro"),
|
|
228
|
-
"gpt-image-2-text-to-image": tieredImage({ "1K": 0.03, "2K": 0.05, "4K": 0.08 }, "openai/gpt-image-2"),
|
|
229
|
-
"gpt-image-2-image-to-image": tieredImage({ "1K": 0.03, "2K": 0.05, "4K": 0.08 }, "openai/gpt-image-2"),
|
|
241
|
+
"nano-banana-pro": tieredImage({ "1K": 0.09, "2K": 0.09, "4K": 0.12 }, "google/nano-banana-pro", "2K"),
|
|
242
|
+
"gpt-image-2-text-to-image": tieredImage({ "1K": 0.03, "2K": 0.05, "4K": 0.08 }, "openai/gpt-image-2", "2K"),
|
|
243
|
+
"gpt-image-2-image-to-image": tieredImage({ "1K": 0.03, "2K": 0.05, "4K": 0.08 }, "openai/gpt-image-2", "2K"),
|
|
230
244
|
"wan/2-7-image": flatImage(0.024, "alibaba/wan-2.7"),
|
|
231
245
|
"wan/2-7-image-pro": flatImage(0.06, "alibaba/wan-2.7"),
|
|
232
246
|
"qwen2/text-to-image": flatImage(0.028, "alibaba/qwen-image-2"),
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"kie.js","sourceRoot":"","sources":["../../../src/pricing/kie.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,QAAQ,EAAE,QAAQ,EAAE,QAAQ,EAAE,aAAa,EAAE,MAAM,WAAW,CAAC;AAExE,uEAAuE;AACvE,6EAA6E;AAC7E,2EAA2E;AAC3E,oEAAoE;AACpE,wEAAwE;AAExE,MAAM,GAAG,GAAG,CAAC,IAAY,EAAE,EAAE,CAAC,CAAC,EAAE,GAAG,EAAE,yBAAyB,IAAI,EAAE,EAAE,CAAC,CAAC;AAEzE,6EAA6E;AAC7E,0EAA0E;AAC1E,MAAM,OAAO,GAAG,CAAC,CAA0B,EAAsB,EAAE,CACjE,aAAa,CAAC,QAAQ,CAAC,CAAC,CAAC,KAAK,CAAC,EAAE,QAAQ,IAAI,CAAC,CAAC,QAAQ,CAAC,CAAC;AAE3D,MAAM,eAAe,GAAG,CAAC,CAA0B,EAAsB,EAAE,CACzE,QAAQ,CAAC,QAAQ,CAAC,CAAC,CAAC,KAAK,CAAC,EAAE,UAAU,CAAC,CAAC;AAE1C,MAAM,SAAS,GAAG,CAAC,CAA0B,EAAsB,EAAE,CACnE,QAAQ,CAAC,QAAQ,CAAC,CAAC,CAAC,KAAK,CAAC,EAAE,IAAI,CAAC,CAAC;AAEpC,mEAAmE;AACnE,4DAA4D;AAC5D,MAAM,UAAU,GAAG,CAAC,CAA0B,EAAU,EAAE,CACxD,QAAQ,CAAC,QAAQ,CAAC,CAAC,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,IAAI,CAAC,CAAC;AAEtC,MAAM,SAAS,GAAG,CAAC,OAAe,EAAE,IAAY,EAAgB,EAAE,CAAC,CAAC;IAClE,IAAI,EAAE,SAAS;IACf,IAAI,EAAE,SAAS;IACf,KAAK,EAAE,OAAO;IACd,MAAM,EAAE,EAAE;IACV,KAAK,EAAE,EAAE,EAAE,EAAE,OAAO,EAAE;IACtB,MAAM,EAAE,GAAG,CAAC,IAAI,CAAC;CAClB,CAAC,CAAC;AAEH,MAAM,SAAS,GAAG,CAAC,OAAe,EAAE,IAAY,EAAgB,EAAE,CAAC,CAAC;IAClE,IAAI,EAAE,SAAS;IACf,IAAI,EAAE,QAAQ;IACd,KAAK,EAAE,UAAU;IACjB,MAAM,EAAE,EAAE;IACV,KAAK,EAAE,EAAE,EAAE,EAAE,OAAO,EAAE;IACtB,MAAM,EAAE,GAAG,CAAC,IAAI,CAAC;CAClB,CAAC,CAAC;AAEH,yEAAyE;AACzE,iEAAiE;AACjE,MAAM,OAAO,GAAG,CAAC,OAAe,EAAE,IAAY,EAAgB,EAAE,CAAC,CAAC;IAChE,IAAI,EAAE,SAAS;IACf,IAAI,EAAE,aAAa;IACnB,KAAK,EAAE,GAAG,EAAE,CAAC,CAAC;IACd,MAAM,EAAE,EAAE;IACV,KAAK,EAAE,EAAE,EAAE,EAAE,OAAO,EAAE;IACtB,MAAM,EAAE,GAAG,CAAC,IAAI,CAAC;CAClB,CAAC,CAAC;AAEH,gEAAgE;AAChE,MAAM,WAAW,GAAG,CAClB,KAA6B,EAC7B,IAAY,
|
|
1
|
+
{"version":3,"file":"kie.js","sourceRoot":"","sources":["../../../src/pricing/kie.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import { type PayGateConfig } from "./paygate";
|
|
2
|
+
export interface WithPaidGateOptions {
|
|
3
|
+
/**
|
|
4
|
+
* Top-level keys to recurse into. Default: HTTP-method buckets.
|
|
5
|
+
*/
|
|
6
|
+
roots?: readonly string[];
|
|
7
|
+
/**
|
|
8
|
+
* Pay-gate configuration (shared HMAC secret + optional replay store/clock)
|
|
9
|
+
* forwarded to every gated dispatch. When omitted, paid endpoints fail closed
|
|
10
|
+
* with `paygate-not-configured`.
|
|
11
|
+
*/
|
|
12
|
+
config?: PayGateConfig;
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Walk a provider tree once and route every paid-endpoint leaf through
|
|
16
|
+
* `dispatchWithPaidGate`. Free leaves are returned untouched. Callable
|
|
17
|
+
* namespaces (functions with child properties — e.g. `xai.v1.models` is a
|
|
18
|
+
* function with `.languageModels` children) preserve all children and their
|
|
19
|
+
* `.schema` attachments.
|
|
20
|
+
*
|
|
21
|
+
* @param providerName Provider identifier matching `PAID_ENDPOINTS`.
|
|
22
|
+
* @param tree The provider object returned by the factory.
|
|
23
|
+
* @param opts Optional roots allowlist and IO injection.
|
|
24
|
+
* @returns A new tree of the same shape; paid leaves accept `(req, approval?)`.
|
|
25
|
+
*/
|
|
26
|
+
export declare function withPaidGate<T extends object>(providerName: string, tree: T, opts?: WithPaidGateOptions): T;
|
|
27
|
+
//# sourceMappingURL=with-paid-gate.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"with-paid-gate.d.ts","sourceRoot":"","sources":["../../src/with-paid-gate.ts"],"names":[],"mappings":"AAAA,OAAO,EAIL,KAAK,aAAa,EACnB,MAAM,WAAW,CAAC;AAWnB,MAAM,WAAW,mBAAmB;IAClC;;OAEG;IACH,KAAK,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IAC1B;;;;OAIG;IACH,MAAM,CAAC,EAAE,aAAa,CAAC;CACxB;AAMD;;;;;;;;;;;GAWG;AACH,wBAAgB,YAAY,CAAC,CAAC,SAAS,MAAM,EAC3C,YAAY,EAAE,MAAM,EACpB,IAAI,EAAE,CAAC,EACP,IAAI,CAAC,EAAE,mBAAmB,GACzB,CAAC,CAoBH"}
|