@haven_ai/connect 0.1.16-alpha.0 → 0.1.18-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
@@ -245,6 +245,14 @@ interface RuntimeInstallDeps {
245
245
  env?: NodeJS.ProcessEnv;
246
246
  homeDir?: string;
247
247
  fetch?: typeof fetch;
248
+ /**
249
+ * Optional live progress callback. installRuntime's slowest steps (signer
250
+ * pre-install, runtime config write, MCP handshake probes) otherwise emit
251
+ * nothing until the caller flushes the collected `messages` after this
252
+ * returns — leaving the console silent through the longest part of setup.
253
+ * When provided, a few lightweight heartbeat lines are emitted as they run.
254
+ */
255
+ onProgress?: (message: string) => void;
248
256
  runCommand?: (command: string, args: string[]) => Promise<void>;
249
257
  prepareLocalMcpRuntime?: (input: PrepareLocalMcpRuntimeInput) => Promise<PreparedLocalMcpRuntime>;
250
258
  prepareSignerRuntime?: (input: PrepareSignerRuntimeInput) => Promise<PreparedSignerRuntime>;
@@ -256,7 +264,7 @@ declare function runtimeInstallCapabilities(runtime: string | undefined, env?: N
256
264
  restartRequired: boolean;
257
265
  };
258
266
 
259
- declare const CONNECTOR_VERSION = "0.1.16-alpha.0";
267
+ declare const CONNECTOR_VERSION = "0.1.18-alpha.0";
260
268
  interface ConnectOptions {
261
269
  setupToken: string;
262
270
  apiBaseUrl: string;
@@ -297,11 +305,11 @@ declare function shortAddress(address: string): string;
297
305
 
298
306
  declare const MCP_RUNTIME_MANIFEST: {
299
307
  readonly mcpPackage: "@haven_ai/mcp";
300
- readonly mcpVersion: "0.1.16-alpha.0";
308
+ readonly mcpVersion: "0.1.18-alpha.0";
301
309
  readonly sdkPackage: "@haven_ai/sdk";
302
- readonly sdkVersion: "0.1.16-alpha.0";
310
+ readonly sdkVersion: "0.1.18-alpha.0";
303
311
  readonly signerPackage: "@haven_ai/signer";
304
- readonly signerVersion: "0.1.16-alpha.0";
312
+ readonly signerVersion: "0.1.18-alpha.0";
305
313
  readonly minimumNodeVersion: "20.0.0";
306
314
  readonly supportedClients: readonly ["codex-cli", "codex-desktop", "claude-code"];
307
315
  readonly requiredTools: readonly string[];
package/dist/index.d.ts CHANGED
@@ -245,6 +245,14 @@ interface RuntimeInstallDeps {
245
245
  env?: NodeJS.ProcessEnv;
246
246
  homeDir?: string;
247
247
  fetch?: typeof fetch;
248
+ /**
249
+ * Optional live progress callback. installRuntime's slowest steps (signer
250
+ * pre-install, runtime config write, MCP handshake probes) otherwise emit
251
+ * nothing until the caller flushes the collected `messages` after this
252
+ * returns — leaving the console silent through the longest part of setup.
253
+ * When provided, a few lightweight heartbeat lines are emitted as they run.
254
+ */
255
+ onProgress?: (message: string) => void;
248
256
  runCommand?: (command: string, args: string[]) => Promise<void>;
249
257
  prepareLocalMcpRuntime?: (input: PrepareLocalMcpRuntimeInput) => Promise<PreparedLocalMcpRuntime>;
250
258
  prepareSignerRuntime?: (input: PrepareSignerRuntimeInput) => Promise<PreparedSignerRuntime>;
@@ -256,7 +264,7 @@ declare function runtimeInstallCapabilities(runtime: string | undefined, env?: N
256
264
  restartRequired: boolean;
257
265
  };
258
266
 
259
- declare const CONNECTOR_VERSION = "0.1.16-alpha.0";
267
+ declare const CONNECTOR_VERSION = "0.1.18-alpha.0";
260
268
  interface ConnectOptions {
261
269
  setupToken: string;
262
270
  apiBaseUrl: string;
@@ -297,11 +305,11 @@ declare function shortAddress(address: string): string;
297
305
 
298
306
  declare const MCP_RUNTIME_MANIFEST: {
299
307
  readonly mcpPackage: "@haven_ai/mcp";
300
- readonly mcpVersion: "0.1.16-alpha.0";
308
+ readonly mcpVersion: "0.1.18-alpha.0";
301
309
  readonly sdkPackage: "@haven_ai/sdk";
302
- readonly sdkVersion: "0.1.16-alpha.0";
310
+ readonly sdkVersion: "0.1.18-alpha.0";
303
311
  readonly signerPackage: "@haven_ai/signer";
304
- readonly signerVersion: "0.1.16-alpha.0";
312
+ readonly signerVersion: "0.1.18-alpha.0";
305
313
  readonly minimumNodeVersion: "20.0.0";
306
314
  readonly supportedClients: readonly ["codex-cli", "codex-desktop", "claude-code"];
307
315
  readonly requiredTools: readonly string[];
package/dist/index.js CHANGED
@@ -229,9 +229,9 @@ var MCP_RUNTIME_MANIFEST = {
229
229
  mcpPackage: "@haven_ai/mcp",
230
230
  mcpVersion: MCP_VERSION,
231
231
  sdkPackage: "@haven_ai/sdk",
232
- sdkVersion: "0.1.16-alpha.0",
232
+ sdkVersion: "0.1.18-alpha.0",
233
233
  signerPackage: "@haven_ai/signer",
234
- signerVersion: "0.1.16-alpha.0",
234
+ signerVersion: "0.1.18-alpha.0",
235
235
  minimumNodeVersion: "20.0.0",
236
236
  supportedClients: ["codex-cli", "codex-desktop", "claude-code"],
237
237
  requiredTools: registeredToolNames()
@@ -246,117 +246,6 @@ function signerPackageSpec() {
246
246
  return `${MCP_RUNTIME_MANIFEST.signerPackage}@${MCP_RUNTIME_MANIFEST.signerVersion}`;
247
247
  }
248
248
 
249
- // src/runtime-registry.ts
250
- var RUNTIME_PROFILES = {
251
- "claude-code": {
252
- id: "claude-code",
253
- label: "Claude Code",
254
- restartMode: "restart-session",
255
- canWriteRuntimeConfig: true
256
- },
257
- "codex-cli": {
258
- id: "codex-cli",
259
- label: "Codex CLI",
260
- restartMode: "restart-session",
261
- canWriteRuntimeConfig: true
262
- },
263
- "codex-desktop": {
264
- id: "codex-desktop",
265
- label: "Codex Desktop",
266
- restartMode: "restart-session",
267
- canWriteRuntimeConfig: true
268
- },
269
- cursor: {
270
- id: "cursor",
271
- label: "Cursor",
272
- restartMode: "hot-reload",
273
- canWriteRuntimeConfig: true
274
- },
275
- vscode: {
276
- id: "vscode",
277
- label: "VS Code",
278
- restartMode: "hot-reload",
279
- canWriteRuntimeConfig: true
280
- },
281
- "vscode-insiders": {
282
- id: "vscode-insiders",
283
- label: "VS Code Insiders",
284
- restartMode: "hot-reload",
285
- canWriteRuntimeConfig: true
286
- },
287
- "claude-desktop": {
288
- id: "claude-desktop",
289
- label: "Claude Desktop",
290
- restartMode: "restart-app",
291
- canWriteRuntimeConfig: true
292
- },
293
- other: {
294
- id: "other",
295
- label: "Other agent runtime",
296
- restartMode: "manual",
297
- canWriteRuntimeConfig: false
298
- }
299
- };
300
- var RUNTIME_ALIASES = {
301
- claude: "claude-code",
302
- "claude-code": "claude-code",
303
- claudecode: "claude-code",
304
- "claude_code": "claude-code",
305
- codex: "codex-cli",
306
- "codex-cli": "codex-cli",
307
- codexcli: "codex-cli",
308
- "codex_cli": "codex-cli",
309
- "codex-desktop": "codex-desktop",
310
- "codex_desktop": "codex-desktop",
311
- codexdesktop: "codex-desktop",
312
- "codex-app": "codex-desktop",
313
- "codex_app": "codex-desktop",
314
- codexapp: "codex-desktop",
315
- cursor: "cursor",
316
- vscode: "vscode",
317
- "vs-code": "vscode",
318
- "vs_code": "vscode",
319
- code: "vscode",
320
- "vscode-insiders": "vscode-insiders",
321
- "vscode_insiders": "vscode-insiders",
322
- vscodeinsiders: "vscode-insiders",
323
- "vs-code-insiders": "vscode-insiders",
324
- "code-insiders": "vscode-insiders",
325
- insiders: "vscode-insiders",
326
- "claude-desktop": "claude-desktop",
327
- "claude_desktop": "claude-desktop",
328
- claudesktop: "claude-desktop",
329
- desktop: "claude-desktop",
330
- other: "other",
331
- manual: "other"
332
- };
333
- function runtimeProfile(runtime, env = process.env) {
334
- return RUNTIME_PROFILES[normalizeRuntime(runtime, env)];
335
- }
336
- function normalizeRuntime(runtime, env = process.env) {
337
- const explicit = normalizeRuntimeName(runtime);
338
- if (explicit) return explicit;
339
- return detectRuntime(env) ?? "other";
340
- }
341
- function restartRequiredForRuntime(runtime, env = process.env) {
342
- const mode = runtimeProfile(runtime, env).restartMode;
343
- return mode === "restart-session" || mode === "restart-app";
344
- }
345
- function runtimeRequiresHardRestart(runtime) {
346
- return runtime === "claude-desktop" || runtime === "codex-desktop";
347
- }
348
- function normalizeRuntimeName(runtime) {
349
- const key = runtime?.trim().toLowerCase();
350
- if (!key) return null;
351
- return RUNTIME_ALIASES[key.replace(/\s+/g, "-")] ?? null;
352
- }
353
- function detectRuntime(env) {
354
- if (env.CLAUDECODE || env.CLAUDE_CODE || env.CLAUDECODE_CWD) return "claude-code";
355
- if (env.CODEX_SANDBOX || env.CODEX_HOME || env.CODEX_CWD) return "codex-cli";
356
- if (env.VSCODE_CWD || env.VSCODE_IPC_HOOK_CLI || env.TERM_PROGRAM === "vscode") return "vscode";
357
- return null;
358
- }
359
-
360
249
  // src/config-writers.ts
361
250
  var InvalidCodexTomlError = class extends Error {
362
251
  constructor(message) {
@@ -503,7 +392,6 @@ async function writeJsonRuntimeConfig(input, target, serverRoot) {
503
392
  async function writeCodexConfig(input) {
504
393
  const target = codexConfigPath(input.homeDir);
505
394
  const local = input.mode === "local";
506
- const restartMessage = runtimeRequiresHardRestart(input.runtime) ? "After Haven approval, restart Codex Desktop so it can load Haven tools." : "After Haven approval, Haven tools should appear in your next Codex message. If they don't, restart Codex to load them.";
507
395
  try {
508
396
  const existing = await readOptional(target);
509
397
  if (local) {
@@ -521,11 +409,7 @@ async function writeCodexConfig(input) {
521
409
  changed: existing !== merged2,
522
410
  restartRequired: true,
523
411
  messages: [
524
- `Updated local Haven MCP entry in ${configTargetLabel(input.runtime)}.`,
525
- // Codex Desktop loads MCP servers at app launch; Codex CLI typically
526
- // picks them up in the next session. Branch the copy so desktop users
527
- // get the unambiguous instruction.
528
- restartMessage
412
+ `Updated local Haven MCP entry in ${configTargetLabel(input.runtime)}.`
529
413
  ]
530
414
  };
531
415
  }
@@ -540,8 +424,7 @@ async function writeCodexConfig(input) {
540
424
  changed: existing !== merged,
541
425
  restartRequired: true,
542
426
  messages: [
543
- `Updated Haven MCP entries in ${configTargetLabel(input.runtime)}.`,
544
- restartMessage
427
+ `Updated Haven MCP entries in ${configTargetLabel(input.runtime)}.`
545
428
  ]
546
429
  };
547
430
  } catch (err) {
@@ -1094,23 +977,29 @@ function parseNodeVersion(value) {
1094
977
  ];
1095
978
  }
1096
979
  async function installRuntimePackages(runtimeDirectory, npmCacheDirectory, runCommand) {
1097
- const args = [
980
+ const baseArgs = [
1098
981
  "install",
1099
982
  "--prefix",
1100
983
  runtimeDirectory,
1101
- "--cache",
1102
- npmCacheDirectory,
1103
984
  "--no-audit",
1104
985
  "--no-fund",
1105
986
  "--omit=dev",
987
+ "--prefer-offline",
1106
988
  mcpPackageSpec(),
1107
989
  sdkPackageSpec()
1108
990
  ];
1109
- try {
991
+ const run = async (args) => {
1110
992
  if (runCommand) await runCommand("npm", args);
1111
993
  else await execFileAsync("npm", args, { timeout: 12e4, maxBuffer: 1024 * 1024 });
1112
- } catch (err) {
1113
- throw new Error(`Could not install local Haven MCP runtime ${mcpPackageSpec()}: ${err instanceof Error ? err.message : String(err)}`);
994
+ };
995
+ try {
996
+ await run(baseArgs);
997
+ } catch {
998
+ try {
999
+ await run([...baseArgs, "--cache", npmCacheDirectory]);
1000
+ } catch (err) {
1001
+ throw new Error(`Could not install local Haven MCP runtime ${mcpPackageSpec()}: ${err instanceof Error ? err.message : String(err)}`);
1002
+ }
1114
1003
  }
1115
1004
  }
1116
1005
  async function installedRuntimeMatches(runtimeDirectory, cliPath) {
@@ -1214,25 +1103,31 @@ async function prepareSignerRuntime(input, deps = {}) {
1214
1103
  };
1215
1104
  }
1216
1105
  async function installRuntimePackages2(runtimeDirectory, npmCacheDirectory, runCommand) {
1217
- const args = [
1106
+ const baseArgs = [
1218
1107
  "install",
1219
1108
  "--prefix",
1220
1109
  runtimeDirectory,
1221
- "--cache",
1222
- npmCacheDirectory,
1223
1110
  "--no-audit",
1224
1111
  "--no-fund",
1225
1112
  "--omit=dev",
1113
+ "--prefer-offline",
1226
1114
  signerPackageSpec(),
1227
1115
  sdkPackageSpec()
1228
1116
  ];
1229
- try {
1117
+ const run = async (args) => {
1230
1118
  if (runCommand) await runCommand("npm", args);
1231
1119
  else await execFileAsync2("npm", args, { timeout: 12e4, maxBuffer: 1024 * 1024 });
1232
- } catch (err) {
1233
- throw new Error(
1234
- `Could not install local Haven signer runtime ${signerPackageSpec()}: ${err instanceof Error ? err.message : String(err)}`
1235
- );
1120
+ };
1121
+ try {
1122
+ await run(baseArgs);
1123
+ } catch {
1124
+ try {
1125
+ await run([...baseArgs, "--cache", npmCacheDirectory]);
1126
+ } catch (err) {
1127
+ throw new Error(
1128
+ `Could not install local Haven signer runtime ${signerPackageSpec()}: ${err instanceof Error ? err.message : String(err)}`
1129
+ );
1130
+ }
1236
1131
  }
1237
1132
  }
1238
1133
  async function installedRuntimeMatches2(runtimeDirectory, cliPath) {
@@ -1295,6 +1190,117 @@ async function assertFileExists2(path, label) {
1295
1190
  throw new Error(`Missing ${label}: ${path}`);
1296
1191
  }
1297
1192
  }
1193
+
1194
+ // src/runtime-registry.ts
1195
+ var RUNTIME_PROFILES = {
1196
+ "claude-code": {
1197
+ id: "claude-code",
1198
+ label: "Claude Code",
1199
+ restartMode: "restart-session",
1200
+ canWriteRuntimeConfig: true
1201
+ },
1202
+ "codex-cli": {
1203
+ id: "codex-cli",
1204
+ label: "Codex CLI",
1205
+ restartMode: "restart-session",
1206
+ canWriteRuntimeConfig: true
1207
+ },
1208
+ "codex-desktop": {
1209
+ id: "codex-desktop",
1210
+ label: "Codex Desktop",
1211
+ restartMode: "restart-session",
1212
+ canWriteRuntimeConfig: true
1213
+ },
1214
+ cursor: {
1215
+ id: "cursor",
1216
+ label: "Cursor",
1217
+ restartMode: "hot-reload",
1218
+ canWriteRuntimeConfig: true
1219
+ },
1220
+ vscode: {
1221
+ id: "vscode",
1222
+ label: "VS Code",
1223
+ restartMode: "hot-reload",
1224
+ canWriteRuntimeConfig: true
1225
+ },
1226
+ "vscode-insiders": {
1227
+ id: "vscode-insiders",
1228
+ label: "VS Code Insiders",
1229
+ restartMode: "hot-reload",
1230
+ canWriteRuntimeConfig: true
1231
+ },
1232
+ "claude-desktop": {
1233
+ id: "claude-desktop",
1234
+ label: "Claude Desktop",
1235
+ restartMode: "restart-app",
1236
+ canWriteRuntimeConfig: true
1237
+ },
1238
+ other: {
1239
+ id: "other",
1240
+ label: "Other agent runtime",
1241
+ restartMode: "manual",
1242
+ canWriteRuntimeConfig: false
1243
+ }
1244
+ };
1245
+ var RUNTIME_ALIASES = {
1246
+ claude: "claude-code",
1247
+ "claude-code": "claude-code",
1248
+ claudecode: "claude-code",
1249
+ "claude_code": "claude-code",
1250
+ codex: "codex-cli",
1251
+ "codex-cli": "codex-cli",
1252
+ codexcli: "codex-cli",
1253
+ "codex_cli": "codex-cli",
1254
+ "codex-desktop": "codex-desktop",
1255
+ "codex_desktop": "codex-desktop",
1256
+ codexdesktop: "codex-desktop",
1257
+ "codex-app": "codex-desktop",
1258
+ "codex_app": "codex-desktop",
1259
+ codexapp: "codex-desktop",
1260
+ cursor: "cursor",
1261
+ vscode: "vscode",
1262
+ "vs-code": "vscode",
1263
+ "vs_code": "vscode",
1264
+ code: "vscode",
1265
+ "vscode-insiders": "vscode-insiders",
1266
+ "vscode_insiders": "vscode-insiders",
1267
+ vscodeinsiders: "vscode-insiders",
1268
+ "vs-code-insiders": "vscode-insiders",
1269
+ "code-insiders": "vscode-insiders",
1270
+ insiders: "vscode-insiders",
1271
+ "claude-desktop": "claude-desktop",
1272
+ "claude_desktop": "claude-desktop",
1273
+ claudesktop: "claude-desktop",
1274
+ desktop: "claude-desktop",
1275
+ other: "other",
1276
+ manual: "other"
1277
+ };
1278
+ function runtimeProfile(runtime, env = process.env) {
1279
+ return RUNTIME_PROFILES[normalizeRuntime(runtime, env)];
1280
+ }
1281
+ function normalizeRuntime(runtime, env = process.env) {
1282
+ const explicit = normalizeRuntimeName(runtime);
1283
+ if (explicit) return explicit;
1284
+ return detectRuntime(env) ?? "other";
1285
+ }
1286
+ function restartRequiredForRuntime(runtime, env = process.env) {
1287
+ const mode = runtimeProfile(runtime, env).restartMode;
1288
+ return mode === "restart-session" || mode === "restart-app";
1289
+ }
1290
+ function runtimeRequiresHardRestart(runtime) {
1291
+ return runtime === "claude-desktop" || runtime === "codex-desktop";
1292
+ }
1293
+ function normalizeRuntimeName(runtime) {
1294
+ const key = runtime?.trim().toLowerCase();
1295
+ if (!key) return null;
1296
+ return RUNTIME_ALIASES[key.replace(/\s+/g, "-")] ?? null;
1297
+ }
1298
+ function detectRuntime(env) {
1299
+ if (env.CLAUDECODE || env.CLAUDE_CODE || env.CLAUDECODE_CWD) return "claude-code";
1300
+ if (env.CODEX_SANDBOX || env.CODEX_HOME || env.CODEX_CWD) return "codex-cli";
1301
+ if (env.VSCODE_CWD || env.VSCODE_IPC_HOOK_CLI || env.TERM_PROGRAM === "vscode") return "vscode";
1302
+ return null;
1303
+ }
1298
1304
  async function acknowledgeLocalSignerConsent(signerPath, log) {
1299
1305
  try {
1300
1306
  const input = await buildSignerConsentInput(signerPath);
@@ -1370,6 +1376,7 @@ var execFileAsync3 = promisify(execFile);
1370
1376
  async function installRuntime(input, deps = {}) {
1371
1377
  const runtime = normalizeRuntime(input.runtime, deps.env);
1372
1378
  const profile = runtimeProfile(runtime, deps.env);
1379
+ const progress = deps.onProgress ?? (() => void 0);
1373
1380
  const localRuntime = input.localMcp === true && supportsLocalMcp(runtime);
1374
1381
  const consentMessages = [];
1375
1382
  const localMcpConsent = localRuntime ? await resolveLocalMcpConsent(input, consentMessages) : void 0;
@@ -1392,7 +1399,12 @@ async function installRuntime(input, deps = {}) {
1392
1399
  localMcpAcknowledged: false,
1393
1400
  messages: [
1394
1401
  ...consentMessages,
1395
- "Runtime was not recognized. Keep the local credentials and add Haven MCP entries manually after wallet approval."
1402
+ "Custom runtime: Haven did not auto-configure it. Your credentials are on disk (chmod 600) \u2014 read them at runtime; never paste a key into the agent prompt, memory, or logs.",
1403
+ ` identity (hosted MCP Bearer): ${input.identityPath}`,
1404
+ ` signer (local signing key): ${input.signerPath}`,
1405
+ "After wallet approval, wire the runtime to Haven by reference:",
1406
+ ` Hosted MCP + local signer: point your MCP client at ${input.hostedMcpUrl} with the api_key from identity.json, then run npx -y ${signerPackageSpec()} --credentials ${input.signerPath}`,
1407
+ ` Fully local MCP (no hosted dependency): npx -y ${mcpPackageSpec()} --identity ${input.identityPath} --signer ${input.signerPath}`
1396
1408
  ]
1397
1409
  };
1398
1410
  }
@@ -1429,6 +1441,7 @@ async function installRuntime(input, deps = {}) {
1429
1441
  }
1430
1442
  let signerCommand;
1431
1443
  if (!localRuntime) {
1444
+ progress("Getting the signer ready\u2026");
1432
1445
  try {
1433
1446
  const signerRuntime = await prepareSignerForRuntime(input, deps);
1434
1447
  signerCommand = { command: signerRuntime.command, args: signerRuntime.args };
@@ -1440,6 +1453,7 @@ async function installRuntime(input, deps = {}) {
1440
1453
  }
1441
1454
  }
1442
1455
  const signerRuntimePrepared = localRuntime ? void 0 : signerCommand !== void 0;
1456
+ progress("Setting up your Haven tools\u2026");
1443
1457
  const configResult = runtime === "claude-code" ? localRuntime ? await configureClaudeCode(deps, localRuntimeInstall?.command ?? "") : await configureClaudeCodeHosted(deps, input, signerCommand) : await writeRuntimeConfig({
1444
1458
  runtime,
1445
1459
  hostedMcpUrl: input.hostedMcpUrl,
@@ -1452,6 +1466,7 @@ async function installRuntime(input, deps = {}) {
1452
1466
  homeDir: deps.homeDir,
1453
1467
  mode: localRuntime ? "local" : "hosted"
1454
1468
  });
1469
+ progress("Almost there \u2014 just confirming everything connects\u2026");
1455
1470
  const localProbePromise = configResult.runtimeMcpMode === "local_stdio" && localRuntimeInstall ? runLocalMcpProbe(localRuntimeInstall, deps) : Promise.resolve(void 0);
1456
1471
  const [hostedProbe, signerCredentialReady, localMcpProbe] = await Promise.all([
1457
1472
  configResult.hostedConfigured ? probeHostedMcpTools(input.apiKey, input.hostedMcpUrl, deps.fetch) : Promise.resolve({ status: "bad_response" }),
@@ -1516,8 +1531,7 @@ async function configureClaudeCode(deps, localMcpCommand) {
1516
1531
  restartRequired: true,
1517
1532
  messages: [
1518
1533
  "Updated local Haven MCP entry with Claude Code.",
1519
- ...verified ? ["Verified Claude Code MCP entry."] : [],
1520
- "After Haven approval, Haven tools should appear in your next Claude Code message. If they don't, restart the session to load them."
1534
+ ...verified ? ["Verified Claude Code MCP entry."] : []
1521
1535
  ]
1522
1536
  };
1523
1537
  } catch (err) {
@@ -1566,8 +1580,7 @@ async function configureClaudeCodeHosted(deps, input, signerCommand) {
1566
1580
  restartRequired: true,
1567
1581
  messages: [
1568
1582
  "Updated hosted Haven MCP and local signer entries with Claude Code.",
1569
- ...verified ? ["Verified Claude Code MCP entry."] : [],
1570
- "After Haven approval, Haven tools should appear in your next Claude Code message. If they don't, restart the session to load them."
1583
+ ...verified ? ["Verified Claude Code MCP entry."] : []
1571
1584
  ]
1572
1585
  };
1573
1586
  } catch (err) {
@@ -1695,7 +1708,7 @@ function localRuntimePrepareErrorCode(err) {
1695
1708
  }
1696
1709
 
1697
1710
  // src/runtime.ts
1698
- var CONNECTOR_VERSION = "0.1.16-alpha.0";
1711
+ var CONNECTOR_VERSION = "0.1.18-alpha.0";
1699
1712
  async function runConnect(options, deps = {}) {
1700
1713
  const connectorVersion = options.connectorVersion ?? CONNECTOR_VERSION;
1701
1714
  const api = deps.api ?? createConnectApiClient(options.apiBaseUrl);
@@ -1715,6 +1728,7 @@ async function runConnect(options, deps = {}) {
1715
1728
  );
1716
1729
  }
1717
1730
  }
1731
+ log("Warming up your connection to Haven\u2026");
1718
1732
  const setup = await api.resolveSetup({
1719
1733
  setupToken: options.setupToken,
1720
1734
  connectorVersion,
@@ -1722,12 +1736,12 @@ async function runConnect(options, deps = {}) {
1722
1736
  });
1723
1737
  printSetupSummary(setup, log);
1724
1738
  await preflightStorage({ baseDir: options.credentialsDir, warn: log });
1725
- log("Checked local credential storage.");
1739
+ log("Checked local credential storage \u2014 all clear.");
1726
1740
  const localKey = generateKey();
1727
1741
  const localApiKey = generateLocalApiKey();
1728
- log("Generated local signing key.");
1729
- log("Generated local Haven API key.");
1742
+ log("Minting a fresh signing key and API key \u2014 both stay on this machine.");
1730
1743
  const proofSignature = await localKey.signChallenge(setup.challenge.message);
1744
+ log("Introducing your agent to Haven\u2026");
1731
1745
  const registration = await api.registerSetup({
1732
1746
  setupToken: options.setupToken,
1733
1747
  connectorVersion,
@@ -1744,6 +1758,7 @@ async function runConnect(options, deps = {}) {
1744
1758
  installCapabilities
1745
1759
  });
1746
1760
  log(`Registered signing address with Haven: ${shortAddress(registration.delegate_address)}.`);
1761
+ log("Tucking your credentials away safely on disk\u2026");
1747
1762
  const credentialPaths = await writeCredentials({
1748
1763
  baseDir: options.credentialsDir,
1749
1764
  agentId: registration.agent_id,
@@ -1784,8 +1799,14 @@ async function runConnect(options, deps = {}) {
1784
1799
  ackSigner: options.ackSigner,
1785
1800
  ackLocalTools: options.ackLocalTools,
1786
1801
  localMcp: options.localMcp
1787
- });
1802
+ }, { onProgress: log });
1788
1803
  printRuntimeInstall(runtimeInstall, log);
1804
+ if (runtimeInstall.errorCode) {
1805
+ log("Haven setup needs a couple more steps on this machine \u2014 see the notes above.");
1806
+ } else {
1807
+ log("Haven setup on this machine is complete.");
1808
+ }
1809
+ printNextSteps(runtimeInstall, log);
1789
1810
  try {
1790
1811
  await api.updateInstallStatus(registration.setup_id, localApiKey, {
1791
1812
  runtime: runtimeInstall.runtime,
@@ -1808,14 +1829,6 @@ async function runConnect(options, deps = {}) {
1808
1829
  } catch (err) {
1809
1830
  log(`Could not report install status to Haven: ${err instanceof Error ? err.message : String(err)}`);
1810
1831
  }
1811
- log("Return to Haven to approve the agent rules.");
1812
- if (runtimeInstall.restartRequired) {
1813
- if (runtimeRequiresHardRestart(runtimeInstall.runtime)) {
1814
- log("After approval, restart this agent so it can load Haven tools.");
1815
- } else {
1816
- log("After approval, Haven tools should appear in your next message. If they don't, restart this agent to load them.");
1817
- }
1818
- }
1819
1832
  return {
1820
1833
  setupId: registration.setup_id,
1821
1834
  agentId: registration.agent_id,
@@ -1853,6 +1866,18 @@ function printRuntimeInstall(result, log) {
1853
1866
  log("Local Haven signer still needs runtime setup.");
1854
1867
  }
1855
1868
  }
1869
+ function printNextSteps(result, log) {
1870
+ log("Next: approve the agent rules in Haven. No Haven tools appear until you approve \u2014 restart or not.");
1871
+ if (result.restartRequired) {
1872
+ if (runtimeRequiresHardRestart(result.runtime)) {
1873
+ log("After you approve, restart this agent so it can load Haven tools.");
1874
+ } else {
1875
+ log("After you approve, restart this agent \u2014 your current session won't load the Haven tools until you do.");
1876
+ }
1877
+ } else {
1878
+ log("After you approve, the Haven tools should appear in this runtime shortly.");
1879
+ }
1880
+ }
1856
1881
 
1857
1882
  // src/args.ts
1858
1883
  function parseArgs(argv, env = process.env) {