@haven_ai/mcp 0.9.0-alpha.0 → 0.10.0-alpha.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
@@ -415,7 +415,7 @@ declare function createHavenMcpServer(options?: HavenMcpServerOptions): Promise<
415
415
  * `agent_tool_invocations` rows are always attributed to the right tool.
416
416
  */
417
417
  declare const MCP_NAME = "@haven_ai/mcp";
418
- declare const MCP_VERSION = "0.9.0-alpha.0";
418
+ declare const MCP_VERSION = "0.10.0-alpha.0";
419
419
  /**
420
420
  * Refuse to start on an unsupported Node (#1161).
421
421
  *
package/dist/index.d.ts CHANGED
@@ -415,7 +415,7 @@ declare function createHavenMcpServer(options?: HavenMcpServerOptions): Promise<
415
415
  * `agent_tool_invocations` rows are always attributed to the right tool.
416
416
  */
417
417
  declare const MCP_NAME = "@haven_ai/mcp";
418
- declare const MCP_VERSION = "0.9.0-alpha.0";
418
+ declare const MCP_VERSION = "0.10.0-alpha.0";
419
419
  /**
420
420
  * Refuse to start on an unsupported Node (#1161).
421
421
  *
package/dist/index.js CHANGED
@@ -1,6 +1,6 @@
1
1
  import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
2
2
  import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
3
- import { composeDescription, toolDescriptions as toolDescriptions$1, TASK_SIGN_CONTEXT_VERSION, connectorUpgradeCommand, HavenPaymentStateError, HavenSigningError, HavenApiError, AgentPaymentNextAction, HavenError, resolveTokenBySymbol, formatTokenAmount, HavenClient, havenClientIdentity, isSupportedNodeVersion, unsupportedNodeVersionMessage, verifyPaymentReceipt, discoverMerchantMcpUrl, sameUrl, AgentPaymentFailureCode, resolveTokenFromAddress } from '@haven_ai/sdk';
3
+ import { composeDescription, toolDescriptions as toolDescriptions$1, TASK_SIGN_CONTEXT_VERSION, connectorUpgradeCommand, HavenPaymentStateError, HavenSigningError, HavenApiError, AgentPaymentNextAction, HavenError, resolveTokenBySymbol, formatTokenAmount, HavenClient, havenClientIdentity, isSupportedNodeVersion, unsupportedNodeVersionMessage, verifyPaymentReceipt, catalogFundingLegExpected, discoverMerchantMcpUrl, sameUrl, AgentPaymentFailureCode, resolveTokenFromAddress } from '@haven_ai/sdk';
4
4
  import { readFile, stat, mkdir, writeFile } from 'fs/promises';
5
5
  import { z } from 'zod/v3';
6
6
  import { createHash } from 'crypto';
@@ -725,6 +725,10 @@ function createToolHandlers(haven) {
725
725
  price_atomic: entry.priceAtomic,
726
726
  asset: entry.asset,
727
727
  network: entry.network,
728
+ // #3839: same hint the hosted surface emits — a catalog hint, the
729
+ // live quote stays authoritative; "unknown" when nothing is recorded.
730
+ asset_transfer_methods: entry.assetTransferMethods ?? null,
731
+ funding_leg_expected: catalogFundingLegExpected(entry.assetTransferMethods),
728
732
  status: entry.status,
729
733
  verified_at: entry.verifiedAt,
730
734
  source: entry.source,
@@ -990,17 +994,26 @@ function parseMaybeJson(text) {
990
994
  return text;
991
995
  }
992
996
  }
997
+ var MERCHANT_OUT_OF_GAS_REASON = "settlement_wallet_out_of_gas";
998
+ function merchantOutOfGasMessage(settlementsRemaining, failFloor) {
999
+ const remaining = typeof settlementsRemaining === "number" ? settlementsRemaining : null;
1000
+ const floor = typeof failFloor === "number" ? failFloor : null;
1001
+ const figures = remaining !== null && floor !== null ? ` It has gas for ${remaining} more settlement${remaining === 1 ? "" : "s"} and refuses new payments below ${floor} (settlements_remaining: ${remaining}, fail_floor: ${floor}).` : remaining !== null ? ` settlements_remaining: ${remaining}.` : "";
1002
+ return `The merchant refused this call: its settlement wallet is out of gas (reason_code: ${MERCHANT_OUT_OF_GAS_REASON}).` + figures + " No payment was created. The merchant's operator must top up its settlement wallet; until then every retry is refused again. Tell the user, and re-quote once the merchant has been topped up.";
1003
+ }
993
1004
  var MerchantNotReadyError = class extends Error {
1005
+ constructor(message, nextToolOmittedReason = "the merchant needs to recover first; re-quote after the retry_after_s in the message") {
1006
+ super(message);
1007
+ this.nextToolOmittedReason = nextToolOmittedReason;
1008
+ this.name = "MerchantNotReadyError";
1009
+ }
1010
+ nextToolOmittedReason;
994
1011
  code = AgentPaymentFailureCode.MerchantNotReady;
995
1012
  statusCode = 503;
996
1013
  nextAction = AgentPaymentNextAction.StopAndTellUser;
997
1014
  // Genuinely retryable — unlike a rejection, nothing about THIS call was
998
1015
  // wrong; the merchant's own wallet needs to recover first.
999
1016
  retryWithNewQuote = true;
1000
- constructor(message) {
1001
- super(message);
1002
- this.name = "MerchantNotReadyError";
1003
- }
1004
1017
  };
1005
1018
  async function merchantNotReadyErrorFor(response) {
1006
1019
  if (response.status !== 503) return null;
@@ -1013,7 +1026,14 @@ async function merchantNotReadyErrorFor(response) {
1013
1026
  if (!body || typeof body !== "object" || body.error !== "merchant_not_ready") {
1014
1027
  return null;
1015
1028
  }
1016
- const { reason_code, settlements_remaining, retry_after_s } = body;
1029
+ const { reason_code, settlements_remaining, fail_floor, retry_after_s } = body;
1030
+ if (reason_code === MERCHANT_OUT_OF_GAS_REASON) {
1031
+ return new MerchantNotReadyError(
1032
+ merchantOutOfGasMessage(settlements_remaining, fail_floor),
1033
+ // Same reason the hosted runtime returns (support/mcp-context.ts).
1034
+ "the merchant's operator must top up its settlement wallet first; re-quote after that"
1035
+ );
1036
+ }
1017
1037
  return new MerchantNotReadyError(
1018
1038
  "The merchant refused this call: it cannot settle a payment right now" + (typeof reason_code === "string" ? ` (reason_code: ${reason_code})` : "") + (typeof settlements_remaining === "number" ? `, settlements_remaining: ${settlements_remaining}` : "") + ". No payment was created." + (typeof retry_after_s === "number" ? ` Retry after approximately ${retry_after_s}s.` : " This is often transient; retry later.")
1019
1039
  );
@@ -1034,8 +1054,10 @@ function normalizeError(err) {
1034
1054
  next_action: err.nextAction,
1035
1055
  retry_with_new_quote: err.retryWithNewQuote,
1036
1056
  // #3103: the local runtime's one decision site — no tool can act until
1037
- // the merchant recovers; the message carries retry_after_s.
1038
- next_tool_omitted_reason: "the merchant needs to recover first; re-quote after the retry_after_s in the message"
1057
+ // the merchant recovers. The reason rides the error (#3834): the
1058
+ // generic one points at the message's retry_after_s, the out-of-gas
1059
+ // one at the operator top-up.
1060
+ next_tool_omitted_reason: err.nextToolOmittedReason
1039
1061
  };
1040
1062
  }
1041
1063
  if (err instanceof HavenPaymentStateError) {
@@ -1321,7 +1343,7 @@ async function createHavenMcpServer(options = {}) {
1321
1343
  return buildMcpServer(haven);
1322
1344
  }
1323
1345
  var MCP_NAME = "@haven_ai/mcp";
1324
- var MCP_VERSION = "0.9.0-alpha.0";
1346
+ var MCP_VERSION = "0.10.0-alpha.0";
1325
1347
  var MCP_INSTRUCTIONS = [
1326
1348
  "Haven local MCP server: signs in-process with the delegate key it holds on",
1327
1349
  "this machine \u2014 the key never leaves this process. Call haven_get_agent",