@adhdev/daemon-standalone 0.9.82-rc.364 → 0.9.82-rc.365

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.js CHANGED
@@ -30036,10 +30036,10 @@ var require_dist3 = __commonJS({
30036
30036
  }
30037
30037
  function getDaemonBuildInfo() {
30038
30038
  if (cached2) return cached2;
30039
- const commit = readInjected(true ? "1428e9d027beefe860a77f34dea34d202db80f00" : void 0) ?? "unknown";
30040
- const commitShort = readInjected(true ? "1428e9d0" : void 0) ?? (commit !== "unknown" ? commit.slice(0, 7) : "unknown");
30041
- const version2 = readInjected(true ? "0.9.82-rc.364" : void 0) ?? readInjected(typeof process !== "undefined" ? process.env?.ADHDEV_PKG_VERSION : void 0) ?? "unknown";
30042
- const builtAt = readInjected(true ? "2026-06-24T00:06:20.085Z" : void 0);
30039
+ const commit = readInjected(true ? "fe24f3fb158efc949e806b79bca2479b1c29d753" : void 0) ?? "unknown";
30040
+ const commitShort = readInjected(true ? "fe24f3fb" : void 0) ?? (commit !== "unknown" ? commit.slice(0, 7) : "unknown");
30041
+ const version2 = readInjected(true ? "0.9.82-rc.365" : void 0) ?? readInjected(typeof process !== "undefined" ? process.env?.ADHDEV_PKG_VERSION : void 0) ?? "unknown";
30042
+ const builtAt = readInjected(true ? "2026-06-24T00:48:25.762Z" : void 0);
30043
30043
  cached2 = builtAt ? { commit, commitShort, version: version2, builtAt } : { commit, commitShort, version: version2 };
30044
30044
  return cached2;
30045
30045
  }
@@ -31927,6 +31927,19 @@ ${error48.message || ""}`;
31927
31927
  MAX_ACTIVITY = 30;
31928
31928
  }
31929
31929
  });
31930
+ function sha256Hex(input) {
31931
+ return (0, import_node_crypto.createHash)("sha256").update(input).digest("hex");
31932
+ }
31933
+ function shortHash(input, length = 16) {
31934
+ return sha256Hex(input).slice(0, length);
31935
+ }
31936
+ var import_node_crypto;
31937
+ var init_hash = __esm2({
31938
+ "src/system/hash.ts"() {
31939
+ "use strict";
31940
+ import_node_crypto = require("crypto");
31941
+ }
31942
+ });
31930
31943
  function readObject(value) {
31931
31944
  return value && typeof value === "object" && !Array.isArray(value) ? value : null;
31932
31945
  }
@@ -32201,7 +32214,7 @@ ${error48.message || ""}`;
32201
32214
  return normalized;
32202
32215
  }
32203
32216
  function tokenIdForManualPairing(token) {
32204
- return `tok_${(0, import_crypto3.createHash)("sha256").update(token).digest("hex").slice(0, 16)}`;
32217
+ return `tok_${shortHash(token)}`;
32205
32218
  }
32206
32219
  function normalizeTokenExpiry(value) {
32207
32220
  if (typeof value !== "string" || !value.trim()) return void 0;
@@ -32440,6 +32453,7 @@ ${error48.message || ""}`;
32440
32453
  import_fs3 = require("fs");
32441
32454
  import_path3 = require("path");
32442
32455
  import_crypto3 = require("crypto");
32456
+ init_hash();
32443
32457
  init_config();
32444
32458
  init_repo_mesh_types();
32445
32459
  init_mesh_host_ownership();
@@ -36860,7 +36874,7 @@ Valid status values: \`completed\` | \`failed\` | \`blocked\` | \`partial\`.`;
36860
36874
  function resolveHermesCoordinatorHome(meshId, workspace) {
36861
36875
  const key = `${meshId || "mesh"}
36862
36876
  ${(0, import_node_path.resolve)(workspace || os42.tmpdir())}`;
36863
- const hash2 = (0, import_node_crypto.createHash)("sha256").update(key).digest("hex").slice(0, 16);
36877
+ const hash2 = shortHash(key);
36864
36878
  return (0, import_node_path.join)(os42.tmpdir(), `adhdev-hermes-mesh-coordinator-${hash2}`);
36865
36879
  }
36866
36880
  function resolveMcpConfigPath(configPath, workspace) {
@@ -37069,7 +37083,6 @@ ${rendered}`, "utf-8");
37069
37083
  });
37070
37084
  });
37071
37085
  }
37072
- var import_node_crypto;
37073
37086
  var import_node_fs3;
37074
37087
  var os42;
37075
37088
  var import_session_host_core4;
@@ -37081,12 +37094,12 @@ ${rendered}`, "utf-8");
37081
37094
  var init_mesh_coordinator = __esm2({
37082
37095
  "src/commands/mesh-coordinator.ts"() {
37083
37096
  "use strict";
37084
- import_node_crypto = require("crypto");
37085
37097
  import_node_fs3 = require("fs");
37086
37098
  os42 = __toESM2(require("os"));
37087
37099
  import_session_host_core4 = require_dist();
37088
37100
  import_node_path = require("path");
37089
37101
  init_logger();
37102
+ init_hash();
37090
37103
  DEFAULT_SERVER_NAME = "adhdev-mesh";
37091
37104
  DEFAULT_ADHDEV_MCP_COMMAND = "adhdev";
37092
37105
  HERMES_CLI_TYPE = "hermes-cli";
@@ -37953,6 +37966,46 @@ ${rendered}`, "utf-8");
37953
37966
  const isFreshUnacknowledged = Boolean(ledgerOnlyStaleReason && !liveStaleReason);
37954
37967
  return { ledgerOnlyStaleReason, isFreshUnacknowledged };
37955
37968
  }
37969
+ function buildLedgerDirectDispatchRecord(dispatch, ctx) {
37970
+ const taskId = directDispatchTaskId(dispatch);
37971
+ const terminal = ctx.terminals.filter((entry) => new Date(entry.timestamp).getTime() >= new Date(dispatch.timestamp).getTime()).find((entry) => terminalMatchesDispatch(entry, dispatch, taskId));
37972
+ const terminalStatus = terminal ? statusFromTerminal(terminal) : void 0;
37973
+ const live = sessionStatusFromNodes(ctx.nodes, dispatch.nodeId, dispatch.sessionId);
37974
+ const status = terminalStatus || live.status || "assigned";
37975
+ const terminalRow = Boolean(terminal && terminal.kind !== "task_approval_needed");
37976
+ const { ledgerOnlyStaleReason, isFreshUnacknowledged } = classifyDirectDispatch({
37977
+ status,
37978
+ isTerminalRow: terminalRow,
37979
+ hasTerminalStatus: Boolean(terminalStatus),
37980
+ liveStatus: live.status,
37981
+ liveStaleReason: live.staleReason,
37982
+ dispatchedToIdleSession: dispatch.payload?.dispatchedToIdleSession === true
37983
+ });
37984
+ const message = readString6(dispatch.payload?.message) || readString6(dispatch.payload?.summary) || "";
37985
+ const { title, summary } = summarizeMessage(message);
37986
+ const record2 = {
37987
+ taskId,
37988
+ source: "direct",
37989
+ status,
37990
+ nodeId: dispatch.nodeId,
37991
+ sessionId: dispatch.sessionId,
37992
+ providerType: dispatch.providerType || readString6(dispatch.payload?.providerType),
37993
+ taskTitle: readString6(dispatch.payload?.taskTitle) || title,
37994
+ taskSummary: readString6(dispatch.payload?.taskSummary) || summary,
37995
+ message,
37996
+ taskMode: readString6(dispatch.payload?.taskMode),
37997
+ createdAt: dispatch.timestamp,
37998
+ updatedAt: terminal?.timestamp || dispatch.timestamp,
37999
+ dispatchedAt: dispatch.timestamp,
38000
+ elapsedMs: elapsedSince(dispatch.timestamp, ctx.now),
38001
+ terminal: terminalRow,
38002
+ terminalKind: terminal?.kind,
38003
+ terminalAt: terminal?.timestamp,
38004
+ staleReason: live.staleReason || ledgerOnlyStaleReason,
38005
+ ...isFreshUnacknowledged ? { staleDispatchUnacknowledged: true } : {}
38006
+ };
38007
+ return { record: record2, terminalRow };
38008
+ }
37956
38009
  function buildMeshActiveWorkSummary(activeWork) {
37957
38010
  const statusCounts = {
37958
38011
  pending: 0,
@@ -38058,49 +38111,13 @@ ${rendered}`, "utf-8");
38058
38111
  const ledgerEntries = (opts.ledgerEntries || []).slice().sort((a, b) => new Date(a.timestamp).getTime() - new Date(b.timestamp).getTime());
38059
38112
  const terminals = ledgerEntries.filter((entry) => TERMINAL_LEDGER_KINDS.has(entry.kind) || entry.kind === "task_approval_needed");
38060
38113
  for (const dispatch of ledgerEntries.filter(isDirectDispatch)) {
38061
- const taskId = directDispatchTaskId(dispatch);
38062
- if (dbTaskIds.has(taskId)) continue;
38063
- const terminal = terminals.filter((entry) => new Date(entry.timestamp).getTime() >= new Date(dispatch.timestamp).getTime()).find((entry) => terminalMatchesDispatch(entry, dispatch, taskId));
38064
- const terminalStatus = terminal ? statusFromTerminal(terminal) : void 0;
38065
- const live = sessionStatusFromNodes(opts.nodes, dispatch.nodeId, dispatch.sessionId);
38066
- const status = terminalStatus || live.status || "assigned";
38067
- const terminalRow = Boolean(terminal && terminal.kind !== "task_approval_needed");
38068
- const { ledgerOnlyStaleReason, isFreshUnacknowledged } = classifyDirectDispatch({
38069
- status,
38070
- isTerminalRow: terminalRow,
38071
- hasTerminalStatus: Boolean(terminalStatus),
38072
- liveStatus: live.status,
38073
- liveStaleReason: live.staleReason,
38074
- dispatchedToIdleSession: dispatch.payload?.dispatchedToIdleSession === true
38075
- });
38076
- const message = readString6(dispatch.payload?.message) || readString6(dispatch.payload?.summary) || "";
38077
- const { title, summary: summary2 } = summarizeMessage(message);
38078
- const record2 = {
38079
- taskId,
38080
- source: "direct",
38081
- status,
38082
- nodeId: dispatch.nodeId,
38083
- sessionId: dispatch.sessionId,
38084
- providerType: dispatch.providerType || readString6(dispatch.payload?.providerType),
38085
- taskTitle: readString6(dispatch.payload?.taskTitle) || title,
38086
- taskSummary: readString6(dispatch.payload?.taskSummary) || summary2,
38087
- message,
38088
- taskMode: readString6(dispatch.payload?.taskMode),
38089
- createdAt: dispatch.timestamp,
38090
- updatedAt: terminal?.timestamp || dispatch.timestamp,
38091
- dispatchedAt: dispatch.timestamp,
38092
- elapsedMs: elapsedSince(dispatch.timestamp, now),
38093
- terminal: terminalRow,
38094
- terminalKind: terminal?.kind,
38095
- terminalAt: terminal?.timestamp,
38096
- staleReason: live.staleReason || ledgerOnlyStaleReason,
38097
- ...isFreshUnacknowledged ? { staleDispatchUnacknowledged: true } : {}
38098
- };
38114
+ if (dbTaskIds.has(directDispatchTaskId(dispatch))) continue;
38115
+ const { record: record2, terminalRow } = buildLedgerDirectDispatchRecord(dispatch, { terminals, nodes: opts.nodes, now });
38099
38116
  if (terminalRow) {
38100
38117
  terminalDirectWork.push(record2);
38101
38118
  if (opts.includeTerminalDirect !== true) continue;
38102
38119
  }
38103
- if ((live.staleReason || ledgerOnlyStaleReason) && !terminalRow) {
38120
+ if (record2.staleReason && !terminalRow) {
38104
38121
  staleDirectWork.push(record2);
38105
38122
  continue;
38106
38123
  }
@@ -38110,48 +38127,12 @@ ${rendered}`, "utf-8");
38110
38127
  const ledgerEntries = (opts.ledgerEntries || []).slice().sort((a, b) => new Date(a.timestamp).getTime() - new Date(b.timestamp).getTime());
38111
38128
  const terminals = ledgerEntries.filter((entry) => TERMINAL_LEDGER_KINDS.has(entry.kind) || entry.kind === "task_approval_needed");
38112
38129
  for (const dispatch of ledgerEntries.filter(isDirectDispatch)) {
38113
- const taskId = directDispatchTaskId(dispatch);
38114
- const terminal = terminals.filter((entry) => new Date(entry.timestamp).getTime() >= new Date(dispatch.timestamp).getTime()).find((entry) => terminalMatchesDispatch(entry, dispatch, taskId));
38115
- const terminalStatus = terminal ? statusFromTerminal(terminal) : void 0;
38116
- const live = sessionStatusFromNodes(opts.nodes, dispatch.nodeId, dispatch.sessionId);
38117
- const status = terminalStatus || live.status || "assigned";
38118
- const terminalRow = Boolean(terminal && terminal.kind !== "task_approval_needed");
38119
- const { ledgerOnlyStaleReason, isFreshUnacknowledged } = classifyDirectDispatch({
38120
- status,
38121
- isTerminalRow: terminalRow,
38122
- hasTerminalStatus: Boolean(terminalStatus),
38123
- liveStatus: live.status,
38124
- liveStaleReason: live.staleReason,
38125
- dispatchedToIdleSession: dispatch.payload?.dispatchedToIdleSession === true
38126
- });
38127
- const message = readString6(dispatch.payload?.message) || readString6(dispatch.payload?.summary) || "";
38128
- const { title, summary: summary2 } = summarizeMessage(message);
38129
- const record2 = {
38130
- taskId,
38131
- source: "direct",
38132
- status,
38133
- nodeId: dispatch.nodeId,
38134
- sessionId: dispatch.sessionId,
38135
- providerType: dispatch.providerType || readString6(dispatch.payload?.providerType),
38136
- taskTitle: readString6(dispatch.payload?.taskTitle) || title,
38137
- taskSummary: readString6(dispatch.payload?.taskSummary) || summary2,
38138
- message,
38139
- taskMode: readString6(dispatch.payload?.taskMode),
38140
- createdAt: dispatch.timestamp,
38141
- updatedAt: terminal?.timestamp || dispatch.timestamp,
38142
- dispatchedAt: dispatch.timestamp,
38143
- elapsedMs: elapsedSince(dispatch.timestamp, now),
38144
- terminal: terminalRow,
38145
- terminalKind: terminal?.kind,
38146
- terminalAt: terminal?.timestamp,
38147
- staleReason: live.staleReason || ledgerOnlyStaleReason,
38148
- ...isFreshUnacknowledged ? { staleDispatchUnacknowledged: true } : {}
38149
- };
38130
+ const { record: record2, terminalRow } = buildLedgerDirectDispatchRecord(dispatch, { terminals, nodes: opts.nodes, now });
38150
38131
  if (terminalRow) {
38151
38132
  terminalDirectWork.push(record2);
38152
38133
  if (opts.includeTerminalDirect !== true) continue;
38153
38134
  }
38154
- if ((live.staleReason || ledgerOnlyStaleReason) && !terminalRow) {
38135
+ if (record2.staleReason && !terminalRow) {
38155
38136
  staleDirectWork.push(record2);
38156
38137
  continue;
38157
38138
  }
@@ -64392,6 +64373,7 @@ ${body}
64392
64373
  ...meshNodeLogsHandlers
64393
64374
  })
64394
64375
  );
64376
+ init_dist();
64395
64377
  var os21 = __toESM2(require("os"));
64396
64378
  var path27 = __toESM2(require("path"));
64397
64379
  var crypto5 = __toESM2(require("crypto"));
@@ -64404,6 +64386,7 @@ ${body}
64404
64386
  init_state_store();
64405
64387
  init_workspaces();
64406
64388
  init_recent_activity();
64389
+ init_hash();
64407
64390
  init_coordinator_registry();
64408
64391
  init_summary_metadata();
64409
64392
  var os20 = __toESM2(require("os"));
@@ -70757,7 +70740,7 @@ ${rawInput}` : rawInput;
70757
70740
  function ensureEmptyDelegatedMcpConfig(workspace) {
70758
70741
  const baseDir = path27.join(os21.tmpdir(), "adhdev-delegated-agent-empty-mcp");
70759
70742
  (0, import_fs15.mkdirSync)(baseDir, { recursive: true });
70760
- const workspaceHash = crypto5.createHash("sha256").update(path27.resolve(workspace || os21.tmpdir())).digest("hex").slice(0, 16);
70743
+ const workspaceHash = shortHash(path27.resolve(workspace || os21.tmpdir()));
70761
70744
  const filePath = path27.join(baseDir, `${workspaceHash}.json`);
70762
70745
  (0, import_fs15.writeFileSync)(filePath, JSON.stringify({ mcpServers: {} }, null, 2), "utf-8");
70763
70746
  return filePath;
@@ -71724,6 +71707,154 @@ Run 'adhdev doctor' for detailed diagnostics.`
71724
71707
  return null;
71725
71708
  }
71726
71709
  };
71710
+ init_state_store();
71711
+ init_recent_activity();
71712
+ init_mesh_events_utils();
71713
+ var cliAgentHandlers = {
71714
+ launch_cli: async (ctx, args) => {
71715
+ const launchResult = await ctx.deps.cliManager.handleCliCommand("launch_cli", args);
71716
+ const meshNodeId = readStringValue(args?.settings?.meshNodeId);
71717
+ const meshId = readStringValue(args?.settings?.meshNodeFor);
71718
+ if (meshNodeId && meshId && launchResult?.success !== false) {
71719
+ try {
71720
+ const { getMesh: getMesh2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
71721
+ const meshObj = getMesh2(meshId) ?? ctx.getCachedInlineMesh(meshId);
71722
+ const nodeObj = Array.isArray(meshObj?.nodes) ? meshObj.nodes.find((n) => meshNodeIdMatches(n, meshNodeId)) : void 0;
71723
+ const bootstrapStatus = readStringValue(nodeObj?.worktreeBootstrap?.status);
71724
+ if (bootstrapStatus === "running") {
71725
+ return { success: true, ...launchResult, bootstrapPending: true };
71726
+ }
71727
+ } catch {
71728
+ }
71729
+ }
71730
+ return launchResult;
71731
+ },
71732
+ stop_cli: async (ctx, args) => {
71733
+ return ctx.deps.cliManager.handleCliCommand("stop_cli", args);
71734
+ },
71735
+ set_cli_view_mode: async (ctx, args) => {
71736
+ return ctx.deps.cliManager.handleCliCommand("set_cli_view_mode", args);
71737
+ },
71738
+ record_provider_pty: async (ctx, args) => {
71739
+ return ctx.deps.cliManager.handleCliCommand("record_provider_pty", args);
71740
+ },
71741
+ agent_command: async (ctx, args) => {
71742
+ {
71743
+ const dispatchSessionId = readStringValue(args?.targetSessionId, args?.sessionId, args?.instanceId);
71744
+ const dispatchMeshContext = args?.meshContext;
71745
+ if (dispatchSessionId && dispatchMeshContext) {
71746
+ try {
71747
+ const inst = ctx.deps.instanceManager.getInstance(dispatchSessionId);
71748
+ if (inst && typeof inst.updateSettings === "function") {
71749
+ const stamp = buildMeshWorkerRelayStamp(
71750
+ inst.getState?.()?.settings,
71751
+ {
71752
+ meshId: dispatchMeshContext.meshId,
71753
+ nodeId: dispatchMeshContext.nodeId,
71754
+ coordinatorDaemonId: dispatchMeshContext.coordinatorDaemonId,
71755
+ // Session-level anchor: preserved across the P2P dispatch to a
71756
+ // remote worker so its completion echoes back to the right session.
71757
+ coordinatorSessionId: dispatchMeshContext.coordinatorSessionId
71758
+ }
71759
+ );
71760
+ if (stamp) inst.updateSettings(stamp);
71761
+ }
71762
+ } catch {
71763
+ }
71764
+ }
71765
+ }
71766
+ const agentResult = await ctx.deps.cliManager.handleCliCommand("agent_command", args);
71767
+ const meshCtx = args?.meshContext;
71768
+ const dispatchNodeId = readStringValue(meshCtx?.nodeId);
71769
+ const dispatchMeshId = readStringValue(meshCtx?.meshId);
71770
+ if (dispatchNodeId && dispatchMeshId && agentResult?.success !== false) {
71771
+ try {
71772
+ const { getMesh: getMesh2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
71773
+ const meshObj = getMesh2(dispatchMeshId) ?? ctx.getCachedInlineMesh(dispatchMeshId);
71774
+ const nodeObj = Array.isArray(meshObj?.nodes) ? meshObj.nodes.find((n) => meshNodeIdMatches(n, dispatchNodeId)) : void 0;
71775
+ const bootstrapStatus = readStringValue(nodeObj?.worktreeBootstrap?.status);
71776
+ if (bootstrapStatus === "running") {
71777
+ return {
71778
+ success: true,
71779
+ ...agentResult,
71780
+ dispatchAcknowledgementRisk: true,
71781
+ dispatchAcknowledgementRiskReason: "bootstrap_still_running",
71782
+ nextAction: "Wait for worktree_bootstrap_complete event before dispatching work to this node."
71783
+ };
71784
+ }
71785
+ } catch {
71786
+ }
71787
+ }
71788
+ return agentResult;
71789
+ },
71790
+ // ─── Logs ───
71791
+ list_saved_sessions: async (ctx, args) => {
71792
+ const providerType = typeof args?.providerType === "string" ? args.providerType.trim() : typeof args?.agentType === "string" ? args.agentType.trim() : "";
71793
+ const kind = args?.kind === "acp" ? "acp" : "cli";
71794
+ if (!providerType) {
71795
+ return { success: false, error: "providerType required" };
71796
+ }
71797
+ const wantsAll = args?.all === true;
71798
+ const offset = wantsAll ? 0 : Math.max(0, Number(args?.offset) || 0);
71799
+ const limit = wantsAll ? Number.MAX_SAFE_INTEGER : Math.max(1, Math.min(100, Number(args?.limit) || 30));
71800
+ const requestedWorkspace = typeof args?.workspace === "string" ? args.workspace.trim() : "";
71801
+ const requestedProviderSessionId = typeof args?.providerSessionId === "string" ? args.providerSessionId.trim() : typeof args?.activeProviderSessionId === "string" ? args.activeProviderSessionId.trim() : "";
71802
+ const providerMeta = ctx.deps.providerLoader.resolve?.(providerType) || ctx.deps.providerLoader.getMeta(providerType);
71803
+ const { sessions: historySessions, hasMore, source } = listProviderHistorySessions(providerType, {
71804
+ canonicalHistory: providerMeta?.nativeHistory,
71805
+ offset,
71806
+ limit,
71807
+ historyBehavior: providerMeta?.historyBehavior,
71808
+ scripts: providerMeta?.scripts
71809
+ });
71810
+ const state = loadState();
71811
+ const savedSessions = getSavedProviderSessions(state, { providerType, kind });
71812
+ const recentSessions = getRecentActivity(state, 200).filter((entry) => entry.providerType === providerType && entry.kind === kind && entry.providerSessionId);
71813
+ const savedSessionById = new Map(savedSessions.map((entry) => [entry.providerSessionId, entry]));
71814
+ const recentSessionById = new Map(recentSessions.map((entry) => [entry.providerSessionId, entry]));
71815
+ const canResumeById = supportsExplicitSessionResume(providerMeta?.resume);
71816
+ return {
71817
+ success: true,
71818
+ sessions: historySessions.map((session) => {
71819
+ const saved = savedSessionById.get(session.historySessionId);
71820
+ const recent = recentSessionById.get(session.historySessionId);
71821
+ const workspace = saved?.workspace || recent?.workspace || session.workspace || (requestedWorkspace && requestedProviderSessionId === session.historySessionId ? requestedWorkspace : void 0);
71822
+ return {
71823
+ id: session.historySessionId,
71824
+ providerSessionId: session.historySessionId,
71825
+ providerType,
71826
+ providerName: saved?.providerName || recent?.providerName || providerType,
71827
+ kind: saved?.kind || recent?.kind || kind,
71828
+ title: saved?.title || recent?.title || session.sessionTitle || session.preview || providerType,
71829
+ workspace,
71830
+ summaryMetadata: saved?.summaryMetadata || recent?.summaryMetadata,
71831
+ preview: session.preview,
71832
+ messageCount: session.messageCount,
71833
+ firstMessageAt: session.firstMessageAt,
71834
+ lastMessageAt: session.lastMessageAt,
71835
+ canResume: !!workspace && canResumeById,
71836
+ historySource: session.source,
71837
+ sourcePath: session.sourcePath,
71838
+ sourceMtimeMs: session.sourceMtimeMs
71839
+ };
71840
+ }),
71841
+ hasMore,
71842
+ source
71843
+ };
71844
+ },
71845
+ // ─── restart_session: IDE / CLI / ACP unified ───
71846
+ restart_session: async (ctx, args) => {
71847
+ const targetType = args?.cliType || args?.agentType || args?.ideType;
71848
+ if (!targetType) throw new Error("cliType or ideType required");
71849
+ const isIde = ctx.deps.cdpManagers.has(targetType) || ctx.deps.providerLoader.getMeta(targetType)?.category === "ide";
71850
+ if (isIde) {
71851
+ await ctx.stopIde(targetType, true);
71852
+ const launchResult = await ctx.launchIde({ ideType: targetType, enableCdp: true, workspace: args?.workspace });
71853
+ return { success: true, restarted: true, ideType: targetType, launch: launchResult };
71854
+ }
71855
+ return ctx.deps.cliManager.handleCliCommand("restart_session", args);
71856
+ }
71857
+ };
71727
71858
  var import_child_process9 = require("child_process");
71728
71859
  var net3 = __toESM2(require("net"));
71729
71860
  var os26 = __toESM2(require("os"));
@@ -75528,6 +75659,1320 @@ ${formatManifestValidationIssues2(validation2.issues)}`);
75528
75659
  init_workspaces();
75529
75660
  init_recent_activity();
75530
75661
  init_cli_detector();
75662
+ init_logger();
75663
+ async function launchIde(ctx, args) {
75664
+ const ideKey = args?.ideId || args?.ideType;
75665
+ const resolvedWorkspace = resolveIdeLaunchWorkspace(
75666
+ {
75667
+ workspace: args?.workspace,
75668
+ workspaceId: args?.workspaceId,
75669
+ useDefaultWorkspace: args?.useDefaultWorkspace
75670
+ },
75671
+ loadConfig2()
75672
+ );
75673
+ const launchArgs = {
75674
+ ideId: ideKey,
75675
+ workspace: resolvedWorkspace,
75676
+ newWindow: args?.newWindow
75677
+ };
75678
+ LOG2.info("LaunchIDE", `target=${ideKey || "auto"}`);
75679
+ const result = await launchWithCdp(launchArgs);
75680
+ if (result.success && result.port && result.ideId && !ctx.deps.cdpManagers.has(result.ideId)) {
75681
+ const logFn = ctx.deps.getCdpLogFn ? ctx.deps.getCdpLogFn(result.ideId) : LOG2.forComponent(`CDP:${result.ideId}`).asLogFn();
75682
+ const provider = ctx.deps.providerLoader.getMeta(result.ideId);
75683
+ const manager = new DaemonCdpManager(result.port, logFn, void 0, provider?.targetFilter);
75684
+ const connected = await manager.connect();
75685
+ if (connected) {
75686
+ registerExtensionProviders(ctx.deps.providerLoader, manager, result.ideId);
75687
+ ctx.deps.cdpManagers.set(result.ideId, manager);
75688
+ LOG2.info("CDP", `Connected: ${result.ideId} (port ${result.port})`);
75689
+ LOG2.info("CDP", `${ctx.deps.cdpManagers.size} IDE(s) connected`);
75690
+ ctx.deps.onCdpManagerCreated?.(result.ideId, manager);
75691
+ }
75692
+ }
75693
+ ctx.deps.onIdeConnected?.();
75694
+ try {
75695
+ const results = await detectIDEs(ctx.deps.providerLoader);
75696
+ ctx.deps.detectedIdes.value = results;
75697
+ ctx.deps.providerLoader.setIdeDetectionResults(results, true);
75698
+ } catch {
75699
+ }
75700
+ if (result.success && resolvedWorkspace) {
75701
+ try {
75702
+ const next = appendRecentActivity(loadState(), {
75703
+ kind: "ide",
75704
+ providerType: result.ideId || ideKey,
75705
+ providerName: result.ideId || ideKey,
75706
+ workspace: resolvedWorkspace,
75707
+ title: result.ideId || ideKey
75708
+ });
75709
+ saveState(next);
75710
+ } catch {
75711
+ }
75712
+ } else if (result.success && (result.ideId || ideKey)) {
75713
+ try {
75714
+ saveState(appendRecentActivity(loadState(), {
75715
+ kind: "ide",
75716
+ providerType: result.ideId || ideKey,
75717
+ providerName: result.ideId || ideKey,
75718
+ title: result.ideId || ideKey
75719
+ }));
75720
+ } catch {
75721
+ }
75722
+ }
75723
+ return { ...result };
75724
+ }
75725
+ var ideHandlers = {
75726
+ // ─── IDE stop ───
75727
+ stop_ide: async (ctx, args) => {
75728
+ const ideType = args?.ideType;
75729
+ if (!ideType) throw new Error("ideType required");
75730
+ const killProcess = args?.killProcess !== false;
75731
+ await ctx.stopIde(ideType, killProcess);
75732
+ try {
75733
+ const results = await detectIDEs(ctx.deps.providerLoader);
75734
+ ctx.deps.detectedIdes.value = results;
75735
+ ctx.deps.providerLoader.setIdeDetectionResults(results, true);
75736
+ } catch {
75737
+ }
75738
+ return { success: true, ideType, stopped: true, processKilled: killProcess };
75739
+ },
75740
+ // ─── IDE restart ───
75741
+ restart_ide: async (ctx, args) => {
75742
+ const ideType = args?.ideType;
75743
+ if (!ideType) throw new Error("ideType required");
75744
+ await ctx.stopIde(ideType, true);
75745
+ const launchResult = await ctx.launchIde({ ideType, enableCdp: true, workspace: args?.workspace });
75746
+ return { success: true, ideType, restarted: true, launch: launchResult };
75747
+ },
75748
+ // ─── IDE launch + CDP connect ───
75749
+ launch_ide: async (ctx, args) => {
75750
+ return launchIde(ctx, args);
75751
+ },
75752
+ // ─── Detect providers ───
75753
+ detect_provider: async (ctx, args) => {
75754
+ const providerType = typeof args?.providerType === "string" ? args.providerType.trim() : "";
75755
+ if (!providerType) return { success: false, error: "providerType is required" };
75756
+ const normalizedType = ctx.deps.providerLoader.resolveAlias(providerType);
75757
+ const provider = ctx.deps.providerLoader.getByAlias(providerType);
75758
+ if (!provider) return { success: false, error: `Provider not found: ${providerType}` };
75759
+ if (provider.category !== "cli" && provider.category !== "acp") {
75760
+ return { success: false, error: `Provider detection is only supported for CLI/ACP providers: ${providerType}` };
75761
+ }
75762
+ if (!ctx.deps.providerLoader.isMachineProviderEnabled(normalizedType)) {
75763
+ return { success: false, error: `Provider is disabled on this machine: ${providerType}` };
75764
+ }
75765
+ const detected = await detectCLI(normalizedType, ctx.deps.providerLoader, { includeVersion: false });
75766
+ ctx.deps.providerLoader.setCliDetectionResults([{
75767
+ id: normalizedType,
75768
+ installed: !!detected,
75769
+ path: detected?.path
75770
+ }], false);
75771
+ ctx.deps.onStatusChange?.();
75772
+ return {
75773
+ success: true,
75774
+ providerType: normalizedType,
75775
+ detected: !!detected,
75776
+ path: detected?.path || null
75777
+ };
75778
+ },
75779
+ // ─── Detect IDEs ───
75780
+ detect_ides: async (ctx, _args) => {
75781
+ const results = await detectIDEs(ctx.deps.providerLoader);
75782
+ ctx.deps.detectedIdes.value = results;
75783
+ ctx.deps.providerLoader.setIdeDetectionResults(results, true);
75784
+ return { success: true, detectedInfo: results };
75785
+ }
75786
+ };
75787
+ init_dist();
75788
+ init_mesh_host_ownership();
75789
+ init_mesh_events();
75790
+ init_config();
75791
+ var meshCrudHandlers = {
75792
+ list_meshes: async (_ctx, _args) => {
75793
+ try {
75794
+ const { listMeshes: listMeshes2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
75795
+ return { success: true, meshes: listMeshes2() };
75796
+ } catch (e) {
75797
+ return { success: false, error: e.message };
75798
+ }
75799
+ },
75800
+ get_mesh: async (ctx, args) => {
75801
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
75802
+ if (!meshId) return { success: false, error: "meshId required" };
75803
+ const meshRecord = await ctx.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
75804
+ if (!meshRecord?.mesh) return { success: false, error: "Mesh not found" };
75805
+ const requireDirectPeerTruth = args?.requireDirectPeerTruth === true;
75806
+ const probeRemotePeers = args?.refresh === true || args?.forceRefresh === true;
75807
+ const directTruth = await hydrateInlineMeshDirectTruth({
75808
+ mesh: meshRecord.mesh,
75809
+ meshSource: meshRecord.source,
75810
+ dispatchMeshCommand: ctx.deps.dispatchMeshCommand,
75811
+ getMeshPeerConnectionStatus: ctx.deps.getMeshPeerConnectionStatus,
75812
+ statusInstanceId: ctx.deps.statusInstanceId,
75813
+ localMachineId: loadConfig2().machineId || "",
75814
+ probeRemotePeers,
75815
+ probeCache: ctx.meshGitProbeCache
75816
+ });
75817
+ const directTruthSatisfied = meshRecord.source !== "inline_bootstrap" || directTruth.directEvidenceCount > 0;
75818
+ const sourceOfTruth = {
75819
+ membership: meshRecord.source === "inline_cache" ? "coordinator_inline_mesh_cache" : meshRecord.source === "local_config" ? "local_mesh_config" : "inline_bootstrap_snapshot",
75820
+ coordinatorOwnsLiveTruth: directTruthSatisfied,
75821
+ directPeerTruth: {
75822
+ required: requireDirectPeerTruth,
75823
+ satisfied: directTruthSatisfied,
75824
+ directEvidenceCount: directTruth.directEvidenceCount,
75825
+ localConfirmedCount: directTruth.localConfirmedCount,
75826
+ peerAttemptedCount: directTruth.peerAttemptedCount,
75827
+ peerConfirmedCount: directTruth.peerConfirmedCount,
75828
+ unavailableNodeIds: directTruth.unavailableNodeIds
75829
+ }
75830
+ };
75831
+ if (requireDirectPeerTruth && !directTruthSatisfied) {
75832
+ return {
75833
+ success: false,
75834
+ code: "mesh_direct_peer_truth_unavailable",
75835
+ error: "Selected coordinator could not confirm direct mesh truth yet. Bootstrap inventory stays unavailable until direct get_mesh probes succeed.",
75836
+ sourceOfTruth
75837
+ };
75838
+ }
75839
+ return { success: true, mesh: meshRecord.mesh, sourceOfTruth };
75840
+ },
75841
+ create_mesh: async (_ctx, args) => {
75842
+ const name = typeof args?.name === "string" ? args.name.trim() : "";
75843
+ const repoIdentity = typeof args?.repoIdentity === "string" ? args.repoIdentity.trim() : "";
75844
+ const repoRemoteUrl = typeof args?.repoRemoteUrl === "string" ? args.repoRemoteUrl.trim() : void 0;
75845
+ const defaultBranch = typeof args?.defaultBranch === "string" ? args.defaultBranch.trim() : void 0;
75846
+ if (!name) return { success: false, error: "name required" };
75847
+ try {
75848
+ const { createMesh: createMesh2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
75849
+ const meshHost = args?.meshHost && typeof args.meshHost === "object" && !Array.isArray(args.meshHost) ? args.meshHost : void 0;
75850
+ const mesh = createMesh2({ name, repoIdentity, repoRemoteUrl, defaultBranch, policy: args?.policy, meshHost });
75851
+ return { success: true, mesh };
75852
+ } catch (e) {
75853
+ return { success: false, error: e.message };
75854
+ }
75855
+ },
75856
+ update_mesh: async (ctx, args) => {
75857
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
75858
+ if (!meshId) return { success: false, error: "meshId required" };
75859
+ try {
75860
+ const { updateMesh: updateMesh2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
75861
+ const patch = {};
75862
+ if (typeof args?.name === "string") patch.name = args.name;
75863
+ if (typeof args?.defaultBranch === "string") patch.defaultBranch = args.defaultBranch;
75864
+ if (args?.policy && typeof args.policy === "object" && !Array.isArray(args.policy)) patch.policy = args.policy;
75865
+ if (args?.coordinator && typeof args.coordinator === "object" && !Array.isArray(args.coordinator)) patch.coordinator = args.coordinator;
75866
+ if (args?.meshHost && typeof args.meshHost === "object" && !Array.isArray(args.meshHost)) patch.meshHost = args.meshHost;
75867
+ if (!Object.keys(patch).length) return { success: false, error: "No updates provided" };
75868
+ const mesh = updateMesh2(meshId, patch);
75869
+ if (!mesh) return { success: false, error: "Mesh not found" };
75870
+ ctx.inlineMeshCache.set(meshId, mesh);
75871
+ ctx.invalidateAggregateMeshStatus(meshId);
75872
+ return { success: true, mesh };
75873
+ } catch (e) {
75874
+ return { success: false, error: e.message };
75875
+ }
75876
+ },
75877
+ delete_mesh: async (_ctx, args) => {
75878
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
75879
+ if (!meshId) return { success: false, error: "meshId required" };
75880
+ try {
75881
+ const { deleteMesh: deleteMesh2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
75882
+ const deleted = deleteMesh2(meshId);
75883
+ return { success: true, deleted };
75884
+ } catch (e) {
75885
+ return { success: false, error: e.message };
75886
+ }
75887
+ },
75888
+ add_mesh_node: async (ctx, args) => {
75889
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
75890
+ const workspace = typeof args?.workspace === "string" ? args.workspace.trim() : "";
75891
+ if (!meshId) return { success: false, error: "meshId required" };
75892
+ if (!workspace) return { success: false, error: "workspace required" };
75893
+ const ownerFailure = await ctx.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "node addition");
75894
+ if (ownerFailure) return ownerFailure;
75895
+ try {
75896
+ const { addNode: addNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
75897
+ const providerPriority = Array.isArray(args?.providerPriority) ? args.providerPriority.map((type) => typeof type === "string" ? type.trim() : "").filter(Boolean) : [];
75898
+ const readOnly = args?.readOnly === true;
75899
+ const providerRoles = normalizeProviderRoles(args?.providerRoles);
75900
+ const policy = {
75901
+ ...readOnly ? { readOnly: true } : {},
75902
+ ...providerPriority.length ? { providerPriority } : {},
75903
+ ...providerRoles.length ? { providerRoles } : {}
75904
+ };
75905
+ const role = normalizeMeshDaemonRole(args?.role);
75906
+ const daemonId = typeof args?.daemonId === "string" && args.daemonId.trim() ? args.daemonId.trim() : void 0;
75907
+ const machineId = typeof args?.machineId === "string" && args.machineId.trim() ? args.machineId.trim() : void 0;
75908
+ const repoRoot = typeof args?.repoRoot === "string" && args.repoRoot.trim() ? args.repoRoot.trim() : void 0;
75909
+ const node = addNode2(meshId, {
75910
+ workspace,
75911
+ ...repoRoot ? { repoRoot } : {},
75912
+ ...daemonId ? { daemonId } : {},
75913
+ ...machineId ? { machineId } : {},
75914
+ ...policy ? { policy } : {},
75915
+ ...role ? { role } : {}
75916
+ });
75917
+ if (!node) return { success: false, error: "Mesh not found" };
75918
+ ctx.invalidateAggregateMeshStatus(meshId);
75919
+ return { success: true, node };
75920
+ } catch (e) {
75921
+ return { success: false, error: e.message };
75922
+ }
75923
+ },
75924
+ update_mesh_node: async (ctx, args) => {
75925
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
75926
+ const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
75927
+ if (!meshId || !nodeId) return { success: false, error: "meshId and nodeId required" };
75928
+ const ownerFailure = await ctx.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "node update");
75929
+ if (ownerFailure) return ownerFailure;
75930
+ try {
75931
+ const { updateNode: updateNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
75932
+ const policy = args?.policy && typeof args.policy === "object" && !Array.isArray(args.policy) ? { ...args.policy } : {};
75933
+ if (Array.isArray(args?.providerPriority)) {
75934
+ const providerPriority = args.providerPriority.map((type) => typeof type === "string" ? type.trim() : "").filter(Boolean);
75935
+ delete policy.provider_priority;
75936
+ if (providerPriority.length) {
75937
+ policy.providerPriority = providerPriority;
75938
+ } else {
75939
+ delete policy.providerPriority;
75940
+ }
75941
+ }
75942
+ if (Array.isArray(args?.providerRoles)) {
75943
+ const providerRoles = normalizeProviderRoles(args.providerRoles);
75944
+ if (providerRoles.length) {
75945
+ policy.providerRoles = providerRoles;
75946
+ } else {
75947
+ delete policy.providerRoles;
75948
+ }
75949
+ }
75950
+ const patch = { policy };
75951
+ if (typeof args?.systemPrompt === "string") {
75952
+ const trimmed = args.systemPrompt.trim();
75953
+ patch.systemPrompt = trimmed || void 0;
75954
+ } else if (args?.systemPrompt === null) {
75955
+ patch.systemPrompt = void 0;
75956
+ }
75957
+ const node = updateNode2(meshId, nodeId, patch);
75958
+ if (!node) return { success: false, error: "Mesh node not found" };
75959
+ ctx.invalidateAggregateMeshStatus(meshId);
75960
+ return { success: true, node };
75961
+ } catch (e) {
75962
+ return { success: false, error: e.message };
75963
+ }
75964
+ },
75965
+ cleanup_mesh_sessions: async (ctx, args) => {
75966
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
75967
+ const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
75968
+ if (!meshId || !nodeId) return { success: false, error: "meshId and nodeId required" };
75969
+ const ownerFailure = await ctx.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "node removal");
75970
+ if (ownerFailure) return ownerFailure;
75971
+ try {
75972
+ const meshRecord = await ctx.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
75973
+ const mesh = meshRecord?.mesh;
75974
+ if (!mesh) return { success: false, error: "Mesh not found" };
75975
+ const node = mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
75976
+ if (!node) return { success: false, error: `Node '${nodeId}' not found in mesh` };
75977
+ const mode = ctx.normalizeMeshSessionCleanupMode(args?.mode ?? mesh?.policy?.sessionCleanupOnNodeRemove);
75978
+ const sessionIds = Array.isArray(args?.sessionIds) ? args.sessionIds.map((id) => typeof id === "string" ? id.trim() : "").filter(Boolean) : void 0;
75979
+ const result = await ctx.cleanupMeshSessions({
75980
+ meshId,
75981
+ nodeId,
75982
+ node,
75983
+ mode,
75984
+ sessionIds,
75985
+ dryRun: args?.dryRun === true,
75986
+ source: "mesh_cleanup_sessions"
75987
+ });
75988
+ return result;
75989
+ } catch (e) {
75990
+ return { success: false, error: e.message };
75991
+ }
75992
+ },
75993
+ remove_mesh_node: async (ctx, args) => {
75994
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
75995
+ const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
75996
+ if (!meshId || !nodeId) return { success: false, error: "meshId and nodeId required" };
75997
+ try {
75998
+ const meshRecord = await ctx.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
75999
+ const mesh = meshRecord?.mesh;
76000
+ const node = mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
76001
+ if (node && !args?._meshDirectDispatch && node.isLocalWorktree !== true && args?.force !== true) {
76002
+ const nodeDaemonId = typeof node.daemonId === "string" ? node.daemonId.trim() : "";
76003
+ const nodeMachineId = readMeshNodeMachineId(node) || "";
76004
+ const selfDaemonId = ctx.deps.statusInstanceId || "";
76005
+ const selfMachineId = (() => {
76006
+ try {
76007
+ return loadConfig2().machineId || "";
76008
+ } catch {
76009
+ return "";
76010
+ }
76011
+ })();
76012
+ const isCoordinatorBaseNode = !!selfDaemonId && (nodeDaemonId === selfDaemonId || nodeMachineId === selfDaemonId) || !!selfMachineId && (nodeDaemonId === selfMachineId || nodeMachineId === selfMachineId);
76013
+ if (isCoordinatorBaseNode) {
76014
+ return {
76015
+ success: false,
76016
+ removed: false,
76017
+ code: "mesh_remove_coordinator_base_node_protected",
76018
+ error: `Refusing to remove the coordinator's own base node '${typeof node.workspace === "string" ? node.workspace : nodeId}'. It is the local non-worktree node bound to this coordinator daemon; removing it breaks live mesh membership and forces a restart.`,
76019
+ recoveryHint: "Remove worktree clone nodes instead, or pass force:true only if you are intentionally tearing down this mesh and accept that the coordinator must be re-registered/restarted."
76020
+ };
76021
+ }
76022
+ }
76023
+ const sessionCleanupMode = ctx.normalizeMeshSessionCleanupMode(
76024
+ args?.sessionCleanupMode ?? args?.session_cleanup_mode ?? mesh?.policy?.sessionCleanupOnNodeRemove
76025
+ );
76026
+ const explicitSessionIds = Array.isArray(args?.sessionIds) ? args.sessionIds.filter((v) => typeof v === "string" && v.trim().length > 0).map((v) => v.trim()) : void 0;
76027
+ let sessionCleanup;
76028
+ if (node && sessionCleanupMode !== "preserve") {
76029
+ sessionCleanup = await ctx.cleanupMeshSessions({
76030
+ meshId,
76031
+ nodeId,
76032
+ node,
76033
+ mode: sessionCleanupMode,
76034
+ ...explicitSessionIds && explicitSessionIds.length > 0 ? { sessionIds: explicitSessionIds } : {},
76035
+ source: "mesh_remove_node"
76036
+ });
76037
+ if (sessionCleanup.success === false) return { success: false, removed: false, sessionCleanup };
76038
+ }
76039
+ let worktreeCleanup;
76040
+ if (node?.isLocalWorktree) {
76041
+ const nodeDaemonId = typeof node.daemonId === "string" ? node.daemonId.trim() : void 0;
76042
+ const isRemoteWorktree = nodeDaemonId && !daemonIdsEquivalent(nodeDaemonId, ctx.deps.statusInstanceId) && ctx.deps.dispatchMeshCommand && !args?._meshDirectDispatch;
76043
+ if (isRemoteWorktree) {
76044
+ const forwarded = await ctx.deps.dispatchMeshCommand(nodeDaemonId, "remove_mesh_node", {
76045
+ ...typeof args === "object" && args !== null ? args : {},
76046
+ _meshDirectDispatch: true
76047
+ });
76048
+ return forwarded ?? { success: false, error: "no response from remote node" };
76049
+ }
76050
+ const cleanupResult = await ctx.cleanupLocalWorktreeNode({ mesh, node, nodeId, force: args?.force === true });
76051
+ if (cleanupResult.success === false) {
76052
+ return {
76053
+ success: false,
76054
+ removed: false,
76055
+ code: cleanupResult.code,
76056
+ error: cleanupResult.error,
76057
+ recoveryHint: cleanupResult.recoveryHint,
76058
+ ...sessionCleanup ? { sessionCleanup } : {},
76059
+ worktreeCleanup: cleanupResult
76060
+ };
76061
+ }
76062
+ worktreeCleanup = cleanupResult;
76063
+ }
76064
+ let removed = false;
76065
+ if (meshRecord?.inline) {
76066
+ removed = ctx.removeInlineMeshNode(meshId, mesh, nodeId);
76067
+ if (removed) ctx.invalidateAggregateMeshStatus(meshId);
76068
+ if (!removed && !node) removed = true;
76069
+ } else {
76070
+ const { removeNode: removeNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
76071
+ removed = removeNode2(meshId, nodeId);
76072
+ if (!removed && !node) removed = true;
76073
+ if (removed) ctx.invalidateAggregateMeshStatus(meshId);
76074
+ }
76075
+ if (removed) {
76076
+ try {
76077
+ const { appendLedgerEntry: appendLedgerEntry2 } = await Promise.resolve().then(() => (init_mesh_ledger(), mesh_ledger_exports));
76078
+ appendLedgerEntry2(meshId, {
76079
+ kind: "node_removed",
76080
+ nodeId,
76081
+ payload: {
76082
+ worktree: !!node?.isLocalWorktree,
76083
+ sessionCleanupMode,
76084
+ workspace: typeof node?.workspace === "string" ? node.workspace : void 0,
76085
+ daemonId: typeof node?.daemonId === "string" ? node.daemonId : void 0,
76086
+ worktreeBranch: typeof node?.worktreeBranch === "string" ? node.worktreeBranch : void 0,
76087
+ worktreeCleanupFallback: typeof worktreeCleanup?.fallback === "string" ? worktreeCleanup.fallback : void 0,
76088
+ forced: worktreeCleanup?.forced === true ? true : void 0,
76089
+ forceFallbackReason: typeof worktreeCleanup?.reason === "string" ? worktreeCleanup.reason : void 0
76090
+ }
76091
+ });
76092
+ } catch {
76093
+ }
76094
+ }
76095
+ const residueWarning = worktreeCleanup?.residue === true && typeof worktreeCleanup?.residueWarning === "string" ? worktreeCleanup.residueWarning : void 0;
76096
+ return {
76097
+ success: true,
76098
+ removed,
76099
+ ...residueWarning ? { residueWarning } : {},
76100
+ ...sessionCleanup ? { sessionCleanup } : {},
76101
+ ...worktreeCleanup ? { worktreeCleanup } : {}
76102
+ };
76103
+ } catch (e) {
76104
+ return { success: false, error: e.message };
76105
+ }
76106
+ },
76107
+ clone_mesh_node: async (ctx, args) => {
76108
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76109
+ const sourceNodeId = typeof args?.sourceNodeId === "string" ? args.sourceNodeId.trim() : "";
76110
+ const branch = typeof args?.branch === "string" ? args.branch.trim() : "";
76111
+ const baseBranch = typeof args?.baseBranch === "string" ? args.baseBranch.trim() : void 0;
76112
+ if (!meshId) return { success: false, error: "meshId required" };
76113
+ if (!sourceNodeId) return { success: false, error: "sourceNodeId required" };
76114
+ if (!branch) return { success: false, error: "branch required" };
76115
+ const ownerFailure = await ctx.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "worktree clone");
76116
+ if (ownerFailure) return ownerFailure;
76117
+ try {
76118
+ const meshRecord = await ctx.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
76119
+ const mesh = meshRecord?.mesh;
76120
+ if (!mesh) return { success: false, error: "Mesh not found" };
76121
+ const sourceNode = mesh.nodes?.find((n) => meshNodeIdMatches(n, sourceNodeId));
76122
+ if (!sourceNode) return { success: false, error: `Source node '${sourceNodeId}' not found in mesh` };
76123
+ const sourceDaemonId = typeof sourceNode.daemonId === "string" ? sourceNode.daemonId.trim() : void 0;
76124
+ if (sourceDaemonId && !daemonIdsEquivalent(sourceDaemonId, ctx.deps.statusInstanceId) && ctx.deps.dispatchMeshCommand && !args?._meshDirectDispatch) {
76125
+ const forwarded = await ctx.deps.dispatchMeshCommand(sourceDaemonId, "clone_mesh_node", {
76126
+ ...typeof args === "object" && args !== null ? args : {},
76127
+ _meshDirectDispatch: true
76128
+ });
76129
+ return forwarded ?? { success: false, error: "no response from remote node" };
76130
+ }
76131
+ const repoRoot = sourceNode.repoRoot || sourceNode.workspace;
76132
+ const { createWorktree: createWorktree2 } = await Promise.resolve().then(() => (init_git_worktree(), git_worktree_exports));
76133
+ const result = await createWorktree2({
76134
+ repoRoot,
76135
+ branch,
76136
+ baseBranch,
76137
+ meshName: mesh.name
76138
+ });
76139
+ let node;
76140
+ if (meshRecord.inline) {
76141
+ const { randomUUID: randomUUID15 } = await import("crypto");
76142
+ node = {
76143
+ id: `node_${randomUUID15().replace(/-/g, "")}`,
76144
+ workspace: result.worktreePath,
76145
+ repoRoot: result.worktreePath,
76146
+ daemonId: sourceNode.daemonId,
76147
+ machineId: sourceNode.machineId ?? sourceNode.machine_id,
76148
+ userOverrides: { ...sourceNode.userOverrides || {} },
76149
+ policy: { ...sourceNode.policy || {} },
76150
+ isLocalWorktree: true,
76151
+ worktreeBranch: result.branch,
76152
+ clonedFromNodeId: sourceNodeId
76153
+ };
76154
+ ctx.updateInlineMeshNode(meshId, mesh, node);
76155
+ } else {
76156
+ const { addNode: addNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
76157
+ node = addNode2(meshId, {
76158
+ workspace: result.worktreePath,
76159
+ repoRoot: result.worktreePath,
76160
+ daemonId: sourceNode.daemonId,
76161
+ machineId: sourceNode.machineId ?? sourceNode.machine_id,
76162
+ userOverrides: { ...sourceNode.userOverrides || {} },
76163
+ isLocalWorktree: true,
76164
+ worktreeBranch: result.branch,
76165
+ clonedFromNodeId: sourceNodeId,
76166
+ policy: { ...sourceNode.policy || {} }
76167
+ });
76168
+ if (!node) return { success: false, error: "Failed to register worktree node" };
76169
+ const inlineForReconcile = ctx.getCachedInlineMesh(meshId);
76170
+ if (inlineForReconcile) ctx.updateInlineMeshNode(meshId, inlineForReconcile, node);
76171
+ ctx.invalidateAggregateMeshStatus(meshId);
76172
+ }
76173
+ const persistWorktreeSetupState = async (bootstrapState2) => {
76174
+ node.worktreeBootstrap = bootstrapState2;
76175
+ if (meshRecord.inline) {
76176
+ ctx.updateInlineMeshNode(meshId, mesh, node);
76177
+ return;
76178
+ }
76179
+ try {
76180
+ const { updateNode: updateNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
76181
+ updateNode2(meshId, node.id, { worktreeBootstrap: bootstrapState2 });
76182
+ ctx.invalidateAggregateMeshStatus(meshId);
76183
+ } catch {
76184
+ }
76185
+ };
76186
+ const appendCloneLedger = async (initSubmodules2, bootstrapState2) => {
76187
+ try {
76188
+ const { appendLedgerEntry: appendLedgerEntry2 } = await Promise.resolve().then(() => (init_mesh_ledger(), mesh_ledger_exports));
76189
+ appendLedgerEntry2(meshId, {
76190
+ kind: "node_cloned",
76191
+ nodeId: node.id,
76192
+ payload: {
76193
+ sourceNodeId,
76194
+ branch: result.branch,
76195
+ worktreePath: result.worktreePath,
76196
+ submodulesInitialized: initSubmodules2,
76197
+ worktreeBootstrap: {
76198
+ status: bootstrapState2.status,
76199
+ required: bootstrapState2.required,
76200
+ configSource: bootstrapState2.configSource,
76201
+ configSourceType: bootstrapState2.configSourceType,
76202
+ lastCommand: bootstrapState2.lastCommand,
76203
+ exitCode: bootstrapState2.exitCode
76204
+ }
76205
+ }
76206
+ });
76207
+ } catch {
76208
+ }
76209
+ };
76210
+ const initSubmodules = sourceNode.policy?.initSubmodulesOnClone !== false;
76211
+ const loadedBootstrap = loadMeshWorktreeBootstrapConfig(mesh, result.worktreePath);
76212
+ const runningBootstrapState = {
76213
+ status: "running",
76214
+ required: loadedBootstrap.config?.required !== false,
76215
+ configSource: loadedBootstrap.path || loadedBootstrap.source,
76216
+ configSourceType: loadedBootstrap.sourceType,
76217
+ startedAt: (/* @__PURE__ */ new Date()).toISOString()
76218
+ };
76219
+ await persistWorktreeSetupState(runningBootstrapState);
76220
+ const finishWorktreeSetup = async () => {
76221
+ let submodulesInitialized2 = false;
76222
+ if (initSubmodules) {
76223
+ try {
76224
+ const { runGit: runGit3 } = await Promise.resolve().then(() => (init_git_executor(), git_executor_exports));
76225
+ await runGit3(
76226
+ { workspace: result.worktreePath, repoRoot: result.worktreePath, isGitRepo: true },
76227
+ ["submodule", "update", "--init", "--recursive"],
76228
+ { timeoutMs: 12e4 }
76229
+ );
76230
+ submodulesInitialized2 = true;
76231
+ const sourceWorkspace = sourceNode.repoRoot || sourceNode.workspace;
76232
+ if (sourceWorkspace) {
76233
+ try {
76234
+ const { runGit: rg } = await Promise.resolve().then(() => (init_git_executor(), git_executor_exports));
76235
+ const sourceCtx = { workspace: sourceWorkspace, repoRoot: sourceWorkspace, isGitRepo: true };
76236
+ const worktreeCtx = { workspace: result.worktreePath, repoRoot: result.worktreePath, isGitRepo: true };
76237
+ const sourceStatusOut = await rg(sourceCtx, ["submodule", "status", "oss"], { timeoutMs: 1e4 });
76238
+ const sourceStatusLine = (typeof sourceStatusOut === "string" ? sourceStatusOut : sourceStatusOut?.stdout ?? "").trim();
76239
+ const sourceShaMatch = sourceStatusLine.match(/^[+\- ]?([0-9a-f]{40})/);
76240
+ const sourceSha = sourceShaMatch?.[1];
76241
+ if (sourceSha) {
76242
+ const ossCtx = { workspace: `${result.worktreePath}/oss`, repoRoot: `${result.worktreePath}/oss`, isGitRepo: true };
76243
+ const worktreeOssHeadOut = await rg(ossCtx, ["rev-parse", "HEAD"], { timeoutMs: 1e4 });
76244
+ const worktreeOssSha = (typeof worktreeOssHeadOut === "string" ? worktreeOssHeadOut : worktreeOssHeadOut?.stdout ?? "").trim();
76245
+ if (worktreeOssSha !== sourceSha) {
76246
+ await rg(ossCtx, ["fetch", `${sourceWorkspace}/oss`, "HEAD"], { timeoutMs: 6e4 });
76247
+ await rg(ossCtx, ["checkout", sourceSha], { timeoutMs: 1e4 });
76248
+ await rg(worktreeCtx, ["add", "oss"], { timeoutMs: 1e4 });
76249
+ await rg(worktreeCtx, ["commit", "-m", "chore: sync oss to source node HEAD on clone"], { timeoutMs: 1e4 });
76250
+ console.log(`[mesh] Synced oss submodule to source HEAD ${sourceSha.slice(0, 8)} in worktree`);
76251
+ }
76252
+ }
76253
+ } catch (ossErr) {
76254
+ console.warn("[mesh] oss submodule sync to source HEAD failed (best-effort):", ossErr.message);
76255
+ }
76256
+ }
76257
+ } catch (subErr) {
76258
+ console.warn("[mesh] Submodule init failed for worktree:", subErr.message);
76259
+ }
76260
+ }
76261
+ const bootstrapState2 = await runMeshWorktreeBootstrap(mesh, result.worktreePath);
76262
+ await persistWorktreeSetupState(bootstrapState2);
76263
+ await appendCloneLedger(submodulesInitialized2, bootstrapState2);
76264
+ return { submodulesInitialized: submodulesInitialized2, bootstrapState: bootstrapState2 };
76265
+ };
76266
+ const requestedSetupWaitMs = Number(args?.setupWaitMs ?? args?.bootstrapWaitMs ?? 8e3);
76267
+ const setupWaitMs = Number.isFinite(requestedSetupWaitMs) ? Math.min(Math.max(requestedSetupWaitMs, 0), 14e3) : 8e3;
76268
+ const setupPromise = finishWorktreeSetup();
76269
+ const setupResult = await Promise.race([
76270
+ setupPromise.then((value) => ({ completed: true, value })),
76271
+ new Promise((resolve24) => setTimeout(() => resolve24({ completed: false }), setupWaitMs))
76272
+ ]);
76273
+ const emitBootstrapEvent = (eventStatus2, bootstrapState2, startedAtMs, extraPayload) => {
76274
+ try {
76275
+ const durationMs = Date.now() - startedAtMs;
76276
+ const event = `worktree_${eventStatus2}`;
76277
+ const metadataEvent = {
76278
+ source: "clone_mesh_node_bootstrap",
76279
+ nodeId: node.id,
76280
+ status: eventStatus2,
76281
+ worktreePath: result.worktreePath,
76282
+ durationMs,
76283
+ bootstrapStatus: bootstrapState2.status,
76284
+ ...bootstrapState2.error ? { error: bootstrapState2.error } : {},
76285
+ ...bootstrapState2.exitCode !== void 0 ? { exitCode: bootstrapState2.exitCode } : {},
76286
+ ...extraPayload || {}
76287
+ };
76288
+ if (typeof ctx.deps.instanceManager?.getByCategory === "function") {
76289
+ const forwarded = handleMeshForwardEvent(
76290
+ { instanceManager: ctx.deps.instanceManager },
76291
+ { event, meshId, nodeId: node.id, workspace: result.worktreePath, metadataEvent }
76292
+ );
76293
+ if (forwarded?.success === true) return;
76294
+ }
76295
+ queuePendingMeshCoordinatorEvent({
76296
+ event,
76297
+ meshId,
76298
+ nodeLabel: node.id,
76299
+ nodeId: node.id,
76300
+ workspace: result.worktreePath,
76301
+ metadataEvent,
76302
+ queuedAt: Date.now()
76303
+ });
76304
+ } catch {
76305
+ }
76306
+ };
76307
+ const bootstrapStartedMs = Date.now();
76308
+ if (!setupResult.completed) {
76309
+ setupPromise.then(({ bootstrapState: bootstrapState2 }) => {
76310
+ emitBootstrapEvent("bootstrap_complete", bootstrapState2, bootstrapStartedMs);
76311
+ }).catch((error48) => {
76312
+ const failedState = {
76313
+ ...runningBootstrapState,
76314
+ status: "failed",
76315
+ completedAt: (/* @__PURE__ */ new Date()).toISOString(),
76316
+ error: error48?.message || String(error48)
76317
+ };
76318
+ void persistWorktreeSetupState(failedState);
76319
+ void appendCloneLedger(false, failedState);
76320
+ emitBootstrapEvent("bootstrap_failed", failedState, bootstrapStartedMs, { error: error48?.message || String(error48) });
76321
+ });
76322
+ return {
76323
+ success: true,
76324
+ async: true,
76325
+ status: "accepted",
76326
+ node,
76327
+ worktreePath: result.worktreePath,
76328
+ branch: result.branch,
76329
+ worktreeBootstrap: runningBootstrapState,
76330
+ worktreeSetup: {
76331
+ status: "running",
76332
+ setupWaitMs,
76333
+ message: "Worktree node is registered; submodule/bootstrap setup is continuing in the background."
76334
+ }
76335
+ };
76336
+ }
76337
+ const { submodulesInitialized, bootstrapState } = setupResult.value;
76338
+ emitBootstrapEvent("bootstrap_complete", bootstrapState, bootstrapStartedMs);
76339
+ return {
76340
+ success: true,
76341
+ node,
76342
+ worktreePath: result.worktreePath,
76343
+ branch: result.branch,
76344
+ submodulesInitialized,
76345
+ worktreeBootstrap: bootstrapState
76346
+ };
76347
+ } catch (e) {
76348
+ return { success: false, error: e.message };
76349
+ }
76350
+ },
76351
+ retry_mesh_node_bootstrap: async (ctx, args) => {
76352
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76353
+ const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
76354
+ if (!meshId) return { success: false, error: "meshId required" };
76355
+ if (!nodeId) return { success: false, error: "nodeId required" };
76356
+ const ownerFailure = await ctx.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "bootstrap retry");
76357
+ if (ownerFailure) return ownerFailure;
76358
+ try {
76359
+ const meshRecord = await ctx.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
76360
+ const mesh = meshRecord?.mesh;
76361
+ if (!mesh) return { success: false, error: "Mesh not found" };
76362
+ const node = mesh.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
76363
+ if (!node) return { success: false, error: `Node '${nodeId}' not found in mesh` };
76364
+ if (!node.isLocalWorktree) return { success: false, error: "Node is not a local worktree node" };
76365
+ const nodeDaemonId = typeof node.daemonId === "string" ? node.daemonId.trim() : void 0;
76366
+ if (nodeDaemonId && !daemonIdsEquivalent(nodeDaemonId, ctx.deps.statusInstanceId) && ctx.deps.dispatchMeshCommand && !args?._meshDirectDispatch) {
76367
+ const forwarded = await ctx.deps.dispatchMeshCommand(nodeDaemonId, "retry_mesh_node_bootstrap", {
76368
+ ...typeof args === "object" && args !== null ? args : {},
76369
+ _meshDirectDispatch: true
76370
+ });
76371
+ return forwarded ?? { success: false, error: "no response from remote node" };
76372
+ }
76373
+ const currentBootstrap = node.worktreeBootstrap;
76374
+ if (currentBootstrap?.status === "running") {
76375
+ return { success: false, error: "Bootstrap is already running for this node" };
76376
+ }
76377
+ const worktreePath = node.workspace || node.repoRoot;
76378
+ if (!worktreePath) return { success: false, error: "Node has no workspace path" };
76379
+ const loadedBootstrap = loadMeshWorktreeBootstrapConfig(mesh, worktreePath);
76380
+ const runningState = {
76381
+ status: "running",
76382
+ required: loadedBootstrap.config?.required !== false,
76383
+ configSource: loadedBootstrap.path || loadedBootstrap.source,
76384
+ configSourceType: loadedBootstrap.sourceType,
76385
+ startedAt: (/* @__PURE__ */ new Date()).toISOString()
76386
+ };
76387
+ const persistState = async (bootstrapState2) => {
76388
+ node.worktreeBootstrap = bootstrapState2;
76389
+ if (meshRecord.inline) {
76390
+ ctx.updateInlineMeshNode(meshId, mesh, node);
76391
+ return;
76392
+ }
76393
+ try {
76394
+ const { updateNode: updateNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
76395
+ updateNode2(meshId, node.id, { worktreeBootstrap: bootstrapState2 });
76396
+ ctx.invalidateAggregateMeshStatus(meshId);
76397
+ } catch {
76398
+ }
76399
+ };
76400
+ await persistState(runningState);
76401
+ const bootstrapState = await runMeshWorktreeBootstrap(mesh, worktreePath);
76402
+ await persistState(bootstrapState);
76403
+ return { success: true, bootstrapState };
76404
+ } catch (e) {
76405
+ return { success: false, error: e.message };
76406
+ }
76407
+ }
76408
+ };
76409
+ init_mesh_host_ownership();
76410
+ var meshHostPairingHandlers = {
76411
+ get_mesh_host_pairing: async (ctx, args) => {
76412
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76413
+ if (!meshId) return { success: false, error: "meshId required" };
76414
+ const meshRecord = await ctx.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
76415
+ const mesh = meshRecord?.mesh;
76416
+ if (!mesh) return { success: false, error: "Mesh not found" };
76417
+ const meshHost = resolveMeshHostStatus(mesh);
76418
+ const pairingStatus = meshHost.pairing?.status || "not_configured";
76419
+ return {
76420
+ success: true,
76421
+ code: pairingStatus === "not_configured" ? "mesh_host_pairing_not_configured" : "mesh_host_pairing_pending",
76422
+ meshId,
76423
+ hostAddress: meshHost.hostAddress,
76424
+ meshHost,
76425
+ manualPairing: {
76426
+ status: pairingStatus,
76427
+ joinImplemented: true,
76428
+ protocol: "standalone_command_direct_v1",
76429
+ description: "Standalone manual pairing can save address/token metadata, apply a host join over direct standalone command HTTP or injected mesh command dispatch, and check persisted status. P2P signaling remains outside this slice."
76430
+ }
76431
+ };
76432
+ },
76433
+ configure_mesh_host_pairing: async (ctx, args) => {
76434
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76435
+ const hostAddress = typeof args?.hostAddress === "string" ? args.hostAddress.trim() : "";
76436
+ const token = typeof args?.token === "string" ? args.token.trim() : "";
76437
+ if (!meshId) return { success: false, error: "meshId required" };
76438
+ if (!hostAddress || !token) return { success: false, error: "hostAddress and token required" };
76439
+ try {
76440
+ const { configureMeshHostPairing: configureMeshHostPairing2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
76441
+ const configured = configureMeshHostPairing2(meshId, { hostAddress, token });
76442
+ if (!configured) return { success: false, error: "Mesh not found" };
76443
+ ctx.inlineMeshCache.set(meshId, configured.mesh);
76444
+ const meshHost = resolveMeshHostStatus(configured.mesh);
76445
+ return {
76446
+ success: true,
76447
+ code: "mesh_host_pairing_pending",
76448
+ meshId,
76449
+ hostAddress: configured.hostAddress,
76450
+ meshHost,
76451
+ manualPairing: {
76452
+ status: meshHost.pairing?.status || "pairing",
76453
+ joinImplemented: true,
76454
+ protocol: "standalone_command_direct_v1",
76455
+ description: "Manual Mesh Host pairing config was saved locally. Use join_mesh_host_pairing to apply it to the host. Raw token was not persisted."
76456
+ }
76457
+ };
76458
+ } catch (e) {
76459
+ return { success: false, code: "mesh_host_pairing_invalid", meshId, hostAddress, error: e.message };
76460
+ }
76461
+ },
76462
+ create_mesh_host_pairing_token: async (ctx, args) => {
76463
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76464
+ if (!meshId) return { success: false, error: "meshId required" };
76465
+ try {
76466
+ const { createMeshHostPairingToken: createMeshHostPairingToken2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
76467
+ const created = createMeshHostPairingToken2(meshId, {
76468
+ token: typeof args?.token === "string" ? args.token : void 0,
76469
+ expiresAt: typeof args?.expiresAt === "string" ? args.expiresAt : void 0
76470
+ });
76471
+ if (!created) return { success: false, error: "Mesh not found" };
76472
+ ctx.inlineMeshCache.set(meshId, created.mesh);
76473
+ ctx.invalidateAggregateMeshStatus(meshId);
76474
+ return {
76475
+ success: true,
76476
+ code: "mesh_host_pairing_token_created",
76477
+ meshId,
76478
+ token: created.token,
76479
+ tokenId: created.tokenId,
76480
+ expiresAt: created.expiresAt,
76481
+ meshHost: resolveMeshHostStatus(created.mesh),
76482
+ warning: "Raw token is returned once and is not persisted; share it with member daemons over a trusted channel."
76483
+ };
76484
+ } catch (e) {
76485
+ return { success: false, code: "mesh_host_pairing_token_invalid", meshId, error: e.message };
76486
+ }
76487
+ },
76488
+ apply_mesh_host_join: async (ctx, args) => {
76489
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76490
+ const token = typeof args?.token === "string" ? args.token.trim() : "";
76491
+ const memberNode = args?.memberNode && typeof args.memberNode === "object" && !Array.isArray(args.memberNode) ? args.memberNode : null;
76492
+ if (!meshId) return { success: false, error: "meshId required" };
76493
+ if (!token || !memberNode) return { success: false, error: "token and memberNode required" };
76494
+ try {
76495
+ const { applyMeshHostJoinRequest: applyMeshHostJoinRequest2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
76496
+ const applied = applyMeshHostJoinRequest2(meshId, {
76497
+ token,
76498
+ memberNode,
76499
+ memberMeshId: typeof args?.memberMeshId === "string" ? args.memberMeshId : void 0
76500
+ });
76501
+ if (!applied) return { success: false, error: "Mesh not found" };
76502
+ if (!applied.accepted) {
76503
+ return {
76504
+ success: false,
76505
+ code: "mesh_host_join_rejected",
76506
+ meshId,
76507
+ tokenId: applied.tokenId,
76508
+ meshHost: applied.meshHost ? resolveMeshHostStatus({ meshHost: applied.meshHost }) : void 0,
76509
+ error: applied.reason
76510
+ };
76511
+ }
76512
+ ctx.inlineMeshCache.set(meshId, applied.mesh);
76513
+ ctx.invalidateAggregateMeshStatus(meshId);
76514
+ try {
76515
+ const { appendLedgerEntry: appendLedgerEntry2 } = await Promise.resolve().then(() => (init_mesh_ledger(), mesh_ledger_exports));
76516
+ appendLedgerEntry2(meshId, {
76517
+ kind: "node_joined",
76518
+ nodeId: applied.node.id,
76519
+ payload: { role: "member", tokenId: applied.tokenId, workspace: applied.node.workspace }
76520
+ });
76521
+ } catch {
76522
+ }
76523
+ return {
76524
+ success: true,
76525
+ code: "mesh_host_join_accepted",
76526
+ meshId,
76527
+ node: applied.node,
76528
+ tokenId: applied.tokenId,
76529
+ meshHost: resolveMeshHostStatus(applied.mesh)
76530
+ };
76531
+ } catch (e) {
76532
+ return { success: false, code: "mesh_host_join_failed", meshId, error: e.message };
76533
+ }
76534
+ },
76535
+ join_mesh_host_pairing: async (ctx, args) => {
76536
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76537
+ const token = typeof args?.token === "string" ? args.token.trim() : "";
76538
+ if (!meshId) return { success: false, error: "meshId required" };
76539
+ if (!token) return { success: false, error: "token required because raw pairing tokens are not persisted" };
76540
+ const meshRecord = await ctx.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
76541
+ const mesh = meshRecord?.mesh;
76542
+ if (!mesh) return { success: false, error: "Mesh not found" };
76543
+ const meshHost = resolveMeshHostStatus(mesh);
76544
+ if (meshHost.role !== "member") {
76545
+ return { success: false, code: "mesh_host_join_not_member", meshId, meshHost, error: "join_mesh_host_pairing must run from a member daemon configured with a Mesh Host address/token." };
76546
+ }
76547
+ try {
76548
+ const { tokenIdForManualPairing: tokenIdForManualPairing2, markMeshHostPairingJoined: markMeshHostPairingJoined2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
76549
+ const tokenId = tokenIdForManualPairing2(token);
76550
+ if (meshHost.pairing?.tokenId && meshHost.pairing.tokenId !== tokenId) {
76551
+ return { success: false, code: "mesh_host_join_rejected", meshId, tokenId, meshHost, error: "invalid pairing token" };
76552
+ }
76553
+ const memberNode = buildMemberJoinNode(mesh, args, ctx.deps.statusInstanceId);
76554
+ if (!memberNode) return { success: false, error: "member node metadata unavailable" };
76555
+ const hostMeshId = typeof args?.hostMeshId === "string" && args.hostMeshId.trim() ? args.hostMeshId.trim() : meshId;
76556
+ const hostDaemonId = typeof args?.hostDaemonId === "string" && args.hostDaemonId.trim() ? args.hostDaemonId.trim() : meshHost.hostDaemonId;
76557
+ let hostResult;
76558
+ let transport;
76559
+ if (hostDaemonId && ctx.deps.dispatchMeshCommand) {
76560
+ transport = "mesh_command_dispatch";
76561
+ hostResult = await ctx.deps.dispatchMeshCommand(hostDaemonId, "apply_mesh_host_join", {
76562
+ meshId: hostMeshId,
76563
+ token,
76564
+ memberMeshId: meshId,
76565
+ memberNode
76566
+ });
76567
+ } else if (meshHost.hostAddress) {
76568
+ transport = "standalone_http_command";
76569
+ const commandUrl = normalizeStandaloneHostCommandUrl(meshHost.hostAddress);
76570
+ const response = await fetch(commandUrl, {
76571
+ method: "POST",
76572
+ headers: { "Content-Type": "application/json" },
76573
+ body: JSON.stringify({ type: "apply_mesh_host_join", payload: { meshId: hostMeshId, token, memberMeshId: meshId, memberNode } })
76574
+ });
76575
+ hostResult = await response.json().catch(() => ({ success: false, error: `Host returned HTTP ${response.status}` }));
76576
+ if (!response.ok && hostResult?.success !== false) hostResult = { success: false, error: `Host returned HTTP ${response.status}` };
76577
+ } else {
76578
+ return {
76579
+ success: false,
76580
+ code: "mesh_host_join_transport_unavailable",
76581
+ meshId,
76582
+ meshHost,
76583
+ error: "No hostDaemonId dispatch path or hostAddress HTTP command path is available. P2P signaling join is not implemented in this slice."
76584
+ };
76585
+ }
76586
+ if (!hostResult?.success) {
76587
+ return { success: false, code: hostResult?.code || "mesh_host_join_rejected", meshId, meshHost, transport, error: hostResult?.error || "Mesh Host rejected join request", hostResult };
76588
+ }
76589
+ const joined = meshRecord.inline ? null : markMeshHostPairingJoined2(meshId, {
76590
+ tokenId: hostResult.tokenId || tokenId,
76591
+ hostDaemonId: hostResult.meshHost?.hostDaemonId || hostDaemonId,
76592
+ hostNodeId: hostResult.meshHost?.hostNodeId,
76593
+ joinedAt: hostResult.meshHost?.pairing?.joinedAt
76594
+ });
76595
+ if (joined) {
76596
+ ctx.inlineMeshCache.set(meshId, joined.mesh);
76597
+ ctx.invalidateAggregateMeshStatus(meshId);
76598
+ }
76599
+ return {
76600
+ success: true,
76601
+ code: "mesh_host_join_applied",
76602
+ meshId,
76603
+ hostMeshId,
76604
+ transport,
76605
+ node: hostResult.node,
76606
+ tokenId: hostResult.tokenId || tokenId,
76607
+ meshHost: joined ? resolveMeshHostStatus(joined.mesh) : { ...meshHost, pairing: { ...meshHost.pairing || {}, status: "paired", tokenId: hostResult.tokenId || tokenId } },
76608
+ hostResult,
76609
+ manualPairing: {
76610
+ status: "paired",
76611
+ joinImplemented: true,
76612
+ protocol: "standalone_command_direct_v1",
76613
+ description: "Mesh Host accepted the join and local member pairing status was marked paired. P2P runtime signaling remains outside this slice."
76614
+ }
76615
+ };
76616
+ } catch (e) {
76617
+ return { success: false, code: "mesh_host_join_failed", meshId, meshHost, error: e.message };
76618
+ }
76619
+ }
76620
+ };
76621
+ var meshQueueHandlers = {
76622
+ get_mesh_queue: async (_ctx, args) => {
76623
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76624
+ if (!meshId) return { success: false, error: "meshId required" };
76625
+ try {
76626
+ const { getMeshQueueStats: getMeshQueueStats2, getQueue: getQueue2, describeTaskDependencyState: describeTaskDependencyState2 } = await Promise.resolve().then(() => (init_mesh_work_queue(), mesh_work_queue_exports));
76627
+ const status = Array.isArray(args?.status) ? args.status.map((s2) => typeof s2 === "string" ? s2.trim() : "").filter(Boolean) : void 0;
76628
+ const rawQueue = getQueue2(meshId, { status });
76629
+ const statusById = new Map(getQueue2(meshId).map((task) => [task.id, task.status]));
76630
+ const queue = rawQueue.map((task) => Array.isArray(task.dependsOn) && task.dependsOn.length > 0 ? { ...task, ...describeTaskDependencyState2(task, statusById) } : task);
76631
+ const summary = getMeshQueueStats2(meshId);
76632
+ return {
76633
+ success: true,
76634
+ queue,
76635
+ summary,
76636
+ sourceOfTruth: {
76637
+ kind: "mesh_work_queue_file",
76638
+ activeStatuses: ["pending", "assigned"],
76639
+ historicalStatuses: ["completed", "failed", "cancelled"],
76640
+ notes: "pending/assigned are active work; completed/failed/cancelled are historical records."
76641
+ }
76642
+ };
76643
+ } catch (e) {
76644
+ return { success: false, error: e.message };
76645
+ }
76646
+ },
76647
+ cancel_mesh_queue_task: async (ctx, args) => {
76648
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76649
+ const taskId = typeof args?.taskId === "string" ? args.taskId.trim() : "";
76650
+ if (!meshId || !taskId) return { success: false, error: "meshId and taskId required" };
76651
+ const ownerFailure = await ctx.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "queue cancellation");
76652
+ if (ownerFailure) return ownerFailure;
76653
+ try {
76654
+ const { cancelTask: cancelTask2 } = await Promise.resolve().then(() => (init_mesh_work_queue(), mesh_work_queue_exports));
76655
+ const reason = typeof args?.reason === "string" ? args.reason : void 0;
76656
+ const task = cancelTask2(meshId, taskId, { reason });
76657
+ if (!task) return { success: false, error: `Queue task '${taskId}' not found` };
76658
+ return { success: true, task };
76659
+ } catch (e) {
76660
+ return { success: false, error: e.message };
76661
+ }
76662
+ },
76663
+ requeue_mesh_queue_task: async (ctx, args) => {
76664
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76665
+ const taskId = typeof args?.taskId === "string" ? args.taskId.trim() : "";
76666
+ if (!meshId || !taskId) return { success: false, error: "meshId and taskId required" };
76667
+ const ownerFailure = await ctx.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "queue requeue");
76668
+ if (ownerFailure) return ownerFailure;
76669
+ try {
76670
+ const { requeueTask: requeueTask2 } = await Promise.resolve().then(() => (init_mesh_work_queue(), mesh_work_queue_exports));
76671
+ const task = requeueTask2(meshId, taskId, {
76672
+ reason: typeof args?.reason === "string" ? args.reason : void 0,
76673
+ targetNodeId: typeof args?.targetNodeId === "string" ? args.targetNodeId.trim() : void 0,
76674
+ targetSessionId: typeof args?.targetSessionId === "string" ? args.targetSessionId.trim() : void 0,
76675
+ clearTargetNode: args?.clearTargetNode === true,
76676
+ clearTargetSession: args?.clearTargetSession !== false
76677
+ });
76678
+ if (!task) return { success: false, error: `Queue task '${taskId}' not found` };
76679
+ return { success: true, task };
76680
+ } catch (e) {
76681
+ return { success: false, error: e.message };
76682
+ }
76683
+ },
76684
+ trigger_mesh_queue: async (ctx, args) => {
76685
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76686
+ if (!meshId) return { success: false, error: "meshId required" };
76687
+ const ownerFailure = await ctx.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "queue trigger");
76688
+ if (ownerFailure) return ownerFailure;
76689
+ try {
76690
+ const { triggerMeshQueue: triggerMeshQueue2, tryAssignQueueTask: tryAssignQueueTask2 } = await Promise.resolve().then(() => (init_mesh_events(), mesh_events_exports));
76691
+ const preferredNodeId = typeof args?.preferredNodeId === "string" ? args.preferredNodeId.trim() : "";
76692
+ if (preferredNodeId) {
76693
+ const cliInstances = ctx.deps.instanceManager.getByCategory("cli");
76694
+ const sorted = [...cliInstances].sort((a, b) => {
76695
+ const aSettings = a.getState().settings || {};
76696
+ const bSettings = b.getState().settings || {};
76697
+ const aNode = readStringValue(aSettings.meshNodeId, aSettings.nodeId);
76698
+ const bNode = readStringValue(bSettings.meshNodeId, bSettings.nodeId);
76699
+ return (aNode === preferredNodeId ? -1 : 0) - (bNode === preferredNodeId ? -1 : 0);
76700
+ });
76701
+ for (const inst of sorted) {
76702
+ const state = inst.getState();
76703
+ const settings = state.settings || {};
76704
+ const nodeId = readStringValue(settings.meshNodeId, settings.nodeId);
76705
+ if (!nodeId || nodeId !== preferredNodeId) continue;
76706
+ const meshNodeFor = readStringValue(settings.meshNodeFor);
76707
+ if (meshNodeFor !== meshId) continue;
76708
+ const status = (readStringValue(state.status) || "").toLowerCase();
76709
+ if (status !== "idle") continue;
76710
+ const sessionId = typeof state.instanceId === "string" ? state.instanceId : "";
76711
+ const providerType = readStringValue(state.type, settings.providerType) || "";
76712
+ if (sessionId && providerType) {
76713
+ tryAssignQueueTask2(ctx.deps, meshId, nodeId, sessionId, providerType);
76714
+ break;
76715
+ }
76716
+ }
76717
+ }
76718
+ const trigger = await triggerMeshQueue2(ctx.deps, meshId);
76719
+ return { success: true, trigger };
76720
+ } catch (e) {
76721
+ return { success: false, error: e.message };
76722
+ }
76723
+ }
76724
+ };
76725
+ init_dist();
76726
+ init_mesh_fast_forward();
76727
+ var import_fs16 = require("fs");
76728
+ var import_path11 = require("path");
76729
+ var MESH_INIT_REFINE_CONFIG_PATH = MESH_REFINE_CONFIG_LOCATIONS[0];
76730
+ var MESH_INIT_WORKTREE_BOOTSTRAP_CONFIG_PATH = MESH_WORKTREE_BOOTSTRAP_CONFIG_LOCATIONS[0];
76731
+ var CANDIDATE_STALE_INPUTS = [
76732
+ "package-lock.json",
76733
+ "pnpm-lock.yaml",
76734
+ "yarn.lock",
76735
+ "bun.lockb",
76736
+ "Cargo.lock",
76737
+ "go.sum",
76738
+ "poetry.lock",
76739
+ "requirements.txt"
76740
+ ];
76741
+ function writeConfigFile(workspace, relativePath, config2) {
76742
+ const target = (0, import_path11.join)(workspace, relativePath);
76743
+ (0, import_fs16.mkdirSync)((0, import_path11.dirname)(target), { recursive: true });
76744
+ (0, import_fs16.writeFileSync)(target, `${JSON.stringify(config2, null, 2)}
76745
+ `, "utf-8");
76746
+ return target;
76747
+ }
76748
+ function suggestMeshWorktreeBootstrapConfig(workspace) {
76749
+ const commands = [];
76750
+ const hasPackageJson = (0, import_fs16.existsSync)((0, import_path11.join)(workspace, "package.json"));
76751
+ const hasNpmLock = (0, import_fs16.existsSync)((0, import_path11.join)(workspace, "package-lock.json"));
76752
+ if (hasPackageJson) {
76753
+ commands.push(
76754
+ hasNpmLock ? { command: "npm", args: ["ci"] } : { command: "npm", args: ["install"] }
76755
+ );
76756
+ }
76757
+ const staleInputs = CANDIDATE_STALE_INPUTS.filter((relative5) => (0, import_fs16.existsSync)((0, import_path11.join)(workspace, relative5)));
76758
+ if (!commands.length) {
76759
+ return { commands, staleInputs };
76760
+ }
76761
+ return {
76762
+ commands,
76763
+ staleInputs,
76764
+ suggestedConfig: {
76765
+ version: 1,
76766
+ enabled: true,
76767
+ runOnClone: true,
76768
+ required: false,
76769
+ commands,
76770
+ ...staleInputs.length ? { staleInputs } : {}
76771
+ }
76772
+ };
76773
+ }
76774
+ var PROVIDER_PRIORITY_PREFERENCE = ["claude-cli", "codex-cli", "gemini-cli"];
76775
+ function suggestNodeProviderPriority(detected) {
76776
+ const installed = detected.filter((cli) => cli.installed);
76777
+ const installedIds = installed.map((cli) => cli.id);
76778
+ const preferred = PROVIDER_PRIORITY_PREFERENCE.filter((id) => installedIds.includes(id));
76779
+ const rest = installedIds.filter((id) => !preferred.includes(id));
76780
+ const providerPriority = [...preferred, ...rest];
76781
+ return {
76782
+ providerPriority,
76783
+ installedProviders: installed.map((cli) => ({
76784
+ id: cli.id,
76785
+ displayName: cli.displayName,
76786
+ ...cli.version ? { version: cli.version } : {}
76787
+ }))
76788
+ };
76789
+ }
76790
+ function runMeshInit(mesh, workspace, detected, options = {}) {
76791
+ const write = options.write === true;
76792
+ const overwrite = options.overwrite === true;
76793
+ const refine2 = applyConfigSuggestion({
76794
+ workspace,
76795
+ relativePath: MESH_INIT_REFINE_CONFIG_PATH,
76796
+ existing: loadMeshRefineConfig(mesh, workspace).config,
76797
+ suggestedConfig: suggestMeshRefineConfig(mesh, workspace).suggestedConfig,
76798
+ validate: (config2) => validateMeshRefineConfig(config2, MESH_INIT_REFINE_CONFIG_PATH).valid,
76799
+ write,
76800
+ overwrite
76801
+ });
76802
+ const bootstrapSuggestion = suggestMeshWorktreeBootstrapConfig(workspace);
76803
+ const worktreeBootstrap = applyConfigSuggestion({
76804
+ workspace,
76805
+ relativePath: MESH_INIT_WORKTREE_BOOTSTRAP_CONFIG_PATH,
76806
+ existing: loadMeshWorktreeBootstrapConfig(mesh, workspace).config,
76807
+ suggestedConfig: bootstrapSuggestion.suggestedConfig,
76808
+ validate: (config2) => validateMeshWorktreeBootstrapConfig(config2, MESH_INIT_WORKTREE_BOOTSTRAP_CONFIG_PATH).valid,
76809
+ write,
76810
+ overwrite
76811
+ });
76812
+ const providers = suggestNodeProviderPriority(detected);
76813
+ return {
76814
+ success: true,
76815
+ workspace,
76816
+ dryRun: !write,
76817
+ refine: refine2,
76818
+ worktreeBootstrap,
76819
+ providers,
76820
+ note: write ? "Configs written to disk are the execution source of truth; suggestions are scaffold and only take effect once saved. providerPriority is a recommendation \u2014 apply it to node policy via clone/policy update." : "Dry-run: no files written. Re-run with write=true to persist the suggested configs. Heuristic suggestions never execute until saved as repo config."
76821
+ };
76822
+ }
76823
+ function applyConfigSuggestion(input) {
76824
+ const { workspace, relativePath, existing, suggestedConfig, validate, write, overwrite } = input;
76825
+ const absolute = (0, import_path11.join)(workspace, relativePath);
76826
+ if (existing !== void 0 && !overwrite) {
76827
+ return { path: absolute, relativePath, written: false, skippedReason: "already_exists", config: existing };
76828
+ }
76829
+ if (!suggestedConfig || !validate(suggestedConfig)) {
76830
+ return { path: absolute, relativePath, written: false, skippedReason: "no_suggestion" };
76831
+ }
76832
+ if (!write) {
76833
+ return { path: absolute, relativePath, written: false, config: suggestedConfig };
76834
+ }
76835
+ const writtenPath = writeConfigFile(workspace, relativePath, suggestedConfig);
76836
+ return { path: writtenPath, relativePath, written: true, config: suggestedConfig };
76837
+ }
76838
+ init_cli_detector();
76839
+ var fastForwardHandlers = {
76840
+ mesh_init: async (ctx, args) => {
76841
+ const workspace = typeof args?.workspace === "string" && args.workspace.trim() ? args.workspace.trim() : process.cwd();
76842
+ const mesh = args?.inlineMesh || {};
76843
+ try {
76844
+ const detected = await detectCLIs(ctx.deps.providerLoader, { includeVersion: true });
76845
+ return { ...runMeshInit(mesh, workspace, detected, {
76846
+ write: args?.write === true,
76847
+ overwrite: args?.overwrite === true
76848
+ }) };
76849
+ } catch (e) {
76850
+ return { success: false, error: e?.message || String(e) };
76851
+ }
76852
+ },
76853
+ plan_mesh_refine_node: async (ctx, args) => {
76854
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76855
+ const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
76856
+ if (!meshId || !nodeId) return { success: false, error: "meshId and nodeId required" };
76857
+ const meshRecord = await ctx.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
76858
+ const mesh = meshRecord?.mesh;
76859
+ const node = mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
76860
+ if (!node?.workspace) return { success: false, error: `Node '${nodeId}' workspace not found` };
76861
+ return {
76862
+ success: true,
76863
+ dryRun: true,
76864
+ nodeId,
76865
+ workspace: node.workspace,
76866
+ validationPlan: buildMeshRefineValidationPlan(mesh, node.workspace),
76867
+ mergeWillRun: false,
76868
+ cleanupWillRun: false
76869
+ };
76870
+ },
76871
+ fast_forward_mesh_node: async (ctx, args) => {
76872
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76873
+ const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
76874
+ let workspace = typeof args?.workspace === "string" ? args.workspace.trim() : "";
76875
+ let submoduleIgnorePaths = Array.isArray(args?.submoduleIgnorePaths) ? args.submoduleIgnorePaths.filter((value) => typeof value === "string") : void 0;
76876
+ let nodeDaemonId;
76877
+ let allowAutoPublishSubmoduleMainCommits = false;
76878
+ if (meshId && nodeId) {
76879
+ const meshRecord = await ctx.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
76880
+ const mesh = meshRecord?.mesh;
76881
+ const node = mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
76882
+ if (!workspace) {
76883
+ workspace = typeof node?.workspace === "string" ? node.workspace.trim() : "";
76884
+ }
76885
+ if (!submoduleIgnorePaths && Array.isArray(node?.policy?.submoduleIgnorePaths)) {
76886
+ submoduleIgnorePaths = node.policy.submoduleIgnorePaths.filter((value) => typeof value === "string");
76887
+ }
76888
+ allowAutoPublishSubmoduleMainCommits = mesh?.policy?.allowAutoPublishSubmoduleMainCommits === true;
76889
+ nodeDaemonId = typeof node?.daemonId === "string" ? node.daemonId.trim() : void 0;
76890
+ }
76891
+ const selfDaemonId = ctx.deps.statusInstanceId;
76892
+ const isRemote = nodeDaemonId && selfDaemonId && !daemonIdsEquivalent(nodeDaemonId, selfDaemonId);
76893
+ if (isRemote && ctx.deps.dispatchMeshCommand && !args?._meshDirectDispatch) {
76894
+ const forwarded = await ctx.deps.dispatchMeshCommand(nodeDaemonId, "fast_forward_mesh_node", {
76895
+ ...typeof args === "object" && args !== null ? args : {},
76896
+ workspace,
76897
+ _meshDirectDispatch: true
76898
+ });
76899
+ return forwarded ?? { success: false, error: "no response from remote node" };
76900
+ }
76901
+ const result = await fastForwardMeshNode({
76902
+ meshId: meshId || void 0,
76903
+ nodeId: nodeId || void 0,
76904
+ workspace,
76905
+ branch: typeof args?.branch === "string" ? args.branch : void 0,
76906
+ execute: args?.execute === true,
76907
+ dryRun: args?.dryRun === true,
76908
+ updateSubmodules: args?.updateSubmodules === true,
76909
+ submoduleIgnorePaths,
76910
+ mode: args?.mode === "push" ? "push" : "merge",
76911
+ pushSubmodules: args?.pushSubmodules === true,
76912
+ allowAutoPublishSubmoduleMainCommits
76913
+ });
76914
+ return result;
76915
+ },
76916
+ refine_mesh_node: async (ctx, args) => {
76917
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76918
+ const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
76919
+ if (!meshId || !nodeId) return { success: false, error: "meshId and nodeId required" };
76920
+ {
76921
+ const meshRecordForForward = await ctx.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
76922
+ const forwardNode = meshRecordForForward?.mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
76923
+ const nodeDaemonId = typeof forwardNode?.daemonId === "string" ? forwardNode.daemonId.trim() : void 0;
76924
+ const selfDaemonId = ctx.deps.statusInstanceId;
76925
+ const isRemote = nodeDaemonId && selfDaemonId && !daemonIdsEquivalent(nodeDaemonId, selfDaemonId);
76926
+ if (isRemote && ctx.deps.dispatchMeshCommand && !args?._meshDirectDispatch) {
76927
+ const callerCoordinatorDaemonId = typeof args?.coordinatorDaemonId === "string" && args.coordinatorDaemonId.trim() ? args.coordinatorDaemonId.trim() : void 0;
76928
+ const forwarded = await ctx.deps.dispatchMeshCommand(nodeDaemonId, "refine_mesh_node", {
76929
+ ...typeof args === "object" && args !== null ? args : {},
76930
+ coordinatorDaemonId: callerCoordinatorDaemonId || selfDaemonId,
76931
+ _meshDirectDispatch: true
76932
+ });
76933
+ return forwarded ?? { success: false, error: "no response from remote node" };
76934
+ }
76935
+ }
76936
+ const isDryRun = args?.dryRun !== false && args?.execute !== true;
76937
+ if (isDryRun) {
76938
+ const meshRecord = await ctx.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
76939
+ const mesh = meshRecord?.mesh;
76940
+ const node = mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
76941
+ if (!node?.workspace) return { success: false, error: `Node '${nodeId}' workspace not found` };
76942
+ return {
76943
+ success: true,
76944
+ dryRun: true,
76945
+ nodeId,
76946
+ workspace: node.workspace,
76947
+ validationPlan: buildMeshRefineValidationPlan(mesh, node.workspace),
76948
+ mergeWillRun: false,
76949
+ cleanupWillRun: false,
76950
+ hint: "Dry-run only \u2014 no merge/push/cleanup performed. Re-invoke with execute:true to converge this node."
76951
+ };
76952
+ }
76953
+ return ctx.startMeshRefineJob(meshId, nodeId, args);
76954
+ },
76955
+ batch_refine_mesh_nodes: async (ctx, args) => {
76956
+ const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
76957
+ if (!meshId) return { success: false, error: "meshId required" };
76958
+ const requestedNodeIds = Array.isArray(args?.nodeIds) ? args.nodeIds.filter((v) => typeof v === "string" && v.trim().length > 0).map((v) => v.trim()) : void 0;
76959
+ const isDryRun = args?.dryRun !== false && args?.execute !== true;
76960
+ if (isDryRun) return ctx.batchRefineMeshNodes(meshId, requestedNodeIds, args);
76961
+ return ctx.startMeshRefineBatchJob(meshId, requestedNodeIds, args);
76962
+ }
76963
+ };
76964
+ var medFamilyRegistry = new Map(
76965
+ Object.entries({
76966
+ ...cliAgentHandlers,
76967
+ ...ideHandlers,
76968
+ ...meshCrudHandlers,
76969
+ ...meshHostPairingHandlers,
76970
+ ...meshQueueHandlers,
76971
+ ...fastForwardHandlers
76972
+ })
76973
+ );
76974
+ init_config();
76975
+ init_cli_detector();
75531
76976
  init_git_status();
75532
76977
  init_dist();
75533
76978
  init_logger();
@@ -75679,9 +77124,7 @@ ${formatManifestValidationIssues2(validation2.issues)}`);
75679
77124
  init_coordinator_registry();
75680
77125
  init_mesh_events();
75681
77126
  init_mesh_routing();
75682
- init_mesh_events_utils();
75683
77127
  init_mesh_host_ownership();
75684
- init_mesh_fast_forward();
75685
77128
  var import_node_child_process4 = require("child_process");
75686
77129
  var import_node_util4 = require("util");
75687
77130
  var execFileAsync3 = (0, import_node_util4.promisify)(import_node_child_process4.execFile);
@@ -75848,117 +77291,6 @@ ${formatManifestValidationIssues2(validation2.issues)}`);
75848
77291
  };
75849
77292
  }
75850
77293
  init_mesh_refine_status();
75851
- var import_fs16 = require("fs");
75852
- var import_path11 = require("path");
75853
- var MESH_INIT_REFINE_CONFIG_PATH = MESH_REFINE_CONFIG_LOCATIONS[0];
75854
- var MESH_INIT_WORKTREE_BOOTSTRAP_CONFIG_PATH = MESH_WORKTREE_BOOTSTRAP_CONFIG_LOCATIONS[0];
75855
- var CANDIDATE_STALE_INPUTS = [
75856
- "package-lock.json",
75857
- "pnpm-lock.yaml",
75858
- "yarn.lock",
75859
- "bun.lockb",
75860
- "Cargo.lock",
75861
- "go.sum",
75862
- "poetry.lock",
75863
- "requirements.txt"
75864
- ];
75865
- function writeConfigFile(workspace, relativePath, config2) {
75866
- const target = (0, import_path11.join)(workspace, relativePath);
75867
- (0, import_fs16.mkdirSync)((0, import_path11.dirname)(target), { recursive: true });
75868
- (0, import_fs16.writeFileSync)(target, `${JSON.stringify(config2, null, 2)}
75869
- `, "utf-8");
75870
- return target;
75871
- }
75872
- function suggestMeshWorktreeBootstrapConfig(workspace) {
75873
- const commands = [];
75874
- const hasPackageJson = (0, import_fs16.existsSync)((0, import_path11.join)(workspace, "package.json"));
75875
- const hasNpmLock = (0, import_fs16.existsSync)((0, import_path11.join)(workspace, "package-lock.json"));
75876
- if (hasPackageJson) {
75877
- commands.push(
75878
- hasNpmLock ? { command: "npm", args: ["ci"] } : { command: "npm", args: ["install"] }
75879
- );
75880
- }
75881
- const staleInputs = CANDIDATE_STALE_INPUTS.filter((relative5) => (0, import_fs16.existsSync)((0, import_path11.join)(workspace, relative5)));
75882
- if (!commands.length) {
75883
- return { commands, staleInputs };
75884
- }
75885
- return {
75886
- commands,
75887
- staleInputs,
75888
- suggestedConfig: {
75889
- version: 1,
75890
- enabled: true,
75891
- runOnClone: true,
75892
- required: false,
75893
- commands,
75894
- ...staleInputs.length ? { staleInputs } : {}
75895
- }
75896
- };
75897
- }
75898
- var PROVIDER_PRIORITY_PREFERENCE = ["claude-cli", "codex-cli", "gemini-cli"];
75899
- function suggestNodeProviderPriority(detected) {
75900
- const installed = detected.filter((cli) => cli.installed);
75901
- const installedIds = installed.map((cli) => cli.id);
75902
- const preferred = PROVIDER_PRIORITY_PREFERENCE.filter((id) => installedIds.includes(id));
75903
- const rest = installedIds.filter((id) => !preferred.includes(id));
75904
- const providerPriority = [...preferred, ...rest];
75905
- return {
75906
- providerPriority,
75907
- installedProviders: installed.map((cli) => ({
75908
- id: cli.id,
75909
- displayName: cli.displayName,
75910
- ...cli.version ? { version: cli.version } : {}
75911
- }))
75912
- };
75913
- }
75914
- function runMeshInit(mesh, workspace, detected, options = {}) {
75915
- const write = options.write === true;
75916
- const overwrite = options.overwrite === true;
75917
- const refine2 = applyConfigSuggestion({
75918
- workspace,
75919
- relativePath: MESH_INIT_REFINE_CONFIG_PATH,
75920
- existing: loadMeshRefineConfig(mesh, workspace).config,
75921
- suggestedConfig: suggestMeshRefineConfig(mesh, workspace).suggestedConfig,
75922
- validate: (config2) => validateMeshRefineConfig(config2, MESH_INIT_REFINE_CONFIG_PATH).valid,
75923
- write,
75924
- overwrite
75925
- });
75926
- const bootstrapSuggestion = suggestMeshWorktreeBootstrapConfig(workspace);
75927
- const worktreeBootstrap = applyConfigSuggestion({
75928
- workspace,
75929
- relativePath: MESH_INIT_WORKTREE_BOOTSTRAP_CONFIG_PATH,
75930
- existing: loadMeshWorktreeBootstrapConfig(mesh, workspace).config,
75931
- suggestedConfig: bootstrapSuggestion.suggestedConfig,
75932
- validate: (config2) => validateMeshWorktreeBootstrapConfig(config2, MESH_INIT_WORKTREE_BOOTSTRAP_CONFIG_PATH).valid,
75933
- write,
75934
- overwrite
75935
- });
75936
- const providers = suggestNodeProviderPriority(detected);
75937
- return {
75938
- success: true,
75939
- workspace,
75940
- dryRun: !write,
75941
- refine: refine2,
75942
- worktreeBootstrap,
75943
- providers,
75944
- note: write ? "Configs written to disk are the execution source of truth; suggestions are scaffold and only take effect once saved. providerPriority is a recommendation \u2014 apply it to node policy via clone/policy update." : "Dry-run: no files written. Re-run with write=true to persist the suggested configs. Heuristic suggestions never execute until saved as repo config."
75945
- };
75946
- }
75947
- function applyConfigSuggestion(input) {
75948
- const { workspace, relativePath, existing, suggestedConfig, validate, write, overwrite } = input;
75949
- const absolute = (0, import_path11.join)(workspace, relativePath);
75950
- if (existing !== void 0 && !overwrite) {
75951
- return { path: absolute, relativePath, written: false, skippedReason: "already_exists", config: existing };
75952
- }
75953
- if (!suggestedConfig || !validate(suggestedConfig)) {
75954
- return { path: absolute, relativePath, written: false, skippedReason: "no_suggestion" };
75955
- }
75956
- if (!write) {
75957
- return { path: absolute, relativePath, written: false, config: suggestedConfig };
75958
- }
75959
- const writtenPath = writeConfigFile(workspace, relativePath, suggestedConfig);
75960
- return { path: writtenPath, relativePath, written: true, config: suggestedConfig };
75961
- }
75962
77294
  init_mesh_work_queue();
75963
77295
  init_repo_mesh_types();
75964
77296
  var import_os3 = require("os");
@@ -78510,6 +79842,37 @@ ${mergeTreeErr?.stderr || ""}`;
78510
79842
  this.aggregateMeshStatusCache.delete(meshId);
78511
79843
  this.deps.onMeshStateChange?.(meshId);
78512
79844
  }
79845
+ /**
79846
+ * Build the MedFamilyContext handed to RF-ROUTER MED family handlers. Binds the
79847
+ * router-private collaborators those handlers need (mesh resolution, owner
79848
+ * gating, inline-cache mutation, worktree / session cleanup, refine job
79849
+ * starters, IDE stop/launch) plus the inline-mesh and git-probe caches. The
79850
+ * `launchIde` field closes over the freshly-built context so restart_session /
79851
+ * restart_ide invoke the IDE launch directly instead of recursing through
79852
+ * executeDaemonCommand('launch_ide').
79853
+ */
79854
+ buildMedFamilyContext() {
79855
+ const ctx = {
79856
+ deps: this.deps,
79857
+ getMeshForCommand: this.getMeshForCommand.bind(this),
79858
+ getCachedInlineMesh: this.getCachedInlineMesh.bind(this),
79859
+ requireMeshHostMutationOwner: this.requireMeshHostMutationOwner.bind(this),
79860
+ invalidateAggregateMeshStatus: this.invalidateAggregateMeshStatus.bind(this),
79861
+ updateInlineMeshNode: this.updateInlineMeshNode.bind(this),
79862
+ removeInlineMeshNode: this.removeInlineMeshNode.bind(this),
79863
+ normalizeMeshSessionCleanupMode: this.normalizeMeshSessionCleanupMode.bind(this),
79864
+ cleanupMeshSessions: this.cleanupMeshSessions.bind(this),
79865
+ cleanupLocalWorktreeNode: this.cleanupLocalWorktreeNode.bind(this),
79866
+ startMeshRefineJob: this.startMeshRefineJob.bind(this),
79867
+ batchRefineMeshNodes: this.batchRefineMeshNodes.bind(this),
79868
+ startMeshRefineBatchJob: this.startMeshRefineBatchJob.bind(this),
79869
+ stopIde: this.stopIde.bind(this),
79870
+ launchIde: (args) => launchIde(ctx, args),
79871
+ inlineMeshCache: this.inlineMeshCache,
79872
+ meshGitProbeCache: this.meshGitProbeCache
79873
+ };
79874
+ return ctx;
79875
+ }
78513
79876
  async requireMeshHostMutationOwner(meshId, inlineMesh, operation) {
78514
79877
  const meshRecord = await this.getMeshForCommand(meshId, inlineMesh, { preferInline: true });
78515
79878
  const mesh = meshRecord?.mesh;
@@ -80425,6 +81788,10 @@ ${hintLines.join("\n")}` : "",
80425
81788
  getMeshForCommand: this.getMeshForCommand.bind(this)
80426
81789
  }, args);
80427
81790
  }
81791
+ const medFamilyHandler = medFamilyRegistry.get(cmd);
81792
+ if (medFamilyHandler) {
81793
+ return await medFamilyHandler(this.buildMedFamilyContext(), args);
81794
+ }
80428
81795
  switch (cmd) {
80429
81796
  // ─── CLI / ACP commands ───
80430
81797
  case "mesh_forward_event": {
@@ -80445,1315 +81812,6 @@ ${hintLines.join("\n")}` : "",
80445
81812
  this.deps.instanceManager.sendEvent(sessionId, "interactive_prompt_response", response);
80446
81813
  return { success: true };
80447
81814
  }
80448
- case "launch_cli": {
80449
- const launchResult = await this.deps.cliManager.handleCliCommand(cmd, args);
80450
- const meshNodeId = readStringValue(args?.settings?.meshNodeId);
80451
- const meshId = readStringValue(args?.settings?.meshNodeFor);
80452
- if (meshNodeId && meshId && launchResult?.success !== false) {
80453
- try {
80454
- const { getMesh: getMesh2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
80455
- const meshObj = getMesh2(meshId) ?? this.getCachedInlineMesh(meshId);
80456
- const nodeObj = Array.isArray(meshObj?.nodes) ? meshObj.nodes.find((n) => meshNodeIdMatches(n, meshNodeId)) : void 0;
80457
- const bootstrapStatus = readStringValue(nodeObj?.worktreeBootstrap?.status);
80458
- if (bootstrapStatus === "running") {
80459
- return { success: true, ...launchResult, bootstrapPending: true };
80460
- }
80461
- } catch {
80462
- }
80463
- }
80464
- return launchResult;
80465
- }
80466
- case "stop_cli":
80467
- case "set_cli_view_mode":
80468
- case "record_provider_pty": {
80469
- return this.deps.cliManager.handleCliCommand(cmd, args);
80470
- }
80471
- case "agent_command": {
80472
- {
80473
- const dispatchSessionId = readStringValue(args?.targetSessionId, args?.sessionId, args?.instanceId);
80474
- const dispatchMeshContext = args?.meshContext;
80475
- if (dispatchSessionId && dispatchMeshContext) {
80476
- try {
80477
- const inst = this.deps.instanceManager.getInstance(dispatchSessionId);
80478
- if (inst && typeof inst.updateSettings === "function") {
80479
- const stamp = buildMeshWorkerRelayStamp(
80480
- inst.getState?.()?.settings,
80481
- {
80482
- meshId: dispatchMeshContext.meshId,
80483
- nodeId: dispatchMeshContext.nodeId,
80484
- coordinatorDaemonId: dispatchMeshContext.coordinatorDaemonId,
80485
- // Session-level anchor: preserved across the P2P dispatch to a
80486
- // remote worker so its completion echoes back to the right session.
80487
- coordinatorSessionId: dispatchMeshContext.coordinatorSessionId
80488
- }
80489
- );
80490
- if (stamp) inst.updateSettings(stamp);
80491
- }
80492
- } catch {
80493
- }
80494
- }
80495
- }
80496
- const agentResult = await this.deps.cliManager.handleCliCommand(cmd, args);
80497
- const meshCtx = args?.meshContext;
80498
- const dispatchNodeId = readStringValue(meshCtx?.nodeId);
80499
- const dispatchMeshId = readStringValue(meshCtx?.meshId);
80500
- if (dispatchNodeId && dispatchMeshId && agentResult?.success !== false) {
80501
- try {
80502
- const { getMesh: getMesh2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
80503
- const meshObj = getMesh2(dispatchMeshId) ?? this.getCachedInlineMesh(dispatchMeshId);
80504
- const nodeObj = Array.isArray(meshObj?.nodes) ? meshObj.nodes.find((n) => meshNodeIdMatches(n, dispatchNodeId)) : void 0;
80505
- const bootstrapStatus = readStringValue(nodeObj?.worktreeBootstrap?.status);
80506
- if (bootstrapStatus === "running") {
80507
- return {
80508
- success: true,
80509
- ...agentResult,
80510
- dispatchAcknowledgementRisk: true,
80511
- dispatchAcknowledgementRiskReason: "bootstrap_still_running",
80512
- nextAction: "Wait for worktree_bootstrap_complete event before dispatching work to this node."
80513
- };
80514
- }
80515
- } catch {
80516
- }
80517
- }
80518
- return agentResult;
80519
- }
80520
- // ─── Logs ───
80521
- case "list_saved_sessions": {
80522
- const providerType = typeof args?.providerType === "string" ? args.providerType.trim() : typeof args?.agentType === "string" ? args.agentType.trim() : "";
80523
- const kind = args?.kind === "acp" ? "acp" : "cli";
80524
- if (!providerType) {
80525
- return { success: false, error: "providerType required" };
80526
- }
80527
- const wantsAll = args?.all === true;
80528
- const offset = wantsAll ? 0 : Math.max(0, Number(args?.offset) || 0);
80529
- const limit = wantsAll ? Number.MAX_SAFE_INTEGER : Math.max(1, Math.min(100, Number(args?.limit) || 30));
80530
- const requestedWorkspace = typeof args?.workspace === "string" ? args.workspace.trim() : "";
80531
- const requestedProviderSessionId = typeof args?.providerSessionId === "string" ? args.providerSessionId.trim() : typeof args?.activeProviderSessionId === "string" ? args.activeProviderSessionId.trim() : "";
80532
- const providerMeta = this.deps.providerLoader.resolve?.(providerType) || this.deps.providerLoader.getMeta(providerType);
80533
- const { sessions: historySessions, hasMore, source } = listProviderHistorySessions(providerType, {
80534
- canonicalHistory: providerMeta?.nativeHistory,
80535
- offset,
80536
- limit,
80537
- historyBehavior: providerMeta?.historyBehavior,
80538
- scripts: providerMeta?.scripts
80539
- });
80540
- const state = loadState();
80541
- const savedSessions = getSavedProviderSessions(state, { providerType, kind });
80542
- const recentSessions = getRecentActivity(state, 200).filter((entry) => entry.providerType === providerType && entry.kind === kind && entry.providerSessionId);
80543
- const savedSessionById = new Map(savedSessions.map((entry) => [entry.providerSessionId, entry]));
80544
- const recentSessionById = new Map(recentSessions.map((entry) => [entry.providerSessionId, entry]));
80545
- const canResumeById = supportsExplicitSessionResume(providerMeta?.resume);
80546
- return {
80547
- success: true,
80548
- sessions: historySessions.map((session) => {
80549
- const saved = savedSessionById.get(session.historySessionId);
80550
- const recent = recentSessionById.get(session.historySessionId);
80551
- const workspace = saved?.workspace || recent?.workspace || session.workspace || (requestedWorkspace && requestedProviderSessionId === session.historySessionId ? requestedWorkspace : void 0);
80552
- return {
80553
- id: session.historySessionId,
80554
- providerSessionId: session.historySessionId,
80555
- providerType,
80556
- providerName: saved?.providerName || recent?.providerName || providerType,
80557
- kind: saved?.kind || recent?.kind || kind,
80558
- title: saved?.title || recent?.title || session.sessionTitle || session.preview || providerType,
80559
- workspace,
80560
- summaryMetadata: saved?.summaryMetadata || recent?.summaryMetadata,
80561
- preview: session.preview,
80562
- messageCount: session.messageCount,
80563
- firstMessageAt: session.firstMessageAt,
80564
- lastMessageAt: session.lastMessageAt,
80565
- canResume: !!workspace && canResumeById,
80566
- historySource: session.source,
80567
- sourcePath: session.sourcePath,
80568
- sourceMtimeMs: session.sourceMtimeMs
80569
- };
80570
- }),
80571
- hasMore,
80572
- source
80573
- };
80574
- }
80575
- // ─── restart_session: IDE / CLI / ACP unified ───
80576
- case "restart_session": {
80577
- const targetType = args?.cliType || args?.agentType || args?.ideType;
80578
- if (!targetType) throw new Error("cliType or ideType required");
80579
- const isIde = this.deps.cdpManagers.has(targetType) || this.deps.providerLoader.getMeta(targetType)?.category === "ide";
80580
- if (isIde) {
80581
- await this.stopIde(targetType, true);
80582
- const launchResult = await this.executeDaemonCommand("launch_ide", { ideType: targetType, enableCdp: true, workspace: args?.workspace });
80583
- return { success: true, restarted: true, ideType: targetType, launch: launchResult };
80584
- }
80585
- return this.deps.cliManager.handleCliCommand(cmd, args);
80586
- }
80587
- // ─── IDE stop ───
80588
- case "stop_ide": {
80589
- const ideType = args?.ideType;
80590
- if (!ideType) throw new Error("ideType required");
80591
- const killProcess = args?.killProcess !== false;
80592
- await this.stopIde(ideType, killProcess);
80593
- try {
80594
- const results = await detectIDEs(this.deps.providerLoader);
80595
- this.deps.detectedIdes.value = results;
80596
- this.deps.providerLoader.setIdeDetectionResults(results, true);
80597
- } catch {
80598
- }
80599
- return { success: true, ideType, stopped: true, processKilled: killProcess };
80600
- }
80601
- // ─── IDE restart ───
80602
- case "restart_ide": {
80603
- const ideType = args?.ideType;
80604
- if (!ideType) throw new Error("ideType required");
80605
- await this.stopIde(ideType, true);
80606
- const launchResult = await this.executeDaemonCommand("launch_ide", { ideType, enableCdp: true, workspace: args?.workspace });
80607
- return { success: true, ideType, restarted: true, launch: launchResult };
80608
- }
80609
- // ─── IDE launch + CDP connect ───
80610
- case "launch_ide": {
80611
- const ideKey = args?.ideId || args?.ideType;
80612
- const resolvedWorkspace = resolveIdeLaunchWorkspace(
80613
- {
80614
- workspace: args?.workspace,
80615
- workspaceId: args?.workspaceId,
80616
- useDefaultWorkspace: args?.useDefaultWorkspace
80617
- },
80618
- loadConfig2()
80619
- );
80620
- const launchArgs = {
80621
- ideId: ideKey,
80622
- workspace: resolvedWorkspace,
80623
- newWindow: args?.newWindow
80624
- };
80625
- LOG2.info("LaunchIDE", `target=${ideKey || "auto"}`);
80626
- const result = await launchWithCdp(launchArgs);
80627
- if (result.success && result.port && result.ideId && !this.deps.cdpManagers.has(result.ideId)) {
80628
- const logFn = this.deps.getCdpLogFn ? this.deps.getCdpLogFn(result.ideId) : LOG2.forComponent(`CDP:${result.ideId}`).asLogFn();
80629
- const provider = this.deps.providerLoader.getMeta(result.ideId);
80630
- const manager = new DaemonCdpManager(result.port, logFn, void 0, provider?.targetFilter);
80631
- const connected = await manager.connect();
80632
- if (connected) {
80633
- registerExtensionProviders(this.deps.providerLoader, manager, result.ideId);
80634
- this.deps.cdpManagers.set(result.ideId, manager);
80635
- LOG2.info("CDP", `Connected: ${result.ideId} (port ${result.port})`);
80636
- LOG2.info("CDP", `${this.deps.cdpManagers.size} IDE(s) connected`);
80637
- this.deps.onCdpManagerCreated?.(result.ideId, manager);
80638
- }
80639
- }
80640
- this.deps.onIdeConnected?.();
80641
- try {
80642
- const results = await detectIDEs(this.deps.providerLoader);
80643
- this.deps.detectedIdes.value = results;
80644
- this.deps.providerLoader.setIdeDetectionResults(results, true);
80645
- } catch {
80646
- }
80647
- if (result.success && resolvedWorkspace) {
80648
- try {
80649
- const next = appendRecentActivity(loadState(), {
80650
- kind: "ide",
80651
- providerType: result.ideId || ideKey,
80652
- providerName: result.ideId || ideKey,
80653
- workspace: resolvedWorkspace,
80654
- title: result.ideId || ideKey
80655
- });
80656
- saveState(next);
80657
- } catch {
80658
- }
80659
- } else if (result.success && (result.ideId || ideKey)) {
80660
- try {
80661
- saveState(appendRecentActivity(loadState(), {
80662
- kind: "ide",
80663
- providerType: result.ideId || ideKey,
80664
- providerName: result.ideId || ideKey,
80665
- title: result.ideId || ideKey
80666
- }));
80667
- } catch {
80668
- }
80669
- }
80670
- return { ...result };
80671
- }
80672
- // ─── Detect providers ───
80673
- case "detect_provider": {
80674
- const providerType = typeof args?.providerType === "string" ? args.providerType.trim() : "";
80675
- if (!providerType) return { success: false, error: "providerType is required" };
80676
- const normalizedType = this.deps.providerLoader.resolveAlias(providerType);
80677
- const provider = this.deps.providerLoader.getByAlias(providerType);
80678
- if (!provider) return { success: false, error: `Provider not found: ${providerType}` };
80679
- if (provider.category !== "cli" && provider.category !== "acp") {
80680
- return { success: false, error: `Provider detection is only supported for CLI/ACP providers: ${providerType}` };
80681
- }
80682
- if (!this.deps.providerLoader.isMachineProviderEnabled(normalizedType)) {
80683
- return { success: false, error: `Provider is disabled on this machine: ${providerType}` };
80684
- }
80685
- const detected = await detectCLI(normalizedType, this.deps.providerLoader, { includeVersion: false });
80686
- this.deps.providerLoader.setCliDetectionResults([{
80687
- id: normalizedType,
80688
- installed: !!detected,
80689
- path: detected?.path
80690
- }], false);
80691
- this.deps.onStatusChange?.();
80692
- return {
80693
- success: true,
80694
- providerType: normalizedType,
80695
- detected: !!detected,
80696
- path: detected?.path || null
80697
- };
80698
- }
80699
- // ─── Detect IDEs ───
80700
- case "detect_ides": {
80701
- const results = await detectIDEs(this.deps.providerLoader);
80702
- this.deps.detectedIdes.value = results;
80703
- this.deps.providerLoader.setIdeDetectionResults(results, true);
80704
- return { success: true, detectedInfo: results };
80705
- }
80706
- // ─── Mesh CRUD (local meshes.json) ───
80707
- case "list_meshes": {
80708
- try {
80709
- const { listMeshes: listMeshes2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
80710
- return { success: true, meshes: listMeshes2() };
80711
- } catch (e) {
80712
- return { success: false, error: e.message };
80713
- }
80714
- }
80715
- case "get_mesh": {
80716
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
80717
- if (!meshId) return { success: false, error: "meshId required" };
80718
- const meshRecord = await this.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
80719
- if (!meshRecord?.mesh) return { success: false, error: "Mesh not found" };
80720
- const requireDirectPeerTruth = args?.requireDirectPeerTruth === true;
80721
- const probeRemotePeers = args?.refresh === true || args?.forceRefresh === true;
80722
- const directTruth = await hydrateInlineMeshDirectTruth({
80723
- mesh: meshRecord.mesh,
80724
- meshSource: meshRecord.source,
80725
- dispatchMeshCommand: this.deps.dispatchMeshCommand,
80726
- getMeshPeerConnectionStatus: this.deps.getMeshPeerConnectionStatus,
80727
- statusInstanceId: this.deps.statusInstanceId,
80728
- localMachineId: loadConfig2().machineId || "",
80729
- probeRemotePeers,
80730
- probeCache: this.meshGitProbeCache
80731
- });
80732
- const directTruthSatisfied = meshRecord.source !== "inline_bootstrap" || directTruth.directEvidenceCount > 0;
80733
- const sourceOfTruth = {
80734
- membership: meshRecord.source === "inline_cache" ? "coordinator_inline_mesh_cache" : meshRecord.source === "local_config" ? "local_mesh_config" : "inline_bootstrap_snapshot",
80735
- coordinatorOwnsLiveTruth: directTruthSatisfied,
80736
- directPeerTruth: {
80737
- required: requireDirectPeerTruth,
80738
- satisfied: directTruthSatisfied,
80739
- directEvidenceCount: directTruth.directEvidenceCount,
80740
- localConfirmedCount: directTruth.localConfirmedCount,
80741
- peerAttemptedCount: directTruth.peerAttemptedCount,
80742
- peerConfirmedCount: directTruth.peerConfirmedCount,
80743
- unavailableNodeIds: directTruth.unavailableNodeIds
80744
- }
80745
- };
80746
- if (requireDirectPeerTruth && !directTruthSatisfied) {
80747
- return {
80748
- success: false,
80749
- code: "mesh_direct_peer_truth_unavailable",
80750
- error: "Selected coordinator could not confirm direct mesh truth yet. Bootstrap inventory stays unavailable until direct get_mesh probes succeed.",
80751
- sourceOfTruth
80752
- };
80753
- }
80754
- return { success: true, mesh: meshRecord.mesh, sourceOfTruth };
80755
- }
80756
- case "create_mesh": {
80757
- const name = typeof args?.name === "string" ? args.name.trim() : "";
80758
- const repoIdentity = typeof args?.repoIdentity === "string" ? args.repoIdentity.trim() : "";
80759
- const repoRemoteUrl = typeof args?.repoRemoteUrl === "string" ? args.repoRemoteUrl.trim() : void 0;
80760
- const defaultBranch = typeof args?.defaultBranch === "string" ? args.defaultBranch.trim() : void 0;
80761
- if (!name) return { success: false, error: "name required" };
80762
- try {
80763
- const { createMesh: createMesh2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
80764
- const meshHost = args?.meshHost && typeof args.meshHost === "object" && !Array.isArray(args.meshHost) ? args.meshHost : void 0;
80765
- const mesh = createMesh2({ name, repoIdentity, repoRemoteUrl, defaultBranch, policy: args?.policy, meshHost });
80766
- return { success: true, mesh };
80767
- } catch (e) {
80768
- return { success: false, error: e.message };
80769
- }
80770
- }
80771
- case "update_mesh": {
80772
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
80773
- if (!meshId) return { success: false, error: "meshId required" };
80774
- try {
80775
- const { updateMesh: updateMesh2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
80776
- const patch = {};
80777
- if (typeof args?.name === "string") patch.name = args.name;
80778
- if (typeof args?.defaultBranch === "string") patch.defaultBranch = args.defaultBranch;
80779
- if (args?.policy && typeof args.policy === "object" && !Array.isArray(args.policy)) patch.policy = args.policy;
80780
- if (args?.coordinator && typeof args.coordinator === "object" && !Array.isArray(args.coordinator)) patch.coordinator = args.coordinator;
80781
- if (args?.meshHost && typeof args.meshHost === "object" && !Array.isArray(args.meshHost)) patch.meshHost = args.meshHost;
80782
- if (!Object.keys(patch).length) return { success: false, error: "No updates provided" };
80783
- const mesh = updateMesh2(meshId, patch);
80784
- if (!mesh) return { success: false, error: "Mesh not found" };
80785
- this.inlineMeshCache.set(meshId, mesh);
80786
- this.invalidateAggregateMeshStatus(meshId);
80787
- return { success: true, mesh };
80788
- } catch (e) {
80789
- return { success: false, error: e.message };
80790
- }
80791
- }
80792
- case "get_mesh_host_pairing": {
80793
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
80794
- if (!meshId) return { success: false, error: "meshId required" };
80795
- const meshRecord = await this.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
80796
- const mesh = meshRecord?.mesh;
80797
- if (!mesh) return { success: false, error: "Mesh not found" };
80798
- const meshHost = resolveMeshHostStatus(mesh);
80799
- const pairingStatus = meshHost.pairing?.status || "not_configured";
80800
- return {
80801
- success: true,
80802
- code: pairingStatus === "not_configured" ? "mesh_host_pairing_not_configured" : "mesh_host_pairing_pending",
80803
- meshId,
80804
- hostAddress: meshHost.hostAddress,
80805
- meshHost,
80806
- manualPairing: {
80807
- status: pairingStatus,
80808
- joinImplemented: true,
80809
- protocol: "standalone_command_direct_v1",
80810
- description: "Standalone manual pairing can save address/token metadata, apply a host join over direct standalone command HTTP or injected mesh command dispatch, and check persisted status. P2P signaling remains outside this slice."
80811
- }
80812
- };
80813
- }
80814
- case "configure_mesh_host_pairing": {
80815
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
80816
- const hostAddress = typeof args?.hostAddress === "string" ? args.hostAddress.trim() : "";
80817
- const token = typeof args?.token === "string" ? args.token.trim() : "";
80818
- if (!meshId) return { success: false, error: "meshId required" };
80819
- if (!hostAddress || !token) return { success: false, error: "hostAddress and token required" };
80820
- try {
80821
- const { configureMeshHostPairing: configureMeshHostPairing2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
80822
- const configured = configureMeshHostPairing2(meshId, { hostAddress, token });
80823
- if (!configured) return { success: false, error: "Mesh not found" };
80824
- this.inlineMeshCache.set(meshId, configured.mesh);
80825
- const meshHost = resolveMeshHostStatus(configured.mesh);
80826
- return {
80827
- success: true,
80828
- code: "mesh_host_pairing_pending",
80829
- meshId,
80830
- hostAddress: configured.hostAddress,
80831
- meshHost,
80832
- manualPairing: {
80833
- status: meshHost.pairing?.status || "pairing",
80834
- joinImplemented: true,
80835
- protocol: "standalone_command_direct_v1",
80836
- description: "Manual Mesh Host pairing config was saved locally. Use join_mesh_host_pairing to apply it to the host. Raw token was not persisted."
80837
- }
80838
- };
80839
- } catch (e) {
80840
- return { success: false, code: "mesh_host_pairing_invalid", meshId, hostAddress, error: e.message };
80841
- }
80842
- }
80843
- case "create_mesh_host_pairing_token": {
80844
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
80845
- if (!meshId) return { success: false, error: "meshId required" };
80846
- try {
80847
- const { createMeshHostPairingToken: createMeshHostPairingToken2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
80848
- const created = createMeshHostPairingToken2(meshId, {
80849
- token: typeof args?.token === "string" ? args.token : void 0,
80850
- expiresAt: typeof args?.expiresAt === "string" ? args.expiresAt : void 0
80851
- });
80852
- if (!created) return { success: false, error: "Mesh not found" };
80853
- this.inlineMeshCache.set(meshId, created.mesh);
80854
- this.invalidateAggregateMeshStatus(meshId);
80855
- return {
80856
- success: true,
80857
- code: "mesh_host_pairing_token_created",
80858
- meshId,
80859
- token: created.token,
80860
- tokenId: created.tokenId,
80861
- expiresAt: created.expiresAt,
80862
- meshHost: resolveMeshHostStatus(created.mesh),
80863
- warning: "Raw token is returned once and is not persisted; share it with member daemons over a trusted channel."
80864
- };
80865
- } catch (e) {
80866
- return { success: false, code: "mesh_host_pairing_token_invalid", meshId, error: e.message };
80867
- }
80868
- }
80869
- case "apply_mesh_host_join": {
80870
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
80871
- const token = typeof args?.token === "string" ? args.token.trim() : "";
80872
- const memberNode = args?.memberNode && typeof args.memberNode === "object" && !Array.isArray(args.memberNode) ? args.memberNode : null;
80873
- if (!meshId) return { success: false, error: "meshId required" };
80874
- if (!token || !memberNode) return { success: false, error: "token and memberNode required" };
80875
- try {
80876
- const { applyMeshHostJoinRequest: applyMeshHostJoinRequest2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
80877
- const applied = applyMeshHostJoinRequest2(meshId, {
80878
- token,
80879
- memberNode,
80880
- memberMeshId: typeof args?.memberMeshId === "string" ? args.memberMeshId : void 0
80881
- });
80882
- if (!applied) return { success: false, error: "Mesh not found" };
80883
- if (!applied.accepted) {
80884
- return {
80885
- success: false,
80886
- code: "mesh_host_join_rejected",
80887
- meshId,
80888
- tokenId: applied.tokenId,
80889
- meshHost: applied.meshHost ? resolveMeshHostStatus({ meshHost: applied.meshHost }) : void 0,
80890
- error: applied.reason
80891
- };
80892
- }
80893
- this.inlineMeshCache.set(meshId, applied.mesh);
80894
- this.invalidateAggregateMeshStatus(meshId);
80895
- try {
80896
- const { appendLedgerEntry: appendLedgerEntry2 } = await Promise.resolve().then(() => (init_mesh_ledger(), mesh_ledger_exports));
80897
- appendLedgerEntry2(meshId, {
80898
- kind: "node_joined",
80899
- nodeId: applied.node.id,
80900
- payload: { role: "member", tokenId: applied.tokenId, workspace: applied.node.workspace }
80901
- });
80902
- } catch {
80903
- }
80904
- return {
80905
- success: true,
80906
- code: "mesh_host_join_accepted",
80907
- meshId,
80908
- node: applied.node,
80909
- tokenId: applied.tokenId,
80910
- meshHost: resolveMeshHostStatus(applied.mesh)
80911
- };
80912
- } catch (e) {
80913
- return { success: false, code: "mesh_host_join_failed", meshId, error: e.message };
80914
- }
80915
- }
80916
- case "join_mesh_host_pairing": {
80917
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
80918
- const token = typeof args?.token === "string" ? args.token.trim() : "";
80919
- if (!meshId) return { success: false, error: "meshId required" };
80920
- if (!token) return { success: false, error: "token required because raw pairing tokens are not persisted" };
80921
- const meshRecord = await this.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
80922
- const mesh = meshRecord?.mesh;
80923
- if (!mesh) return { success: false, error: "Mesh not found" };
80924
- const meshHost = resolveMeshHostStatus(mesh);
80925
- if (meshHost.role !== "member") {
80926
- return { success: false, code: "mesh_host_join_not_member", meshId, meshHost, error: "join_mesh_host_pairing must run from a member daemon configured with a Mesh Host address/token." };
80927
- }
80928
- try {
80929
- const { tokenIdForManualPairing: tokenIdForManualPairing2, markMeshHostPairingJoined: markMeshHostPairingJoined2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
80930
- const tokenId = tokenIdForManualPairing2(token);
80931
- if (meshHost.pairing?.tokenId && meshHost.pairing.tokenId !== tokenId) {
80932
- return { success: false, code: "mesh_host_join_rejected", meshId, tokenId, meshHost, error: "invalid pairing token" };
80933
- }
80934
- const memberNode = buildMemberJoinNode(mesh, args, this.deps.statusInstanceId);
80935
- if (!memberNode) return { success: false, error: "member node metadata unavailable" };
80936
- const hostMeshId = typeof args?.hostMeshId === "string" && args.hostMeshId.trim() ? args.hostMeshId.trim() : meshId;
80937
- const hostDaemonId = typeof args?.hostDaemonId === "string" && args.hostDaemonId.trim() ? args.hostDaemonId.trim() : meshHost.hostDaemonId;
80938
- let hostResult;
80939
- let transport;
80940
- if (hostDaemonId && this.deps.dispatchMeshCommand) {
80941
- transport = "mesh_command_dispatch";
80942
- hostResult = await this.deps.dispatchMeshCommand(hostDaemonId, "apply_mesh_host_join", {
80943
- meshId: hostMeshId,
80944
- token,
80945
- memberMeshId: meshId,
80946
- memberNode
80947
- });
80948
- } else if (meshHost.hostAddress) {
80949
- transport = "standalone_http_command";
80950
- const commandUrl = normalizeStandaloneHostCommandUrl(meshHost.hostAddress);
80951
- const response = await fetch(commandUrl, {
80952
- method: "POST",
80953
- headers: { "Content-Type": "application/json" },
80954
- body: JSON.stringify({ type: "apply_mesh_host_join", payload: { meshId: hostMeshId, token, memberMeshId: meshId, memberNode } })
80955
- });
80956
- hostResult = await response.json().catch(() => ({ success: false, error: `Host returned HTTP ${response.status}` }));
80957
- if (!response.ok && hostResult?.success !== false) hostResult = { success: false, error: `Host returned HTTP ${response.status}` };
80958
- } else {
80959
- return {
80960
- success: false,
80961
- code: "mesh_host_join_transport_unavailable",
80962
- meshId,
80963
- meshHost,
80964
- error: "No hostDaemonId dispatch path or hostAddress HTTP command path is available. P2P signaling join is not implemented in this slice."
80965
- };
80966
- }
80967
- if (!hostResult?.success) {
80968
- return { success: false, code: hostResult?.code || "mesh_host_join_rejected", meshId, meshHost, transport, error: hostResult?.error || "Mesh Host rejected join request", hostResult };
80969
- }
80970
- const joined = meshRecord.inline ? null : markMeshHostPairingJoined2(meshId, {
80971
- tokenId: hostResult.tokenId || tokenId,
80972
- hostDaemonId: hostResult.meshHost?.hostDaemonId || hostDaemonId,
80973
- hostNodeId: hostResult.meshHost?.hostNodeId,
80974
- joinedAt: hostResult.meshHost?.pairing?.joinedAt
80975
- });
80976
- if (joined) {
80977
- this.inlineMeshCache.set(meshId, joined.mesh);
80978
- this.invalidateAggregateMeshStatus(meshId);
80979
- }
80980
- return {
80981
- success: true,
80982
- code: "mesh_host_join_applied",
80983
- meshId,
80984
- hostMeshId,
80985
- transport,
80986
- node: hostResult.node,
80987
- tokenId: hostResult.tokenId || tokenId,
80988
- meshHost: joined ? resolveMeshHostStatus(joined.mesh) : { ...meshHost, pairing: { ...meshHost.pairing || {}, status: "paired", tokenId: hostResult.tokenId || tokenId } },
80989
- hostResult,
80990
- manualPairing: {
80991
- status: "paired",
80992
- joinImplemented: true,
80993
- protocol: "standalone_command_direct_v1",
80994
- description: "Mesh Host accepted the join and local member pairing status was marked paired. P2P runtime signaling remains outside this slice."
80995
- }
80996
- };
80997
- } catch (e) {
80998
- return { success: false, code: "mesh_host_join_failed", meshId, meshHost, error: e.message };
80999
- }
81000
- }
81001
- case "delete_mesh": {
81002
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81003
- if (!meshId) return { success: false, error: "meshId required" };
81004
- try {
81005
- const { deleteMesh: deleteMesh2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
81006
- const deleted = deleteMesh2(meshId);
81007
- return { success: true, deleted };
81008
- } catch (e) {
81009
- return { success: false, error: e.message };
81010
- }
81011
- }
81012
- case "get_mesh_queue": {
81013
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81014
- if (!meshId) return { success: false, error: "meshId required" };
81015
- try {
81016
- const { getMeshQueueStats: getMeshQueueStats2, getQueue: getQueue2, describeTaskDependencyState: describeTaskDependencyState2 } = await Promise.resolve().then(() => (init_mesh_work_queue(), mesh_work_queue_exports));
81017
- const status = Array.isArray(args?.status) ? args.status.map((s2) => typeof s2 === "string" ? s2.trim() : "").filter(Boolean) : void 0;
81018
- const rawQueue = getQueue2(meshId, { status });
81019
- const statusById = new Map(getQueue2(meshId).map((task) => [task.id, task.status]));
81020
- const queue = rawQueue.map((task) => Array.isArray(task.dependsOn) && task.dependsOn.length > 0 ? { ...task, ...describeTaskDependencyState2(task, statusById) } : task);
81021
- const summary = getMeshQueueStats2(meshId);
81022
- return {
81023
- success: true,
81024
- queue,
81025
- summary,
81026
- sourceOfTruth: {
81027
- kind: "mesh_work_queue_file",
81028
- activeStatuses: ["pending", "assigned"],
81029
- historicalStatuses: ["completed", "failed", "cancelled"],
81030
- notes: "pending/assigned are active work; completed/failed/cancelled are historical records."
81031
- }
81032
- };
81033
- } catch (e) {
81034
- return { success: false, error: e.message };
81035
- }
81036
- }
81037
- case "cancel_mesh_queue_task": {
81038
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81039
- const taskId = typeof args?.taskId === "string" ? args.taskId.trim() : "";
81040
- if (!meshId || !taskId) return { success: false, error: "meshId and taskId required" };
81041
- const ownerFailure = await this.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "queue cancellation");
81042
- if (ownerFailure) return ownerFailure;
81043
- try {
81044
- const { cancelTask: cancelTask2 } = await Promise.resolve().then(() => (init_mesh_work_queue(), mesh_work_queue_exports));
81045
- const reason = typeof args?.reason === "string" ? args.reason : void 0;
81046
- const task = cancelTask2(meshId, taskId, { reason });
81047
- if (!task) return { success: false, error: `Queue task '${taskId}' not found` };
81048
- return { success: true, task };
81049
- } catch (e) {
81050
- return { success: false, error: e.message };
81051
- }
81052
- }
81053
- case "requeue_mesh_queue_task": {
81054
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81055
- const taskId = typeof args?.taskId === "string" ? args.taskId.trim() : "";
81056
- if (!meshId || !taskId) return { success: false, error: "meshId and taskId required" };
81057
- const ownerFailure = await this.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "queue requeue");
81058
- if (ownerFailure) return ownerFailure;
81059
- try {
81060
- const { requeueTask: requeueTask2 } = await Promise.resolve().then(() => (init_mesh_work_queue(), mesh_work_queue_exports));
81061
- const task = requeueTask2(meshId, taskId, {
81062
- reason: typeof args?.reason === "string" ? args.reason : void 0,
81063
- targetNodeId: typeof args?.targetNodeId === "string" ? args.targetNodeId.trim() : void 0,
81064
- targetSessionId: typeof args?.targetSessionId === "string" ? args.targetSessionId.trim() : void 0,
81065
- clearTargetNode: args?.clearTargetNode === true,
81066
- clearTargetSession: args?.clearTargetSession !== false
81067
- });
81068
- if (!task) return { success: false, error: `Queue task '${taskId}' not found` };
81069
- return { success: true, task };
81070
- } catch (e) {
81071
- return { success: false, error: e.message };
81072
- }
81073
- }
81074
- case "add_mesh_node": {
81075
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81076
- const workspace = typeof args?.workspace === "string" ? args.workspace.trim() : "";
81077
- if (!meshId) return { success: false, error: "meshId required" };
81078
- if (!workspace) return { success: false, error: "workspace required" };
81079
- const ownerFailure = await this.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "node addition");
81080
- if (ownerFailure) return ownerFailure;
81081
- try {
81082
- const { addNode: addNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
81083
- const providerPriority = Array.isArray(args?.providerPriority) ? args.providerPriority.map((type) => typeof type === "string" ? type.trim() : "").filter(Boolean) : [];
81084
- const readOnly = args?.readOnly === true;
81085
- const providerRoles = normalizeProviderRoles(args?.providerRoles);
81086
- const policy = {
81087
- ...readOnly ? { readOnly: true } : {},
81088
- ...providerPriority.length ? { providerPriority } : {},
81089
- ...providerRoles.length ? { providerRoles } : {}
81090
- };
81091
- const role = normalizeMeshDaemonRole(args?.role);
81092
- const daemonId = typeof args?.daemonId === "string" && args.daemonId.trim() ? args.daemonId.trim() : void 0;
81093
- const machineId = typeof args?.machineId === "string" && args.machineId.trim() ? args.machineId.trim() : void 0;
81094
- const repoRoot = typeof args?.repoRoot === "string" && args.repoRoot.trim() ? args.repoRoot.trim() : void 0;
81095
- const node = addNode2(meshId, {
81096
- workspace,
81097
- ...repoRoot ? { repoRoot } : {},
81098
- ...daemonId ? { daemonId } : {},
81099
- ...machineId ? { machineId } : {},
81100
- ...policy ? { policy } : {},
81101
- ...role ? { role } : {}
81102
- });
81103
- if (!node) return { success: false, error: "Mesh not found" };
81104
- this.invalidateAggregateMeshStatus(meshId);
81105
- return { success: true, node };
81106
- } catch (e) {
81107
- return { success: false, error: e.message };
81108
- }
81109
- }
81110
- case "update_mesh_node": {
81111
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81112
- const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
81113
- if (!meshId || !nodeId) return { success: false, error: "meshId and nodeId required" };
81114
- const ownerFailure = await this.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "node update");
81115
- if (ownerFailure) return ownerFailure;
81116
- try {
81117
- const { updateNode: updateNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
81118
- const policy = args?.policy && typeof args.policy === "object" && !Array.isArray(args.policy) ? { ...args.policy } : {};
81119
- if (Array.isArray(args?.providerPriority)) {
81120
- const providerPriority = args.providerPriority.map((type) => typeof type === "string" ? type.trim() : "").filter(Boolean);
81121
- delete policy.provider_priority;
81122
- if (providerPriority.length) {
81123
- policy.providerPriority = providerPriority;
81124
- } else {
81125
- delete policy.providerPriority;
81126
- }
81127
- }
81128
- if (Array.isArray(args?.providerRoles)) {
81129
- const providerRoles = normalizeProviderRoles(args.providerRoles);
81130
- if (providerRoles.length) {
81131
- policy.providerRoles = providerRoles;
81132
- } else {
81133
- delete policy.providerRoles;
81134
- }
81135
- }
81136
- const patch = { policy };
81137
- if (typeof args?.systemPrompt === "string") {
81138
- const trimmed = args.systemPrompt.trim();
81139
- patch.systemPrompt = trimmed || void 0;
81140
- } else if (args?.systemPrompt === null) {
81141
- patch.systemPrompt = void 0;
81142
- }
81143
- const node = updateNode2(meshId, nodeId, patch);
81144
- if (!node) return { success: false, error: "Mesh node not found" };
81145
- this.invalidateAggregateMeshStatus(meshId);
81146
- return { success: true, node };
81147
- } catch (e) {
81148
- return { success: false, error: e.message };
81149
- }
81150
- }
81151
- case "cleanup_mesh_sessions": {
81152
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81153
- const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
81154
- if (!meshId || !nodeId) return { success: false, error: "meshId and nodeId required" };
81155
- const ownerFailure = await this.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "node removal");
81156
- if (ownerFailure) return ownerFailure;
81157
- try {
81158
- const meshRecord = await this.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
81159
- const mesh = meshRecord?.mesh;
81160
- if (!mesh) return { success: false, error: "Mesh not found" };
81161
- const node = mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
81162
- if (!node) return { success: false, error: `Node '${nodeId}' not found in mesh` };
81163
- const mode = this.normalizeMeshSessionCleanupMode(args?.mode ?? mesh?.policy?.sessionCleanupOnNodeRemove);
81164
- const sessionIds = Array.isArray(args?.sessionIds) ? args.sessionIds.map((id) => typeof id === "string" ? id.trim() : "").filter(Boolean) : void 0;
81165
- const result = await this.cleanupMeshSessions({
81166
- meshId,
81167
- nodeId,
81168
- node,
81169
- mode,
81170
- sessionIds,
81171
- dryRun: args?.dryRun === true,
81172
- source: "mesh_cleanup_sessions"
81173
- });
81174
- return result;
81175
- } catch (e) {
81176
- return { success: false, error: e.message };
81177
- }
81178
- }
81179
- case "mesh_init": {
81180
- const workspace = typeof args?.workspace === "string" && args.workspace.trim() ? args.workspace.trim() : process.cwd();
81181
- const mesh = args?.inlineMesh || {};
81182
- try {
81183
- const detected = await detectCLIs(this.deps.providerLoader, { includeVersion: true });
81184
- return { ...runMeshInit(mesh, workspace, detected, {
81185
- write: args?.write === true,
81186
- overwrite: args?.overwrite === true
81187
- }) };
81188
- } catch (e) {
81189
- return { success: false, error: e?.message || String(e) };
81190
- }
81191
- }
81192
- case "plan_mesh_refine_node": {
81193
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81194
- const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
81195
- if (!meshId || !nodeId) return { success: false, error: "meshId and nodeId required" };
81196
- const meshRecord = await this.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
81197
- const mesh = meshRecord?.mesh;
81198
- const node = mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
81199
- if (!node?.workspace) return { success: false, error: `Node '${nodeId}' workspace not found` };
81200
- return {
81201
- success: true,
81202
- dryRun: true,
81203
- nodeId,
81204
- workspace: node.workspace,
81205
- validationPlan: buildMeshRefineValidationPlan(mesh, node.workspace),
81206
- mergeWillRun: false,
81207
- cleanupWillRun: false
81208
- };
81209
- }
81210
- case "fast_forward_mesh_node": {
81211
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81212
- const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
81213
- let workspace = typeof args?.workspace === "string" ? args.workspace.trim() : "";
81214
- let submoduleIgnorePaths = Array.isArray(args?.submoduleIgnorePaths) ? args.submoduleIgnorePaths.filter((value) => typeof value === "string") : void 0;
81215
- let nodeDaemonId;
81216
- let allowAutoPublishSubmoduleMainCommits = false;
81217
- if (meshId && nodeId) {
81218
- const meshRecord = await this.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
81219
- const mesh = meshRecord?.mesh;
81220
- const node = mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
81221
- if (!workspace) {
81222
- workspace = typeof node?.workspace === "string" ? node.workspace.trim() : "";
81223
- }
81224
- if (!submoduleIgnorePaths && Array.isArray(node?.policy?.submoduleIgnorePaths)) {
81225
- submoduleIgnorePaths = node.policy.submoduleIgnorePaths.filter((value) => typeof value === "string");
81226
- }
81227
- allowAutoPublishSubmoduleMainCommits = mesh?.policy?.allowAutoPublishSubmoduleMainCommits === true;
81228
- nodeDaemonId = typeof node?.daemonId === "string" ? node.daemonId.trim() : void 0;
81229
- }
81230
- const selfDaemonId = this.deps.statusInstanceId;
81231
- const isRemote = nodeDaemonId && selfDaemonId && !daemonIdsEquivalent(nodeDaemonId, selfDaemonId);
81232
- if (isRemote && this.deps.dispatchMeshCommand && !args?._meshDirectDispatch) {
81233
- const forwarded = await this.deps.dispatchMeshCommand(nodeDaemonId, "fast_forward_mesh_node", {
81234
- ...typeof args === "object" && args !== null ? args : {},
81235
- workspace,
81236
- _meshDirectDispatch: true
81237
- });
81238
- return forwarded ?? { success: false, error: "no response from remote node" };
81239
- }
81240
- const result = await fastForwardMeshNode({
81241
- meshId: meshId || void 0,
81242
- nodeId: nodeId || void 0,
81243
- workspace,
81244
- branch: typeof args?.branch === "string" ? args.branch : void 0,
81245
- execute: args?.execute === true,
81246
- dryRun: args?.dryRun === true,
81247
- updateSubmodules: args?.updateSubmodules === true,
81248
- submoduleIgnorePaths,
81249
- mode: args?.mode === "push" ? "push" : "merge",
81250
- pushSubmodules: args?.pushSubmodules === true,
81251
- allowAutoPublishSubmoduleMainCommits
81252
- });
81253
- return result;
81254
- }
81255
- case "refine_mesh_node": {
81256
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81257
- const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
81258
- if (!meshId || !nodeId) return { success: false, error: "meshId and nodeId required" };
81259
- {
81260
- const meshRecordForForward = await this.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
81261
- const forwardNode = meshRecordForForward?.mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
81262
- const nodeDaemonId = typeof forwardNode?.daemonId === "string" ? forwardNode.daemonId.trim() : void 0;
81263
- const selfDaemonId = this.deps.statusInstanceId;
81264
- const isRemote = nodeDaemonId && selfDaemonId && !daemonIdsEquivalent(nodeDaemonId, selfDaemonId);
81265
- if (isRemote && this.deps.dispatchMeshCommand && !args?._meshDirectDispatch) {
81266
- const callerCoordinatorDaemonId = typeof args?.coordinatorDaemonId === "string" && args.coordinatorDaemonId.trim() ? args.coordinatorDaemonId.trim() : void 0;
81267
- const forwarded = await this.deps.dispatchMeshCommand(nodeDaemonId, "refine_mesh_node", {
81268
- ...typeof args === "object" && args !== null ? args : {},
81269
- coordinatorDaemonId: callerCoordinatorDaemonId || selfDaemonId,
81270
- _meshDirectDispatch: true
81271
- });
81272
- return forwarded ?? { success: false, error: "no response from remote node" };
81273
- }
81274
- }
81275
- const isDryRun = args?.dryRun !== false && args?.execute !== true;
81276
- if (isDryRun) {
81277
- const meshRecord = await this.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
81278
- const mesh = meshRecord?.mesh;
81279
- const node = mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
81280
- if (!node?.workspace) return { success: false, error: `Node '${nodeId}' workspace not found` };
81281
- return {
81282
- success: true,
81283
- dryRun: true,
81284
- nodeId,
81285
- workspace: node.workspace,
81286
- validationPlan: buildMeshRefineValidationPlan(mesh, node.workspace),
81287
- mergeWillRun: false,
81288
- cleanupWillRun: false,
81289
- hint: "Dry-run only \u2014 no merge/push/cleanup performed. Re-invoke with execute:true to converge this node."
81290
- };
81291
- }
81292
- return this.startMeshRefineJob(meshId, nodeId, args);
81293
- }
81294
- case "batch_refine_mesh_nodes": {
81295
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81296
- if (!meshId) return { success: false, error: "meshId required" };
81297
- const requestedNodeIds = Array.isArray(args?.nodeIds) ? args.nodeIds.filter((v) => typeof v === "string" && v.trim().length > 0).map((v) => v.trim()) : void 0;
81298
- const isDryRun = args?.dryRun !== false && args?.execute !== true;
81299
- if (isDryRun) return this.batchRefineMeshNodes(meshId, requestedNodeIds, args);
81300
- return this.startMeshRefineBatchJob(meshId, requestedNodeIds, args);
81301
- }
81302
- case "remove_mesh_node": {
81303
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81304
- const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
81305
- if (!meshId || !nodeId) return { success: false, error: "meshId and nodeId required" };
81306
- try {
81307
- const meshRecord = await this.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
81308
- const mesh = meshRecord?.mesh;
81309
- const node = mesh?.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
81310
- if (node && !args?._meshDirectDispatch && node.isLocalWorktree !== true && args?.force !== true) {
81311
- const nodeDaemonId = typeof node.daemonId === "string" ? node.daemonId.trim() : "";
81312
- const nodeMachineId = readMeshNodeMachineId(node) || "";
81313
- const selfDaemonId = this.deps.statusInstanceId || "";
81314
- const selfMachineId = (() => {
81315
- try {
81316
- return loadConfig2().machineId || "";
81317
- } catch {
81318
- return "";
81319
- }
81320
- })();
81321
- const isCoordinatorBaseNode = !!selfDaemonId && (nodeDaemonId === selfDaemonId || nodeMachineId === selfDaemonId) || !!selfMachineId && (nodeDaemonId === selfMachineId || nodeMachineId === selfMachineId);
81322
- if (isCoordinatorBaseNode) {
81323
- return {
81324
- success: false,
81325
- removed: false,
81326
- code: "mesh_remove_coordinator_base_node_protected",
81327
- error: `Refusing to remove the coordinator's own base node '${typeof node.workspace === "string" ? node.workspace : nodeId}'. It is the local non-worktree node bound to this coordinator daemon; removing it breaks live mesh membership and forces a restart.`,
81328
- recoveryHint: "Remove worktree clone nodes instead, or pass force:true only if you are intentionally tearing down this mesh and accept that the coordinator must be re-registered/restarted."
81329
- };
81330
- }
81331
- }
81332
- const sessionCleanupMode = this.normalizeMeshSessionCleanupMode(
81333
- args?.sessionCleanupMode ?? args?.session_cleanup_mode ?? mesh?.policy?.sessionCleanupOnNodeRemove
81334
- );
81335
- const explicitSessionIds = Array.isArray(args?.sessionIds) ? args.sessionIds.filter((v) => typeof v === "string" && v.trim().length > 0).map((v) => v.trim()) : void 0;
81336
- let sessionCleanup;
81337
- if (node && sessionCleanupMode !== "preserve") {
81338
- sessionCleanup = await this.cleanupMeshSessions({
81339
- meshId,
81340
- nodeId,
81341
- node,
81342
- mode: sessionCleanupMode,
81343
- ...explicitSessionIds && explicitSessionIds.length > 0 ? { sessionIds: explicitSessionIds } : {},
81344
- source: "mesh_remove_node"
81345
- });
81346
- if (sessionCleanup.success === false) return { success: false, removed: false, sessionCleanup };
81347
- }
81348
- let worktreeCleanup;
81349
- if (node?.isLocalWorktree) {
81350
- const nodeDaemonId = typeof node.daemonId === "string" ? node.daemonId.trim() : void 0;
81351
- const isRemoteWorktree = nodeDaemonId && !daemonIdsEquivalent(nodeDaemonId, this.deps.statusInstanceId) && this.deps.dispatchMeshCommand && !args?._meshDirectDispatch;
81352
- if (isRemoteWorktree) {
81353
- const forwarded = await this.deps.dispatchMeshCommand(nodeDaemonId, "remove_mesh_node", {
81354
- ...typeof args === "object" && args !== null ? args : {},
81355
- _meshDirectDispatch: true
81356
- });
81357
- return forwarded ?? { success: false, error: "no response from remote node" };
81358
- }
81359
- const cleanupResult = await this.cleanupLocalWorktreeNode({ mesh, node, nodeId, force: args?.force === true });
81360
- if (cleanupResult.success === false) {
81361
- return {
81362
- success: false,
81363
- removed: false,
81364
- code: cleanupResult.code,
81365
- error: cleanupResult.error,
81366
- recoveryHint: cleanupResult.recoveryHint,
81367
- ...sessionCleanup ? { sessionCleanup } : {},
81368
- worktreeCleanup: cleanupResult
81369
- };
81370
- }
81371
- worktreeCleanup = cleanupResult;
81372
- }
81373
- let removed = false;
81374
- if (meshRecord?.inline) {
81375
- removed = this.removeInlineMeshNode(meshId, mesh, nodeId);
81376
- if (removed) this.invalidateAggregateMeshStatus(meshId);
81377
- if (!removed && !node) removed = true;
81378
- } else {
81379
- const { removeNode: removeNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
81380
- removed = removeNode2(meshId, nodeId);
81381
- if (!removed && !node) removed = true;
81382
- if (removed) this.invalidateAggregateMeshStatus(meshId);
81383
- }
81384
- if (removed) {
81385
- try {
81386
- const { appendLedgerEntry: appendLedgerEntry2 } = await Promise.resolve().then(() => (init_mesh_ledger(), mesh_ledger_exports));
81387
- appendLedgerEntry2(meshId, {
81388
- kind: "node_removed",
81389
- nodeId,
81390
- payload: {
81391
- worktree: !!node?.isLocalWorktree,
81392
- sessionCleanupMode,
81393
- workspace: typeof node?.workspace === "string" ? node.workspace : void 0,
81394
- daemonId: typeof node?.daemonId === "string" ? node.daemonId : void 0,
81395
- worktreeBranch: typeof node?.worktreeBranch === "string" ? node.worktreeBranch : void 0,
81396
- worktreeCleanupFallback: typeof worktreeCleanup?.fallback === "string" ? worktreeCleanup.fallback : void 0,
81397
- forced: worktreeCleanup?.forced === true ? true : void 0,
81398
- forceFallbackReason: typeof worktreeCleanup?.reason === "string" ? worktreeCleanup.reason : void 0
81399
- }
81400
- });
81401
- } catch {
81402
- }
81403
- }
81404
- const residueWarning = worktreeCleanup?.residue === true && typeof worktreeCleanup?.residueWarning === "string" ? worktreeCleanup.residueWarning : void 0;
81405
- return {
81406
- success: true,
81407
- removed,
81408
- ...residueWarning ? { residueWarning } : {},
81409
- ...sessionCleanup ? { sessionCleanup } : {},
81410
- ...worktreeCleanup ? { worktreeCleanup } : {}
81411
- };
81412
- } catch (e) {
81413
- return { success: false, error: e.message };
81414
- }
81415
- }
81416
- case "clone_mesh_node": {
81417
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81418
- const sourceNodeId = typeof args?.sourceNodeId === "string" ? args.sourceNodeId.trim() : "";
81419
- const branch = typeof args?.branch === "string" ? args.branch.trim() : "";
81420
- const baseBranch = typeof args?.baseBranch === "string" ? args.baseBranch.trim() : void 0;
81421
- if (!meshId) return { success: false, error: "meshId required" };
81422
- if (!sourceNodeId) return { success: false, error: "sourceNodeId required" };
81423
- if (!branch) return { success: false, error: "branch required" };
81424
- const ownerFailure = await this.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "worktree clone");
81425
- if (ownerFailure) return ownerFailure;
81426
- try {
81427
- const meshRecord = await this.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
81428
- const mesh = meshRecord?.mesh;
81429
- if (!mesh) return { success: false, error: "Mesh not found" };
81430
- const sourceNode = mesh.nodes?.find((n) => meshNodeIdMatches(n, sourceNodeId));
81431
- if (!sourceNode) return { success: false, error: `Source node '${sourceNodeId}' not found in mesh` };
81432
- const sourceDaemonId = typeof sourceNode.daemonId === "string" ? sourceNode.daemonId.trim() : void 0;
81433
- if (sourceDaemonId && !daemonIdsEquivalent(sourceDaemonId, this.deps.statusInstanceId) && this.deps.dispatchMeshCommand && !args?._meshDirectDispatch) {
81434
- const forwarded = await this.deps.dispatchMeshCommand(sourceDaemonId, "clone_mesh_node", {
81435
- ...typeof args === "object" && args !== null ? args : {},
81436
- _meshDirectDispatch: true
81437
- });
81438
- return forwarded ?? { success: false, error: "no response from remote node" };
81439
- }
81440
- const repoRoot = sourceNode.repoRoot || sourceNode.workspace;
81441
- const { createWorktree: createWorktree2 } = await Promise.resolve().then(() => (init_git_worktree(), git_worktree_exports));
81442
- const result = await createWorktree2({
81443
- repoRoot,
81444
- branch,
81445
- baseBranch,
81446
- meshName: mesh.name
81447
- });
81448
- let node;
81449
- if (meshRecord.inline) {
81450
- const { randomUUID: randomUUID15 } = await import("crypto");
81451
- node = {
81452
- id: `node_${randomUUID15().replace(/-/g, "")}`,
81453
- workspace: result.worktreePath,
81454
- repoRoot: result.worktreePath,
81455
- daemonId: sourceNode.daemonId,
81456
- machineId: sourceNode.machineId ?? sourceNode.machine_id,
81457
- userOverrides: { ...sourceNode.userOverrides || {} },
81458
- policy: { ...sourceNode.policy || {} },
81459
- isLocalWorktree: true,
81460
- worktreeBranch: result.branch,
81461
- clonedFromNodeId: sourceNodeId
81462
- };
81463
- this.updateInlineMeshNode(meshId, mesh, node);
81464
- } else {
81465
- const { addNode: addNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
81466
- node = addNode2(meshId, {
81467
- workspace: result.worktreePath,
81468
- repoRoot: result.worktreePath,
81469
- daemonId: sourceNode.daemonId,
81470
- machineId: sourceNode.machineId ?? sourceNode.machine_id,
81471
- userOverrides: { ...sourceNode.userOverrides || {} },
81472
- isLocalWorktree: true,
81473
- worktreeBranch: result.branch,
81474
- clonedFromNodeId: sourceNodeId,
81475
- policy: { ...sourceNode.policy || {} }
81476
- });
81477
- if (!node) return { success: false, error: "Failed to register worktree node" };
81478
- const inlineForReconcile = this.getCachedInlineMesh(meshId);
81479
- if (inlineForReconcile) this.updateInlineMeshNode(meshId, inlineForReconcile, node);
81480
- this.invalidateAggregateMeshStatus(meshId);
81481
- }
81482
- const persistWorktreeSetupState = async (bootstrapState2) => {
81483
- node.worktreeBootstrap = bootstrapState2;
81484
- if (meshRecord.inline) {
81485
- this.updateInlineMeshNode(meshId, mesh, node);
81486
- return;
81487
- }
81488
- try {
81489
- const { updateNode: updateNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
81490
- updateNode2(meshId, node.id, { worktreeBootstrap: bootstrapState2 });
81491
- this.invalidateAggregateMeshStatus(meshId);
81492
- } catch {
81493
- }
81494
- };
81495
- const appendCloneLedger = async (initSubmodules2, bootstrapState2) => {
81496
- try {
81497
- const { appendLedgerEntry: appendLedgerEntry2 } = await Promise.resolve().then(() => (init_mesh_ledger(), mesh_ledger_exports));
81498
- appendLedgerEntry2(meshId, {
81499
- kind: "node_cloned",
81500
- nodeId: node.id,
81501
- payload: {
81502
- sourceNodeId,
81503
- branch: result.branch,
81504
- worktreePath: result.worktreePath,
81505
- submodulesInitialized: initSubmodules2,
81506
- worktreeBootstrap: {
81507
- status: bootstrapState2.status,
81508
- required: bootstrapState2.required,
81509
- configSource: bootstrapState2.configSource,
81510
- configSourceType: bootstrapState2.configSourceType,
81511
- lastCommand: bootstrapState2.lastCommand,
81512
- exitCode: bootstrapState2.exitCode
81513
- }
81514
- }
81515
- });
81516
- } catch {
81517
- }
81518
- };
81519
- const initSubmodules = sourceNode.policy?.initSubmodulesOnClone !== false;
81520
- const loadedBootstrap = loadMeshWorktreeBootstrapConfig(mesh, result.worktreePath);
81521
- const runningBootstrapState = {
81522
- status: "running",
81523
- required: loadedBootstrap.config?.required !== false,
81524
- configSource: loadedBootstrap.path || loadedBootstrap.source,
81525
- configSourceType: loadedBootstrap.sourceType,
81526
- startedAt: (/* @__PURE__ */ new Date()).toISOString()
81527
- };
81528
- await persistWorktreeSetupState(runningBootstrapState);
81529
- const finishWorktreeSetup = async () => {
81530
- let submodulesInitialized2 = false;
81531
- if (initSubmodules) {
81532
- try {
81533
- const { runGit: runGit3 } = await Promise.resolve().then(() => (init_git_executor(), git_executor_exports));
81534
- await runGit3(
81535
- { workspace: result.worktreePath, repoRoot: result.worktreePath, isGitRepo: true },
81536
- ["submodule", "update", "--init", "--recursive"],
81537
- { timeoutMs: 12e4 }
81538
- );
81539
- submodulesInitialized2 = true;
81540
- const sourceWorkspace = sourceNode.repoRoot || sourceNode.workspace;
81541
- if (sourceWorkspace) {
81542
- try {
81543
- const { runGit: rg } = await Promise.resolve().then(() => (init_git_executor(), git_executor_exports));
81544
- const sourceCtx = { workspace: sourceWorkspace, repoRoot: sourceWorkspace, isGitRepo: true };
81545
- const worktreeCtx = { workspace: result.worktreePath, repoRoot: result.worktreePath, isGitRepo: true };
81546
- const sourceStatusOut = await rg(sourceCtx, ["submodule", "status", "oss"], { timeoutMs: 1e4 });
81547
- const sourceStatusLine = (typeof sourceStatusOut === "string" ? sourceStatusOut : sourceStatusOut?.stdout ?? "").trim();
81548
- const sourceShaMatch = sourceStatusLine.match(/^[+\- ]?([0-9a-f]{40})/);
81549
- const sourceSha = sourceShaMatch?.[1];
81550
- if (sourceSha) {
81551
- const ossCtx = { workspace: `${result.worktreePath}/oss`, repoRoot: `${result.worktreePath}/oss`, isGitRepo: true };
81552
- const worktreeOssHeadOut = await rg(ossCtx, ["rev-parse", "HEAD"], { timeoutMs: 1e4 });
81553
- const worktreeOssSha = (typeof worktreeOssHeadOut === "string" ? worktreeOssHeadOut : worktreeOssHeadOut?.stdout ?? "").trim();
81554
- if (worktreeOssSha !== sourceSha) {
81555
- await rg(ossCtx, ["fetch", `${sourceWorkspace}/oss`, "HEAD"], { timeoutMs: 6e4 });
81556
- await rg(ossCtx, ["checkout", sourceSha], { timeoutMs: 1e4 });
81557
- await rg(worktreeCtx, ["add", "oss"], { timeoutMs: 1e4 });
81558
- await rg(worktreeCtx, ["commit", "-m", "chore: sync oss to source node HEAD on clone"], { timeoutMs: 1e4 });
81559
- console.log(`[mesh] Synced oss submodule to source HEAD ${sourceSha.slice(0, 8)} in worktree`);
81560
- }
81561
- }
81562
- } catch (ossErr) {
81563
- console.warn("[mesh] oss submodule sync to source HEAD failed (best-effort):", ossErr.message);
81564
- }
81565
- }
81566
- } catch (subErr) {
81567
- console.warn("[mesh] Submodule init failed for worktree:", subErr.message);
81568
- }
81569
- }
81570
- const bootstrapState2 = await runMeshWorktreeBootstrap(mesh, result.worktreePath);
81571
- await persistWorktreeSetupState(bootstrapState2);
81572
- await appendCloneLedger(submodulesInitialized2, bootstrapState2);
81573
- return { submodulesInitialized: submodulesInitialized2, bootstrapState: bootstrapState2 };
81574
- };
81575
- const requestedSetupWaitMs = Number(args?.setupWaitMs ?? args?.bootstrapWaitMs ?? 8e3);
81576
- const setupWaitMs = Number.isFinite(requestedSetupWaitMs) ? Math.min(Math.max(requestedSetupWaitMs, 0), 14e3) : 8e3;
81577
- const setupPromise = finishWorktreeSetup();
81578
- const setupResult = await Promise.race([
81579
- setupPromise.then((value) => ({ completed: true, value })),
81580
- new Promise((resolve24) => setTimeout(() => resolve24({ completed: false }), setupWaitMs))
81581
- ]);
81582
- const emitBootstrapEvent = (eventStatus2, bootstrapState2, startedAtMs, extraPayload) => {
81583
- try {
81584
- const durationMs = Date.now() - startedAtMs;
81585
- const event = `worktree_${eventStatus2}`;
81586
- const metadataEvent = {
81587
- source: "clone_mesh_node_bootstrap",
81588
- nodeId: node.id,
81589
- status: eventStatus2,
81590
- worktreePath: result.worktreePath,
81591
- durationMs,
81592
- bootstrapStatus: bootstrapState2.status,
81593
- ...bootstrapState2.error ? { error: bootstrapState2.error } : {},
81594
- ...bootstrapState2.exitCode !== void 0 ? { exitCode: bootstrapState2.exitCode } : {},
81595
- ...extraPayload || {}
81596
- };
81597
- if (typeof this.deps.instanceManager?.getByCategory === "function") {
81598
- const forwarded = handleMeshForwardEvent(
81599
- { instanceManager: this.deps.instanceManager },
81600
- { event, meshId, nodeId: node.id, workspace: result.worktreePath, metadataEvent }
81601
- );
81602
- if (forwarded?.success === true) return;
81603
- }
81604
- queuePendingMeshCoordinatorEvent({
81605
- event,
81606
- meshId,
81607
- nodeLabel: node.id,
81608
- nodeId: node.id,
81609
- workspace: result.worktreePath,
81610
- metadataEvent,
81611
- queuedAt: Date.now()
81612
- });
81613
- } catch {
81614
- }
81615
- };
81616
- const bootstrapStartedMs = Date.now();
81617
- if (!setupResult.completed) {
81618
- setupPromise.then(({ bootstrapState: bootstrapState2 }) => {
81619
- emitBootstrapEvent("bootstrap_complete", bootstrapState2, bootstrapStartedMs);
81620
- }).catch((error48) => {
81621
- const failedState = {
81622
- ...runningBootstrapState,
81623
- status: "failed",
81624
- completedAt: (/* @__PURE__ */ new Date()).toISOString(),
81625
- error: error48?.message || String(error48)
81626
- };
81627
- void persistWorktreeSetupState(failedState);
81628
- void appendCloneLedger(false, failedState);
81629
- emitBootstrapEvent("bootstrap_failed", failedState, bootstrapStartedMs, { error: error48?.message || String(error48) });
81630
- });
81631
- return {
81632
- success: true,
81633
- async: true,
81634
- status: "accepted",
81635
- node,
81636
- worktreePath: result.worktreePath,
81637
- branch: result.branch,
81638
- worktreeBootstrap: runningBootstrapState,
81639
- worktreeSetup: {
81640
- status: "running",
81641
- setupWaitMs,
81642
- message: "Worktree node is registered; submodule/bootstrap setup is continuing in the background."
81643
- }
81644
- };
81645
- }
81646
- const { submodulesInitialized, bootstrapState } = setupResult.value;
81647
- emitBootstrapEvent("bootstrap_complete", bootstrapState, bootstrapStartedMs);
81648
- return {
81649
- success: true,
81650
- node,
81651
- worktreePath: result.worktreePath,
81652
- branch: result.branch,
81653
- submodulesInitialized,
81654
- worktreeBootstrap: bootstrapState
81655
- };
81656
- } catch (e) {
81657
- return { success: false, error: e.message };
81658
- }
81659
- }
81660
- case "retry_mesh_node_bootstrap": {
81661
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81662
- const nodeId = typeof args?.nodeId === "string" ? args.nodeId.trim() : "";
81663
- if (!meshId) return { success: false, error: "meshId required" };
81664
- if (!nodeId) return { success: false, error: "nodeId required" };
81665
- const ownerFailure = await this.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "bootstrap retry");
81666
- if (ownerFailure) return ownerFailure;
81667
- try {
81668
- const meshRecord = await this.getMeshForCommand(meshId, args?.inlineMesh, { preferInline: true });
81669
- const mesh = meshRecord?.mesh;
81670
- if (!mesh) return { success: false, error: "Mesh not found" };
81671
- const node = mesh.nodes?.find((n) => meshNodeIdMatches(n, nodeId));
81672
- if (!node) return { success: false, error: `Node '${nodeId}' not found in mesh` };
81673
- if (!node.isLocalWorktree) return { success: false, error: "Node is not a local worktree node" };
81674
- const nodeDaemonId = typeof node.daemonId === "string" ? node.daemonId.trim() : void 0;
81675
- if (nodeDaemonId && !daemonIdsEquivalent(nodeDaemonId, this.deps.statusInstanceId) && this.deps.dispatchMeshCommand && !args?._meshDirectDispatch) {
81676
- const forwarded = await this.deps.dispatchMeshCommand(nodeDaemonId, "retry_mesh_node_bootstrap", {
81677
- ...typeof args === "object" && args !== null ? args : {},
81678
- _meshDirectDispatch: true
81679
- });
81680
- return forwarded ?? { success: false, error: "no response from remote node" };
81681
- }
81682
- const currentBootstrap = node.worktreeBootstrap;
81683
- if (currentBootstrap?.status === "running") {
81684
- return { success: false, error: "Bootstrap is already running for this node" };
81685
- }
81686
- const worktreePath = node.workspace || node.repoRoot;
81687
- if (!worktreePath) return { success: false, error: "Node has no workspace path" };
81688
- const loadedBootstrap = loadMeshWorktreeBootstrapConfig(mesh, worktreePath);
81689
- const runningState = {
81690
- status: "running",
81691
- required: loadedBootstrap.config?.required !== false,
81692
- configSource: loadedBootstrap.path || loadedBootstrap.source,
81693
- configSourceType: loadedBootstrap.sourceType,
81694
- startedAt: (/* @__PURE__ */ new Date()).toISOString()
81695
- };
81696
- const persistState = async (bootstrapState2) => {
81697
- node.worktreeBootstrap = bootstrapState2;
81698
- if (meshRecord.inline) {
81699
- this.updateInlineMeshNode(meshId, mesh, node);
81700
- return;
81701
- }
81702
- try {
81703
- const { updateNode: updateNode2 } = await Promise.resolve().then(() => (init_mesh_config(), mesh_config_exports));
81704
- updateNode2(meshId, node.id, { worktreeBootstrap: bootstrapState2 });
81705
- this.invalidateAggregateMeshStatus(meshId);
81706
- } catch {
81707
- }
81708
- };
81709
- await persistState(runningState);
81710
- const bootstrapState = await runMeshWorktreeBootstrap(mesh, worktreePath);
81711
- await persistState(bootstrapState);
81712
- return { success: true, bootstrapState };
81713
- } catch (e) {
81714
- return { success: false, error: e.message };
81715
- }
81716
- }
81717
- case "trigger_mesh_queue": {
81718
- const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";
81719
- if (!meshId) return { success: false, error: "meshId required" };
81720
- const ownerFailure = await this.requireMeshHostMutationOwner(meshId, args?.inlineMesh, "queue trigger");
81721
- if (ownerFailure) return ownerFailure;
81722
- try {
81723
- const { triggerMeshQueue: triggerMeshQueue2, tryAssignQueueTask: tryAssignQueueTask2 } = await Promise.resolve().then(() => (init_mesh_events(), mesh_events_exports));
81724
- const preferredNodeId = typeof args?.preferredNodeId === "string" ? args.preferredNodeId.trim() : "";
81725
- if (preferredNodeId) {
81726
- const cliInstances = this.deps.instanceManager.getByCategory("cli");
81727
- const sorted = [...cliInstances].sort((a, b) => {
81728
- const aSettings = a.getState().settings || {};
81729
- const bSettings = b.getState().settings || {};
81730
- const aNode = readStringValue(aSettings.meshNodeId, aSettings.nodeId);
81731
- const bNode = readStringValue(bSettings.meshNodeId, bSettings.nodeId);
81732
- return (aNode === preferredNodeId ? -1 : 0) - (bNode === preferredNodeId ? -1 : 0);
81733
- });
81734
- for (const inst of sorted) {
81735
- const state = inst.getState();
81736
- const settings = state.settings || {};
81737
- const nodeId = readStringValue(settings.meshNodeId, settings.nodeId);
81738
- if (!nodeId || nodeId !== preferredNodeId) continue;
81739
- const meshNodeFor = readStringValue(settings.meshNodeFor);
81740
- if (meshNodeFor !== meshId) continue;
81741
- const status = (readStringValue(state.status) || "").toLowerCase();
81742
- if (status !== "idle") continue;
81743
- const sessionId = typeof state.instanceId === "string" ? state.instanceId : "";
81744
- const providerType = readStringValue(state.type, settings.providerType) || "";
81745
- if (sessionId && providerType) {
81746
- tryAssignQueueTask2(this.deps, meshId, nodeId, sessionId, providerType);
81747
- break;
81748
- }
81749
- }
81750
- }
81751
- const trigger = await triggerMeshQueue2(this.deps, meshId);
81752
- return { success: true, trigger };
81753
- } catch (e) {
81754
- return { success: false, error: e.message };
81755
- }
81756
- }
81757
81815
  // ─── Mesh Coordinator Launch ───
81758
81816
  case "launch_mesh_coordinator": {
81759
81817
  const meshId = typeof args?.meshId === "string" ? args.meshId.trim() : "";