@belticlabs/agent-risk-sdk 0.5.0 → 0.7.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.
@@ -1,24 +1,12 @@
1
- import { PaywallConfig, RoutesConfig, x402ResourceServer } from '@x402/core/server';
1
+ import { RoutesConfig, x402ResourceServer } from '@x402/core/server';
2
2
  import { MiddlewareHandler } from 'hono';
3
- import { B as Beltic } from '../session-D9E-efc0.js';
4
- import { A as AttachOptions } from '../adapter-DEdhsNt-.js';
5
- export { a as attachX402 } from '../adapter-DEdhsNt-.js';
6
- import '../verdict-DMnbFuS5.js';
3
+ import { B as Beltic } from '../client-Xn9M58OJ.js';
4
+ import '../index-DAVKGJs5.js';
7
5
  import 'zod';
8
-
9
- /**
10
- * The seller half as one middleware: the framework's `@x402/*` payment
11
- * middleware over an `x402HTTPResourceServer` with the Beltic hooks
12
- * attached. `@belticlabs/agent-risk-sdk/hono` hands in its framework's
13
- * `paymentMiddlewareFromHTTPServer`.
14
- */
15
-
16
- type GuardedMiddlewareOptions = AttachOptions & {
17
- paywall?: PaywallConfig | undefined;
18
- };
6
+ import '../session-DAN29XoB.js';
19
7
 
20
8
  /** Seller half for hono: `@x402/hono`'s payment middleware with the Beltic hooks attached. */
21
9
 
22
- declare function belticPaymentMiddleware(beltic: Beltic, routes: RoutesConfig, server: x402ResourceServer, opts?: GuardedMiddlewareOptions): MiddlewareHandler;
10
+ declare function belticPaymentMiddleware(beltic: Beltic, routes: RoutesConfig, server: x402ResourceServer): MiddlewareHandler;
23
11
 
24
12
  export { belticPaymentMiddleware };
package/dist/x402/hono.js CHANGED
@@ -1,27 +1,21 @@
1
1
  import {
2
2
  attachX402
3
- } from "../chunk-GM4KEEZB.js";
3
+ } from "../chunk-HI656UWG.js";
4
+ import "../chunk-M4I3FGZG.js";
4
5
  import "../chunk-FQDHFTVR.js";
5
- import "../chunk-X3W2Z5GC.js";
6
+ import "../chunk-UXXSE643.js";
7
+ import "../chunk-FNU4CRJJ.js";
6
8
 
7
9
  // src/x402/hono.ts
8
- import { paymentMiddlewareFromHTTPServer } from "@x402/hono";
9
-
10
- // src/x402/middleware.ts
11
10
  import {
12
11
  x402HTTPResourceServer
13
12
  } from "@x402/core/server";
14
- function guardedPaymentMiddleware(fromHTTPServer, beltic, routes, server, opts = {}) {
13
+ import { paymentMiddlewareFromHTTPServer } from "@x402/hono";
14
+ function belticPaymentMiddleware(beltic, routes, server) {
15
15
  const http = new x402HTTPResourceServer(server, routes);
16
- attachX402(beltic, server, http, opts);
17
- return fromHTTPServer(http, opts.paywall);
18
- }
19
-
20
- // src/x402/hono.ts
21
- function belticPaymentMiddleware(beltic, routes, server, opts) {
22
- return guardedPaymentMiddleware(paymentMiddlewareFromHTTPServer, beltic, routes, server, opts);
16
+ attachX402(beltic, server, http);
17
+ return paymentMiddlewareFromHTTPServer(http);
23
18
  }
24
19
  export {
25
- attachX402,
26
20
  belticPaymentMiddleware
27
21
  };
@@ -1,28 +1,25 @@
1
- export { A as AttachOptions, b as AttachedX402, a as attachX402 } from '../adapter-DEdhsNt-.js';
2
- import { S as SessionSource } from '../session-D9E-efc0.js';
3
- import { p as DeclaredIntent, P as PaymentMomentPayload, Y as JsonObject, a8 as PaymentSummary } from '../verdict-DMnbFuS5.js';
4
- import '@x402/core/server';
1
+ import { x402ResourceServer, x402HTTPResourceServer } from '@x402/core/server';
2
+ import { B as Beltic } from '../client-Xn9M58OJ.js';
3
+ import { S as Session } from '../session-DAN29XoB.js';
4
+ import { h as DeclaredIntent, N as PaymentSummary } from '../index-DAVKGJs5.js';
5
5
  import 'zod';
6
6
 
7
+ declare function attachX402(beltic: Beltic, server: x402ResourceServer, http?: x402HTTPResourceServer): void;
8
+
7
9
  /**
8
10
  * Session binding on the x402 rail (Fraud SDK RFC › Protocol Adapter — x402:
9
11
  * "`PAYMENT-SIGNATURE` extension `beltic.sessionId`"). Where exactly it
10
12
  * lives is GAP-30; that it is outside the wallet-signed payload is GAP-56.
11
- * A presentation the buyer had evaluated first also carries the
12
- * `decisionId` the platform answered with, next to the session (GAP-80).
13
13
  */
14
14
  declare const SESSION_EXTENSION = "beltic.sessionId";
15
15
  declare const SESSION_HEADER = "Beltic-Session-Id";
16
- declare const DECISION_EXTENSION = "beltic.decisionId";
17
- declare function sessionIdOf(extensions: Readonly<Record<string, unknown>> | undefined): string | null;
18
- declare function decisionIdOf(extensions: Readonly<Record<string, unknown>> | undefined): string | null;
19
16
 
20
17
  /**
21
- * The paying fetch, observed. Takes a session or the run that owns one; a
22
- * request made while a fail-open run has no session (the platform could
23
- * not open one, GAP-70) goes through the inner fetch unrecorded.
18
+ * The paying fetch, observed. A request made while the session has no
19
+ * stream (the platform could not open one, GAP-70) goes through the inner
20
+ * fetch unrecorded.
24
21
  */
25
- declare function belticFetch(source: SessionSource, inner?: typeof globalThis.fetch): typeof globalThis.fetch;
22
+ declare function belticFetch(session: Session, inner?: typeof globalThis.fetch): typeof globalThis.fetch;
26
23
 
27
24
  /**
28
25
  * The declared intent for an x402 mandate (Fraud SDK RFC › Session ›
@@ -53,7 +50,6 @@ declare function x402Intent(input: X402IntentInput): DeclaredIntent;
53
50
  * about and what the wrapper records are one and the same.
54
51
  */
55
52
 
56
- declare function x402Currency(network: string, asset: string): string;
57
53
  /**
58
54
  * The minimum an `accepts` entry needs to become a moment; unknown parts
59
55
  * are named, never dropped.
@@ -64,22 +60,6 @@ interface AcceptsLike {
64
60
  network?: string | undefined;
65
61
  asset?: string | undefined;
66
62
  }
67
- /**
68
- * A 402 challenge and a presented payment, as far as a moment needs them.
69
- * `@x402/core`'s `PaymentRequired` and `PaymentPayload` satisfy these
70
- * structurally, so the seller adapter passes its typed values through and
71
- * the buyer needs no `@x402/*` types.
72
- */
73
- interface PaymentRequiredLike {
74
- x402Version?: number | undefined;
75
- accepts?: readonly AcceptsLike[] | undefined;
76
- }
77
- interface PaymentPayloadLike {
78
- x402Version?: number | undefined;
79
- accepted?: AcceptsLike | undefined;
80
- payload?: Readonly<Record<string, unknown>> | undefined;
81
- extensions?: Readonly<Record<string, unknown>> | undefined;
82
- }
83
63
  /**
84
64
  * The one normalization of an x402 `accepts` entry: the payment in the
85
65
  * shape `evaluate` takes, with the payer as `payerOf` would read it. Every
@@ -88,17 +68,5 @@ interface PaymentPayloadLike {
88
68
  declare function x402Summary(accepts: AcceptsLike | undefined, opts?: {
89
69
  payer?: string | undefined;
90
70
  }): PaymentSummary;
91
- /** The payer is scheme-specific; the common EVM shapes are read, anything else stays in `raw`. */
92
- declare function payerOf(payload: PaymentPayloadLike): string | undefined;
93
- declare const x402Moments: {
94
- /** The 402 challenge as the buyer saw it, from the `PAYMENT-REQUIRED` header. */
95
- required(required: PaymentRequiredLike): PaymentMomentPayload;
96
- /** The requirements the seller's resource server resolved for a request. */
97
- requirements(req: AcceptsLike): PaymentMomentPayload;
98
- /** A route's static `accepts` config, before any payment header exists. */
99
- route(route: unknown, raw: JsonObject): PaymentMomentPayload;
100
- /** The signed payment the buyer presented, with the requirement it accepted. */
101
- payload(payload: PaymentPayloadLike): PaymentMomentPayload;
102
- };
103
71
 
104
- export { type AcceptsLike, DECISION_EXTENSION, type PaymentPayloadLike, type PaymentRequiredLike, SESSION_EXTENSION, SESSION_HEADER, type X402IntentInput, belticFetch, decisionIdOf, payerOf, sessionIdOf, x402Currency, x402Intent, x402Moments, x402Summary };
72
+ export { type AcceptsLike, SESSION_EXTENSION, SESSION_HEADER, type X402IntentInput, attachX402, belticFetch, x402Intent, x402Summary };
@@ -1,97 +1,86 @@
1
1
  import {
2
- Session,
3
- Sessions
4
- } from "../chunk-JSE6JQJC.js";
5
- import {
6
- DECISION_EXTENSION,
7
2
  SESSION_EXTENSION,
8
3
  SESSION_HEADER,
9
4
  attachX402,
10
- decisionIdOf,
11
- payerOf,
12
- sessionIdOf,
13
- x402Currency,
14
5
  x402Moments,
15
6
  x402Summary
16
- } from "../chunk-GM4KEEZB.js";
7
+ } from "../chunk-HI656UWG.js";
8
+ import "../chunk-M4I3FGZG.js";
17
9
  import "../chunk-FQDHFTVR.js";
18
- import "../chunk-X3W2Z5GC.js";
10
+ import "../chunk-UXXSE643.js";
11
+ import {
12
+ Money
13
+ } from "../chunk-FNU4CRJJ.js";
19
14
 
20
15
  // src/x402/fetch.ts
21
- var BASE64 = /^[A-Za-z0-9+/]*={0,2}$/;
22
- function belticFetch(source, inner = globalThis.fetch) {
23
- const run = source instanceof Session ? null : source;
16
+ import { z } from "zod";
17
+ var Base64Json = z.string().regex(/^[A-Za-z0-9+/]*={0,2}$/).transform((value, ctx) => {
18
+ try {
19
+ return JSON.parse(Buffer.from(value, "base64").toString("utf8"));
20
+ } catch {
21
+ ctx.addIssue({ code: "custom", message: "not base64 JSON" });
22
+ return z.NEVER;
23
+ }
24
+ });
25
+ var Accepts = z.looseObject({
26
+ payTo: z.string().optional().catch(void 0),
27
+ amount: z.string().optional().catch(void 0),
28
+ network: z.string().optional().catch(void 0),
29
+ asset: z.string().optional().catch(void 0)
30
+ });
31
+ var PaymentRequired = Base64Json.pipe(
32
+ z.looseObject({ accepts: z.array(Accepts).optional().catch(void 0) })
33
+ );
34
+ var PaymentPayload = Base64Json.pipe(
35
+ z.looseObject({
36
+ accepted: Accepts.optional().catch(void 0),
37
+ payload: z.record(z.string(), z.unknown()).optional().catch(void 0),
38
+ extensions: z.record(z.string(), z.unknown()).optional().catch(void 0)
39
+ })
40
+ );
41
+ function belticFetch(session, inner = globalThis.fetch) {
24
42
  return async (input, init) => {
25
- const session = await Sessions.resolve(source);
26
- if (!session) return inner(input, init);
43
+ const stream = await session.stream();
44
+ if (!stream) return inner(input, init);
27
45
  const headers = new Headers(
28
46
  init?.headers ?? (input instanceof Request ? input.headers : void 0)
29
47
  );
30
- headers.set(SESSION_HEADER, session.id);
31
- const signature = headers.get("PAYMENT-SIGNATURE");
32
- const payload = signature ? decodeHeader(signature) : null;
48
+ headers.set(SESSION_HEADER, stream.id);
49
+ const payload = PaymentPayload.safeParse(headers.get("PAYMENT-SIGNATURE")).data;
33
50
  if (payload) {
34
- const decision = run?.decisionFor(x402Moments.payload(payload));
35
- const decisionId = decision && !decision.absent ? decision.decisionId : null;
36
51
  const bound = {
37
52
  ...payload,
38
- extensions: {
39
- ...payload.extensions,
40
- [SESSION_EXTENSION]: session.id,
41
- ...decisionId ? { [DECISION_EXTENSION]: decisionId } : {}
42
- }
53
+ extensions: { ...payload.extensions, [SESSION_EXTENSION]: stream.id }
43
54
  };
44
55
  headers.set("PAYMENT-SIGNATURE", encodeHeader(bound));
45
- await session.emit("payment.presented", x402Moments.payload(bound));
46
- await session.flush();
56
+ await stream.emit("payment.presented", x402Moments.payload(bound));
57
+ await stream.flush();
47
58
  }
48
59
  const res = await inner(input, { ...init, headers });
49
60
  if (res.status !== 402) return res;
50
- const required = challengeOf(res);
51
- if (required) await session.emit("payment.requested", x402Moments.required(required));
61
+ const required = PaymentRequired.safeParse(res.headers.get("PAYMENT-REQUIRED")).data;
62
+ if (required) await stream.emit("payment.requested", x402Moments.required(required));
52
63
  return res;
53
64
  };
54
65
  }
55
- function decodeHeader(value) {
56
- if (!BASE64.test(value)) return null;
57
- try {
58
- const parsed = JSON.parse(Buffer.from(value, "base64").toString("utf8"));
59
- return parsed && typeof parsed === "object" ? parsed : null;
60
- } catch {
61
- return null;
62
- }
63
- }
64
66
  function encodeHeader(value) {
65
67
  return Buffer.from(JSON.stringify(value), "utf8").toString("base64");
66
68
  }
67
- function challengeOf(res) {
68
- const header = res.headers.get("PAYMENT-REQUIRED");
69
- return header ? decodeHeader(header) : null;
70
- }
71
69
 
72
70
  // src/x402/intent.ts
73
71
  function x402Intent(input) {
74
72
  return {
75
73
  mandate: input.mandate,
76
- maxAmount: {
77
- value: input.maxAmount.toString(),
78
- currency: x402Currency(input.network, input.asset)
79
- },
74
+ maxAmount: Money.x402(input.network, input.asset, input.maxAmount).toAmount(),
80
75
  validUntil: new Date(input.validUntil).toISOString(),
81
76
  ...input.merchantAllowlist ? { merchantAllowlist: input.merchantAllowlist } : {}
82
77
  };
83
78
  }
84
79
  export {
85
- DECISION_EXTENSION,
86
80
  SESSION_EXTENSION,
87
81
  SESSION_HEADER,
88
82
  attachX402,
89
83
  belticFetch,
90
- decisionIdOf,
91
- payerOf,
92
- sessionIdOf,
93
- x402Currency,
94
84
  x402Intent,
95
- x402Moments,
96
85
  x402Summary
97
86
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@belticlabs/agent-risk-sdk",
3
- "version": "0.5.0",
3
+ "version": "0.7.0",
4
4
  "description": "The Beltic Agent Risk SDK — one client, two halves: instrument the buyer agent (AI SDK, x402 fetch) and guard the seller boundary (x402 over hono, evaluate).",
5
5
  "license": "UNLICENSED",
6
6
  "repository": {
@@ -1,22 +0,0 @@
1
- import { D as Decision } from './verdict-DMnbFuS5.js';
2
- import { x402ResourceServer, x402HTTPResourceServer } from '@x402/core/server';
3
- import { B as Beltic, j as SessionBorn, i as Session } from './session-D9E-efc0.js';
4
-
5
- interface AttachOptions {
6
- /** Called with every decision; the default logs nothing. */
7
- onDecision?: ((d: {
8
- sessionId: string;
9
- decision: Decision;
10
- reasonCodes: string[];
11
- born: SessionBorn;
12
- /** The verdict the buyer says it obtained before presenting (GAP-80), unverified. */
13
- buyerDecisionId: string | null;
14
- }) => void) | undefined;
15
- }
16
- interface AttachedX402 {
17
- /** Sessions resolved at verify time, keyed by payment digest — for tests and settle hooks. */
18
- readonly inFlight: ReadonlyMap<string, Session>;
19
- }
20
- declare function attachX402(beltic: Beltic, server: x402ResourceServer, http?: x402HTTPResourceServer, opts?: AttachOptions): AttachedX402;
21
-
22
- export { type AttachOptions as A, attachX402 as a, type AttachedX402 as b };