@muhaven/mcp 0.2.8 → 0.3.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/dist/index.d.cts CHANGED
@@ -9,9 +9,46 @@ import { z } from 'zod';
9
9
  * (Windows). Each request is a single JSON object; each response is a
10
10
  * single JSON object. No request pipelining, no streaming.
11
11
  *
12
- * **Protocol version 0.4.0** — additive bump from 0.3.0 for Wave 5
13
- * Path D Slice 1. Adds the policy-snapshot subsystem so the broker can
14
- * enforce scope + per-op spend cap BEFORE signing a UserOp:
12
+ * **Protocol version 0.5.0** — additive bump from 0.4.0 for Wave 5
13
+ * Option D Commit 3. Adds the PermissionValidator install lifecycle so
14
+ * the broker can compose a MODE.ENABLE UserOp on the first Path D buy
15
+ * after a freshly-minted Scoped session (installs the validator on-chain
16
+ * atomically with the inner call). Three additive surfaces:
17
+ * - `current_nonce` — read-side IPC verb. Broker does `eth_call` against
18
+ * the kernel's `currentNonce()` view via its configured chain RPC.
19
+ * MCP server compares the returned uint32 with the mirror's stored
20
+ * `validatorNonce`; mismatch surfaces as fallback `enable_sig_stale`
21
+ * (kernel nonce drifted between mint + first buy → stored enableSig
22
+ * is over a stale typed-data digest).
23
+ * - `notify_userop_landed` — write-side IPC verb. MCP server invokes
24
+ * this after receipt-arrival to hand the broker the on-chain
25
+ * `PermissionInstalled` receipt details. Broker posts the receipt
26
+ * to the backend's `validator-enabled` route over its configured
27
+ * HTTPS egress (R2 design call: broker carries
28
+ * `BROKER_CALLBACK_SERVICE_SECRET`; MCP carries the bundler + RPC
29
+ * URLs only). Exponential backoff retry 5s/15s/60s/5m, max 1h.
30
+ * The backend chain indexer is the authoritative source-of-truth
31
+ * (subscribes to `PermissionInstalled` events independently); this
32
+ * callback is the fast-path optimization.
33
+ * - `PolicySnapshotWire` gains optional `enableData`, `enableSig`, and
34
+ * `validatorNonce`. Backwards-compatible: snapshots without these
35
+ * are treated as already-enabled validator (the legacy posture
36
+ * before C3). New snapshots from C2+ frontends carry all three;
37
+ * broker plumbs them through to the MCP for the MODE.ENABLE wrap.
38
+ *
39
+ * **Threat-model relaxation (R2 design call)**: in C3 the broker gains
40
+ * limited outbound egress (chain RPC `eth_call` + HTTPS to the
41
+ * backend's `validator-enabled` route). The original zero-egress
42
+ * invariant (lethal-trifecta split) is narrowed: the broker still
43
+ * holds NO read-side secrets the network peer cares about (the chain
44
+ * RPC is public; the backend callback is gated on a shared secret the
45
+ * broker holds + asserts in-bound). Documented in
46
+ * `development/DEV_WAVE_5/DEV_LOG.md` C3 entry as a load-bearing
47
+ * decision the operator made at handoff.
48
+ *
49
+ * **Protocol version 0.4.0** (history) — Wave 5 Path D Slice 1. Adds
50
+ * the policy-snapshot subsystem so the broker can enforce scope +
51
+ * per-op spend cap BEFORE signing a UserOp:
15
52
  * - `sign_userop` — like `sign_hash` but carries the structured inner
16
53
  * call (target + callData) so the broker validates against the active
17
54
  * policy snapshot before delegating to the signer. The MCP server
@@ -75,7 +112,7 @@ import { z } from 'zod';
75
112
  * - Requests are size-capped (`maxRequestBytes`) — a malformed peer
76
113
  * cannot exhaust broker memory by sending an unbounded JSON blob.
77
114
  */
78
- declare const BROKER_PROTOCOL_VERSION = "0.4.0";
115
+ declare const BROKER_PROTOCOL_VERSION = "0.5.0";
79
116
  interface BrokerHelloRequest {
80
117
  readonly type: 'hello';
81
118
  }
@@ -171,6 +208,60 @@ interface BrokerClearPolicySnapshotRequest {
171
208
  interface BrokerGetActiveSessionIdRequest {
172
209
  readonly type: 'get_active_session_id';
173
210
  }
211
+ /**
212
+ * Wave 5 Option D Commit 3 — read the kernel's `currentNonce()` view
213
+ * via the broker's chain RPC. The MCP server uses this to gate the
214
+ * MODE.ENABLE composition path: mirror's stored `validatorNonce` must
215
+ * still match the on-chain nonce (the enableSig was signed over the
216
+ * typed-data digest that pinned the nonce; if the kernel's nonce has
217
+ * advanced since mint, the digest no longer matches and the on-chain
218
+ * validator rejects the install).
219
+ *
220
+ * Returns a uint32. Broker daemon enforces the range; MCP-side caller
221
+ * compares to the mirror's stored value as a numeric equality check.
222
+ */
223
+ interface BrokerCurrentNonceRequest {
224
+ readonly type: 'current_nonce';
225
+ /** Kernel/smart-account address. The kernel's `currentNonce()` is
226
+ * a view-only method on the account itself (not the EntryPoint). */
227
+ readonly accountAddress: `0x${string}`;
228
+ }
229
+ /**
230
+ * Wave 5 Option D Commit 3 — MCP server notifies broker that a
231
+ * MODE.ENABLE UserOp has settled on-chain. Broker forwards the receipt
232
+ * to the backend's `validator-enabled` route over HTTPS (using its
233
+ * pre-configured `BROKER_CALLBACK_SERVICE_SECRET` + `BROKER_BACKEND_BASE_URL`).
234
+ *
235
+ * The IPC return is FIRE-AND-FORGET: the broker queues the callback +
236
+ * acks immediately. The retry loop (5s/15s/60s/5m, max 1h)
237
+ * runs in the broker's background; failures are operator-visible via
238
+ * the daemon's log channel only (the MCP server does not block on
239
+ * the broker's egress).
240
+ *
241
+ * Idempotent on the chain-indexer side — the backend route re-verifies
242
+ * the receipt; the chain indexer is the authoritative source of truth.
243
+ */
244
+ interface BrokerNotifyUseropLandedRequest {
245
+ readonly type: 'notify_userop_landed';
246
+ readonly sessionId: string;
247
+ /** Address of the kernel that owns the installed PermissionValidator.
248
+ * Backend uses (account_address, permission_id) to look up the mirror
249
+ * row to flip. */
250
+ readonly accountAddress: `0x${string}`;
251
+ /** 0x-prefixed 4-byte permissionId, lower-cased. */
252
+ readonly permissionId: `0x${string}`;
253
+ /** Tx hash carrying the install. Backend re-verifies via
254
+ * `eth_getTransactionReceipt` before flipping the enum. */
255
+ readonly txHash: `0x${string}`;
256
+ /** Block number containing the receipt — telemetry / forensics. */
257
+ readonly blockNumber: number;
258
+ /** Log index of the matched `SelectorSet` install event within the
259
+ * tx's logs array. INFORMATIONAL only — the backend re-scans the FULL
260
+ * receipt and matches by permissionId, so a wrong/0 logIndex is
261
+ * harmless (the deployed kernel emits `SelectorSet`, not
262
+ * `PermissionInstalled`, for enable-mode installs). */
263
+ readonly logIndex: number;
264
+ }
174
265
  /**
175
266
  * Per-selector enforcement rule. The broker matches `innerCall`'s
176
267
  * selector against `selector`, then — if `capArgIndex` is not null —
@@ -274,6 +365,31 @@ interface PolicySnapshotWire {
274
365
  * (additive optional field, no protocol version bump).
275
366
  */
276
367
  readonly permissionId?: `0x${string}`;
368
+ /**
369
+ * Wave 5 Option D Commit 3 — install material for the MODE.ENABLE
370
+ * UserOp. `enableData` is the validator-install payload built by the
371
+ * frontend at mint time (`permissionValidator.getEnableData(...)`).
372
+ * Variable size — real-world Wave 5 policy sets produce ~30KB hex.
373
+ * Optional in the wire shape; absence = treat as already-enabled
374
+ * (legacy posture; MCP composes MODE.DEFAULT directly).
375
+ */
376
+ readonly enableData?: `0x${string}`;
377
+ /**
378
+ * Wave 5 Option D Commit 3 — WebAuthn-shaped passkey signature over
379
+ * `getPluginsEnableTypedData(...)`. 256-1024 bytes hex; ZeroDev's
380
+ * passkey-validator emits a structured envelope (NOT a bare 65-byte
381
+ * ECDSA). Optional; paired with `enableData` (both present or both
382
+ * absent — broker daemon enforces; see `parsePolicySnapshot`).
383
+ */
384
+ readonly enableSig?: `0x${string}`;
385
+ /**
386
+ * Wave 5 Option D Commit 3 — `currentNonce()` value the kernel
387
+ * returned at mint time. The MCP server's broker pre-check compares
388
+ * this to the LIVE on-chain nonce (via the broker's new
389
+ * `current_nonce` IPC verb) — mismatch surfaces as fallback
390
+ * `enable_sig_stale`. Optional; uint32 range.
391
+ */
392
+ readonly validatorNonce?: number;
277
393
  }
278
394
  interface BrokerHelloResponse {
279
395
  readonly type: 'hello';
@@ -371,14 +487,39 @@ interface BrokerGetActiveSessionIdResponse {
371
487
  * in either case. */
372
488
  readonly sessionId: string | null;
373
489
  }
490
+ interface BrokerCurrentNonceResponse {
491
+ readonly type: 'current_nonce';
492
+ /** uint32 returned by the kernel's `currentNonce()` view. */
493
+ readonly nonce: number;
494
+ /** Mirror of the request — defends against the broker accidentally
495
+ * serving a cached response for a different account. The caller
496
+ * compares this to its request input before trusting `nonce`. */
497
+ readonly accountAddress: `0x${string}`;
498
+ }
499
+ interface BrokerNotifyUseropLandedResponse {
500
+ readonly type: 'notify_userop_landed';
501
+ /** Always `true` once the callback is queued. The broker queues
502
+ * fire-and-forget; failures surface in the broker's log channel
503
+ * only. */
504
+ readonly queued: true;
505
+ readonly sessionId: string;
506
+ }
374
507
  interface BrokerErrorResponse {
375
508
  readonly type: 'error';
376
509
  readonly code: BrokerErrorCode;
377
510
  readonly message: string;
378
511
  }
379
- type BrokerErrorCode = 'invalid_request' | 'payload_too_large' | 'unsupported_type' | 'internal' | 'forbidden' | 'keystore_unavailable' | 'session_key_unavailable' | 'no_active_snapshot' | 'policy_violation' | 'scope_violation' | 'max_spend_exceeded' | 'rate_limited';
380
- type BrokerRequest = BrokerHelloRequest | BrokerSignHashRequest | BrokerStoreJwtRequest | BrokerGetJwtRequest | BrokerClearJwtRequest | BrokerSignUserOpRequest | BrokerStorePolicySnapshotRequest | BrokerGetPolicySnapshotRequest | BrokerClearPolicySnapshotRequest | BrokerGetActiveSessionIdRequest;
381
- type BrokerResponse = BrokerHelloResponse | BrokerSignHashResponse | BrokerStoreJwtResponse | BrokerGetJwtResponse | BrokerClearJwtResponse | BrokerSignUserOpResponse | BrokerStorePolicySnapshotResponse | BrokerGetPolicySnapshotResponse | BrokerClearPolicySnapshotResponse | BrokerGetActiveSessionIdResponse | BrokerErrorResponse;
512
+ type BrokerErrorCode = 'invalid_request' | 'payload_too_large' | 'unsupported_type' | 'internal' | 'forbidden' | 'keystore_unavailable' | 'session_key_unavailable' | 'no_active_snapshot' | 'policy_violation' | 'scope_violation' | 'max_spend_exceeded' | 'rate_limited'
513
+ /** Broker's chain RPC `eth_call` failed (network, malformed reply,
514
+ * RPC error). MCP-side caller falls back to Path C with a clear
515
+ * "broker chain RPC unreachable" remediation message. */
516
+ | 'chain_rpc_failed'
517
+ /** Broker hasn't been configured with the callback secret or backend
518
+ * base URL — `notify_userop_landed` is a no-op IPC verb in this
519
+ * posture (the chain indexer remains the safety net). */
520
+ | 'callback_unconfigured';
521
+ type BrokerRequest = BrokerHelloRequest | BrokerSignHashRequest | BrokerStoreJwtRequest | BrokerGetJwtRequest | BrokerClearJwtRequest | BrokerSignUserOpRequest | BrokerStorePolicySnapshotRequest | BrokerGetPolicySnapshotRequest | BrokerClearPolicySnapshotRequest | BrokerGetActiveSessionIdRequest | BrokerCurrentNonceRequest | BrokerNotifyUseropLandedRequest;
522
+ type BrokerResponse = BrokerHelloResponse | BrokerSignHashResponse | BrokerStoreJwtResponse | BrokerGetJwtResponse | BrokerClearJwtResponse | BrokerSignUserOpResponse | BrokerStorePolicySnapshotResponse | BrokerGetPolicySnapshotResponse | BrokerClearPolicySnapshotResponse | BrokerGetActiveSessionIdResponse | BrokerCurrentNonceResponse | BrokerNotifyUseropLandedResponse | BrokerErrorResponse;
382
523
  /**
383
524
  * Parse a single-line request payload. Returns either the validated
384
525
  * request or a structured error — the daemon converts errors to a
@@ -508,6 +649,15 @@ declare class BrokerClient {
508
649
  getPolicySnapshot(sessionId: string): Promise<BrokerGetPolicySnapshotResponse>;
509
650
  clearPolicySnapshot(sessionId: string): Promise<BrokerClearPolicySnapshotResponse>;
510
651
  getActiveSessionId(): Promise<BrokerGetActiveSessionIdResponse>;
652
+ currentNonce(accountAddress: `0x${string}`): Promise<BrokerCurrentNonceResponse>;
653
+ notifyUseropLanded(args: {
654
+ sessionId: string;
655
+ accountAddress: `0x${string}`;
656
+ permissionId: `0x${string}`;
657
+ txHash: `0x${string}`;
658
+ blockNumber: number;
659
+ logIndex: number;
660
+ }): Promise<BrokerNotifyUseropLandedResponse>;
511
661
  /**
512
662
  * Detect whether the running daemon speaks Path D (protocol 0.4.0+).
513
663
  * Wraps `hello()` with a semver-gte comparison so the MCP tool layer
@@ -618,6 +768,7 @@ declare class BackendClient {
618
768
  private buildUrl;
619
769
  private exchangeWithRetry;
620
770
  private exchange;
771
+ private runFetch;
621
772
  }
622
773
 
623
774
  /**
@@ -1275,6 +1426,38 @@ interface BrokerRuntimeConfig {
1275
1426
  backendBaseUrl: string;
1276
1427
  /** Effective dashboard URL paired with backendBaseUrl. */
1277
1428
  dashboardBaseUrl: string;
1429
+ /**
1430
+ * Wave 5 Option D Commit 3 — chain RPC URL the broker uses to read
1431
+ * `kernel.currentNonce()` via `eth_call` during the MODE.ENABLE
1432
+ * pre-check. Optional: when undefined, `current_nonce` IPC returns
1433
+ * `chain_rpc_failed`. Defaults from `MUHAVEN_BROKER_RPC_URL` (broker-
1434
+ * specific) with fallback to `MUHAVEN_BUNDLER_URL` (shared with the
1435
+ * MCP server; ZeroDev bundlers also serve `eth_call`). Operator can
1436
+ * pin a dedicated read-only RPC via `MUHAVEN_BROKER_RPC_URL` to keep
1437
+ * the broker's egress surface narrower than the MCP server's.
1438
+ *
1439
+ * NOTE: this is the first network-egress capability the broker has
1440
+ * been given — see protocol.ts JSDoc on the threat-model relaxation.
1441
+ */
1442
+ chainRpcUrl?: string;
1443
+ /**
1444
+ * Wave 5 Option D Commit 3 — service secret the broker uses to POST
1445
+ * to the backend's `validator-enabled` route. Optional: when
1446
+ * undefined, `notify_userop_landed` returns `callback_unconfigured`
1447
+ * (chain indexer is still the authoritative safety net).
1448
+ *
1449
+ * Sourced from `BROKER_CALLBACK_SERVICE_SECRET`. Held by the broker
1450
+ * (not the MCP server) to keep the secret outside the LLM-controlled
1451
+ * subprocess.
1452
+ */
1453
+ callbackServiceSecret?: string;
1454
+ /**
1455
+ * Wave 5 Option D Commit 3 — `Origin` header the broker stamps on
1456
+ * outbound bundler / RPC calls. ZeroDev bundlers reject bare Node
1457
+ * fetches with 403 (per [[feedback-zerodev-bundler-origin-header]]).
1458
+ * Defaults to `dashboardBaseUrl`.
1459
+ */
1460
+ outboundOriginHeader?: string;
1278
1461
  }
1279
1462
  /**
1280
1463
  * Compute the default IPC endpoint for the broker. POSIX: a socket file
@@ -1560,17 +1743,114 @@ interface IPolicyStore {
1560
1743
  init?(): Promise<void>;
1561
1744
  }
1562
1745
 
1746
+ interface OutboundConfig {
1747
+ readonly chainRpcUrl?: string;
1748
+ readonly backendBaseUrl: string;
1749
+ readonly callbackServiceSecret?: string;
1750
+ /** Origin header stamped on outbound bundler / RPC calls. */
1751
+ readonly outboundOriginHeader: string;
1752
+ /** Per-fetch timeout in ms. Defaults to 15s. */
1753
+ readonly fetchTimeoutMs?: number;
1754
+ /**
1755
+ * Injectable fetch impl for tests. Defaults to global `fetch`. The
1756
+ * shape matches the standard Fetch API — no node-specific quirks.
1757
+ */
1758
+ readonly fetchImpl?: typeof fetch;
1759
+ /**
1760
+ * Setter/clearer for the retry timer. Tests inject a fake-timer
1761
+ * pair so they can advance virtual time without `await new
1762
+ * Promise(setTimeout)`. Production passes Node's globals.
1763
+ */
1764
+ readonly setTimeout?: typeof setTimeout;
1765
+ readonly clearTimeout?: typeof clearTimeout;
1766
+ }
1767
+ declare class BrokerOutbound {
1768
+ private readonly config;
1769
+ private readonly log;
1770
+ private readonly fetchImpl;
1771
+ private readonly fetchTimeoutMs;
1772
+ private readonly setTimeoutImpl;
1773
+ private readonly clearTimeoutImpl;
1774
+ /**
1775
+ * Wave 5 Option D Commit 3 (multi-agent review SecEng-MED-3) —
1776
+ * in-process dedup of `notify_userop_landed` callbacks. Map of
1777
+ * `<sessionId>:<txHash>` → the in-flight retry loop's Promise.
1778
+ * Repeated IPC calls with the same key fold into the existing
1779
+ * loop instead of spawning a parallel POST. Defends against a
1780
+ * local-socket peer flooding the broker with replay attempts +
1781
+ * caps the retry-budget waste at one loop per real install.
1782
+ */
1783
+ private readonly inflightCallbacks;
1784
+ constructor(config: OutboundConfig, log?: (level: 'info' | 'warn' | 'error', msg: string, meta?: Record<string, unknown>) => void);
1785
+ /**
1786
+ * Read the kernel's `currentNonce()` view via `eth_call` against the
1787
+ * configured chain RPC. Returns a uint32. Throws `ChainRpcError` when
1788
+ * unconfigured / network failed / RPC returned non-decodable bytes.
1789
+ */
1790
+ currentNonce(accountAddress: `0x${string}`): Promise<number>;
1791
+ /**
1792
+ * Whether the callback path is wired (both secret + backend URL set).
1793
+ * The `notify_userop_landed` daemon handler checks this and returns
1794
+ * `callback_unconfigured` when false so the operator sees the gap.
1795
+ */
1796
+ isCallbackConfigured(): boolean;
1797
+ /**
1798
+ * Queue a `validator-enabled` callback POST to the backend. Returns
1799
+ * immediately; the retry loop runs in the background (5s / 15s / 60s
1800
+ * / 5m, max 1h elapsed). Failures are logged but do NOT propagate to
1801
+ * the IPC caller — the chain indexer is the authoritative safety
1802
+ * net.
1803
+ *
1804
+ * Idempotency: every POST carries an `Idempotency-Key` header
1805
+ * `<sessionId>:validator-enabled`. The backend route is no-op if the
1806
+ * mirror row's `enable_status` is already `'enabled'` (because the
1807
+ * chain indexer raced ahead).
1808
+ *
1809
+ * Returns a Promise resolved when the loop terminates (success or
1810
+ * max-elapsed). Callers don't need to await; tests use it for
1811
+ * deterministic assertions.
1812
+ */
1813
+ enqueueValidatorEnabledCallback(args: {
1814
+ readonly sessionId: string;
1815
+ readonly userId?: string;
1816
+ readonly accountAddress: `0x${string}`;
1817
+ readonly permissionId: `0x${string}`;
1818
+ readonly txHash: `0x${string}`;
1819
+ readonly blockNumber: number;
1820
+ readonly logIndex: number;
1821
+ }): Promise<{
1822
+ ok: boolean;
1823
+ attempts: number;
1824
+ lastError?: string;
1825
+ }>;
1826
+ private runCallbackLoop;
1827
+ private postCallback;
1828
+ private sleep;
1829
+ }
1830
+
1563
1831
  /**
1564
1832
  * `muhaven-broker` daemon — the single-purpose process that holds the
1565
- * session-key private half AND the device-flow JWT, exposing only IPC
1566
- * primitives for `sign_hash` + `store_jwt` / `get_jwt` / `clear_jwt`.
1833
+ * session-key private half AND the device-flow JWT, exposing IPC
1834
+ * primitives for `sign_hash` + `store_jwt` / `get_jwt` / `clear_jwt` +
1835
+ * the Wave 5 Path D policy + UserOp signing surface.
1567
1836
  *
1568
1837
  * Design constraints (ranked):
1569
1838
  * 1. Never speak TCP. Reachable only via local socket / named pipe.
1570
- * 2. Never reach out to the network. No fetch, no RPC, no bundler —
1571
- * even after ADR-3 the broker remains zero-egress; the *MCP server*
1572
- * speaks HTTPS to the backend and hands the JWT to the broker for
1573
- * storage via `store_jwt`.
1839
+ * 2. **Outbound network egress is NARROW (Wave 5 Option D Commit 3
1840
+ * relaxation, operator-approved at handoff)**. The broker has
1841
+ * EXACTLY two outbound channels both via the `BrokerOutbound`
1842
+ * module (`./outbound.ts`):
1843
+ * (a) chain RPC `eth_call` to the configured `MUHAVEN_BROKER_RPC_URL`
1844
+ * (fallback `MUHAVEN_BUNDLER_URL`) for `kernel.currentNonce()`
1845
+ * reads, gating the MODE.ENABLE pre-check;
1846
+ * (b) HTTPS POST to the backend's `validator-enabled` route,
1847
+ * gated by `BROKER_CALLBACK_SERVICE_SECRET`.
1848
+ * NO other outbound capability. NO bundler `eth_sendUserOperation`,
1849
+ * NO `eth_call` against non-`currentNonce` selectors, NO non-
1850
+ * backend HTTPS destinations. The JWT keystore + the IPC-mediated
1851
+ * `sign_hash` / `sign_userop` paths remain zero-egress.
1852
+ * See `./protocol.ts` JSDoc (top) for the threat-model rationale
1853
+ * + `./outbound.ts` JSDoc (top) for the per-channel contracts.
1574
1854
  * 3. Peer access is enforced by filesystem permissions on POSIX (parent
1575
1855
  * dir 0700 / socket file 0600). Windows named pipe inherits the
1576
1856
  * creating user's ACL by default.
@@ -1595,6 +1875,12 @@ interface BrokerDaemonOptions {
1595
1875
  * verbs added in Wave 5 Path D Slice 1 (protocol 0.4.0).
1596
1876
  */
1597
1877
  policyStore?: IPolicyStore;
1878
+ /**
1879
+ * Wave 5 Option D Commit 3 — inject the outbound module for tests.
1880
+ * Production builds one from `config.chainRpcUrl` +
1881
+ * `config.callbackServiceSecret` at constructor time.
1882
+ */
1883
+ outbound?: BrokerOutbound;
1598
1884
  /** Override for the connection-handler logger; defaults to silent. */
1599
1885
  logger?: (event: BrokerLogEvent) => void;
1600
1886
  }
@@ -1634,7 +1920,7 @@ interface HandleBrokerRequestOptions {
1634
1920
  */
1635
1921
  pid?: number;
1636
1922
  }
1637
- declare function handleBrokerRequest(req: BrokerRequest, signer: ISigner, keystore: IKeystore, nowSec?: () => number, options?: HandleBrokerRequestOptions, policyStore?: IPolicyStore): Promise<BrokerResponse>;
1923
+ declare function handleBrokerRequest(req: BrokerRequest, signer: ISigner, keystore: IKeystore, nowSec?: () => number, options?: HandleBrokerRequestOptions, policyStore?: IPolicyStore, outbound?: BrokerOutbound): Promise<BrokerResponse>;
1638
1924
  declare class BrokerDaemon {
1639
1925
  private readonly server;
1640
1926
  private readonly signer;
@@ -1642,6 +1928,7 @@ declare class BrokerDaemon {
1642
1928
  private readonly config;
1643
1929
  private keystore;
1644
1930
  private readonly policyStore;
1931
+ private readonly outbound;
1645
1932
  /**
1646
1933
  * Whether a session-key private half is actually loaded. `false` =
1647
1934
  * daemon booted in read-only posture (no `MUHAVEN_BROKER_SESSION_KEY`