@adhdev/daemon-core 0.9.82-rc.230 → 0.9.82-rc.232
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/package.json
CHANGED
package/src/commands/router.ts
CHANGED
|
@@ -5866,12 +5866,15 @@ export class DaemonCommandRouter {
|
|
|
5866
5866
|
nodeDaemonId = typeof node?.daemonId === 'string' ? node.daemonId.trim() : undefined;
|
|
5867
5867
|
}
|
|
5868
5868
|
// If the target node belongs to a remote daemon, forward the command there.
|
|
5869
|
+
// _meshDirectDispatch prevents re-forwarding (and P2P self-dial) when the stored
|
|
5870
|
+
// daemonId uses a legacy format that doesn't match the receiving daemon's identity.
|
|
5869
5871
|
const selfDaemonId = this.deps.statusInstanceId;
|
|
5870
5872
|
const isRemote = nodeDaemonId && selfDaemonId && nodeDaemonId !== selfDaemonId;
|
|
5871
|
-
if (isRemote && this.deps.dispatchMeshCommand) {
|
|
5873
|
+
if (isRemote && this.deps.dispatchMeshCommand && !args?._meshDirectDispatch) {
|
|
5872
5874
|
const forwarded = await this.deps.dispatchMeshCommand(nodeDaemonId!, 'fast_forward_mesh_node', {
|
|
5873
5875
|
...(typeof args === 'object' && args !== null ? args as Record<string, unknown> : {}),
|
|
5874
5876
|
workspace,
|
|
5877
|
+
_meshDirectDispatch: true,
|
|
5875
5878
|
});
|
|
5876
5879
|
return (forwarded ?? { success: false, error: 'no response from remote node' }) as CommandRouterResult;
|
|
5877
5880
|
}
|
|
@@ -5916,11 +5919,14 @@ export class DaemonCommandRouter {
|
|
|
5916
5919
|
let worktreeCleanup: Record<string, unknown> | undefined;
|
|
5917
5920
|
if (node?.isLocalWorktree) {
|
|
5918
5921
|
const nodeDaemonId = typeof node.daemonId === 'string' ? node.daemonId.trim() : undefined;
|
|
5919
|
-
const isRemoteWorktree = nodeDaemonId && nodeDaemonId !== this.deps.statusInstanceId && this.deps.dispatchMeshCommand
|
|
5922
|
+
const isRemoteWorktree = nodeDaemonId && nodeDaemonId !== this.deps.statusInstanceId && this.deps.dispatchMeshCommand
|
|
5923
|
+
&& !args?._meshDirectDispatch;
|
|
5920
5924
|
if (isRemoteWorktree) {
|
|
5921
5925
|
// Worktree lives on a different machine — ask that daemon to clean it up.
|
|
5926
|
+
// _meshDirectDispatch prevents re-forwarding when stored daemonId uses legacy format.
|
|
5922
5927
|
const forwarded = await this.deps.dispatchMeshCommand!(nodeDaemonId!, 'remove_mesh_node', {
|
|
5923
5928
|
...(typeof args === 'object' && args !== null ? args as Record<string, unknown> : {}),
|
|
5929
|
+
_meshDirectDispatch: true,
|
|
5924
5930
|
});
|
|
5925
5931
|
return (forwarded ?? { success: false, error: 'no response from remote node' }) as CommandRouterResult;
|
|
5926
5932
|
}
|
|
@@ -6007,10 +6013,14 @@ export class DaemonCommandRouter {
|
|
|
6007
6013
|
if (!sourceNode) return { success: false, error: `Source node '${sourceNodeId}' not found in mesh` };
|
|
6008
6014
|
|
|
6009
6015
|
// Forward to the source node's daemon if it's on a different machine.
|
|
6016
|
+
// _meshDirectDispatch prevents infinite re-forwarding when the stored daemonId
|
|
6017
|
+
// uses a legacy format that doesn't match the receiving daemon's statusInstanceId.
|
|
6010
6018
|
const sourceDaemonId = typeof sourceNode.daemonId === 'string' ? sourceNode.daemonId.trim() : undefined;
|
|
6011
|
-
if (sourceDaemonId && sourceDaemonId !== this.deps.statusInstanceId && this.deps.dispatchMeshCommand
|
|
6019
|
+
if (sourceDaemonId && sourceDaemonId !== this.deps.statusInstanceId && this.deps.dispatchMeshCommand
|
|
6020
|
+
&& !args?._meshDirectDispatch) {
|
|
6012
6021
|
const forwarded = await this.deps.dispatchMeshCommand(sourceDaemonId, 'clone_mesh_node', {
|
|
6013
6022
|
...(typeof args === 'object' && args !== null ? args as Record<string, unknown> : {}),
|
|
6023
|
+
_meshDirectDispatch: true,
|
|
6014
6024
|
});
|
|
6015
6025
|
return (forwarded ?? { success: false, error: 'no response from remote node' }) as CommandRouterResult;
|
|
6016
6026
|
}
|
|
@@ -6271,10 +6281,13 @@ export class DaemonCommandRouter {
|
|
|
6271
6281
|
if (!node.isLocalWorktree) return { success: false, error: 'Node is not a local worktree node' };
|
|
6272
6282
|
|
|
6273
6283
|
// Bootstrap runs scripts in the worktree path — forward to the node's daemon if remote.
|
|
6284
|
+
// _meshDirectDispatch prevents re-forwarding when stored daemonId uses legacy format.
|
|
6274
6285
|
const nodeDaemonId = typeof node.daemonId === 'string' ? node.daemonId.trim() : undefined;
|
|
6275
|
-
if (nodeDaemonId && nodeDaemonId !== this.deps.statusInstanceId && this.deps.dispatchMeshCommand
|
|
6286
|
+
if (nodeDaemonId && nodeDaemonId !== this.deps.statusInstanceId && this.deps.dispatchMeshCommand
|
|
6287
|
+
&& !args?._meshDirectDispatch) {
|
|
6276
6288
|
const forwarded = await this.deps.dispatchMeshCommand(nodeDaemonId, 'retry_mesh_node_bootstrap', {
|
|
6277
6289
|
...(typeof args === 'object' && args !== null ? args as Record<string, unknown> : {}),
|
|
6290
|
+
_meshDirectDispatch: true,
|
|
6278
6291
|
});
|
|
6279
6292
|
return (forwarded ?? { success: false, error: 'no response from remote node' }) as CommandRouterResult;
|
|
6280
6293
|
}
|
|
@@ -97,6 +97,15 @@ export function buildMeshSystemMessage(args: {
|
|
|
97
97
|
if (args.event === 'monitor:long_generating') {
|
|
98
98
|
return `[System] ${args.nodeLabel} is still reported as generating after a long interval${metadata}. Wait for pendingCoordinatorEvents or a completion/status event; if the user explicitly asks for status, make one bounded status check and then wait again.`;
|
|
99
99
|
}
|
|
100
|
+
if (args.event === 'worktree_bootstrap_complete') {
|
|
101
|
+
const worktreePath = readNonEmptyString(args.metadataEvent.worktreePath);
|
|
102
|
+
const durationMs = typeof args.metadataEvent.durationMs === 'number' ? args.metadataEvent.durationMs : undefined;
|
|
103
|
+
return `[System] ${args.nodeLabel} worktree bootstrap completed${worktreePath ? ` at ${worktreePath}` : ''}${durationMs !== undefined ? ` in ${Math.round(durationMs / 1000)}s` : ''}. The worktree is ready — use \`mesh_launch_session\` to start an agent.`;
|
|
104
|
+
}
|
|
105
|
+
if (args.event === 'worktree_bootstrap_failed') {
|
|
106
|
+
const error = readNonEmptyString(args.metadataEvent.error);
|
|
107
|
+
return `[System] ${args.nodeLabel} worktree bootstrap failed${error ? `: ${error}` : '.'}. Use \`mesh_retry_node_bootstrap\` to retry or inspect the node state.`;
|
|
108
|
+
}
|
|
100
109
|
if (args.event === 'refine:accepted') {
|
|
101
110
|
const jobId = readRefineJobId({ metadataEvent: args.metadataEvent });
|
|
102
111
|
return `[System] Refinery accepted async job${jobId ? ` ${jobId}` : ''} for ${args.nodeLabel}. Completion/failure will be delivered as a terminal refine event; do not poll repeatedly.`;
|
|
@@ -295,11 +295,9 @@ function expandPath(template: string, input: NativeHistoryInput): string | null
|
|
|
295
295
|
// Re-expand ~ in case the fallback used it.
|
|
296
296
|
if (out.startsWith('~/')) out = path.join(os.homedir(), out.slice(2));
|
|
297
297
|
const now = new Date();
|
|
298
|
-
//
|
|
299
|
-
//
|
|
300
|
-
//
|
|
301
|
-
// Without realpath, the spec template `~/.claude/projects/{cwd_dashed}/…`
|
|
302
|
-
// builds `-tmp-foo` and never finds the actual `-private-tmp-foo` dir.
|
|
298
|
+
// Claude writes per-cwd transcripts under the resolved path and replaces
|
|
299
|
+
// every non-alphanumeric project-path character except `_` and `-` with
|
|
300
|
+
// `-`. Realpath also handles aliases such as /tmp -> /private/tmp.
|
|
303
301
|
const workspaceRaw = input.workspace ?? '';
|
|
304
302
|
let workspaceResolved = workspaceRaw;
|
|
305
303
|
if (workspaceRaw) {
|
|
@@ -309,6 +307,7 @@ function expandPath(template: string, input: NativeHistoryInput): string | null
|
|
|
309
307
|
const vars: Record<string, string> = {
|
|
310
308
|
cwd: workspaceResolved,
|
|
311
309
|
cwd_dashed: workspaceResolved.replace(/\//g, '-'),
|
|
310
|
+
cwd_claude_project: claudeProjectDirName(workspaceResolved),
|
|
312
311
|
session_id: input.providerSessionId || input.sessionId || input.historySessionId || '',
|
|
313
312
|
yyyy: String(now.getFullYear()),
|
|
314
313
|
mm: String(now.getMonth() + 1).padStart(2, '0'),
|
|
@@ -329,6 +328,10 @@ function expandPath(template: string, input: NativeHistoryInput): string | null
|
|
|
329
328
|
return out;
|
|
330
329
|
}
|
|
331
330
|
|
|
331
|
+
function claudeProjectDirName(workspace: string): string {
|
|
332
|
+
return workspace.replace(/[^A-Za-z0-9_-]/g, '-');
|
|
333
|
+
}
|
|
334
|
+
|
|
332
335
|
function globToRegex(pattern: string): RegExp {
|
|
333
336
|
// Minimal glob: `*` → `[^/]*`, `?` → `[^/]`, `.` → `\.`. Anchored.
|
|
334
337
|
const re = pattern
|
|
@@ -463,6 +466,7 @@ function expandPathForDate(template: string, input: NativeHistoryInput, day: Dat
|
|
|
463
466
|
const vars: Record<string, string> = {
|
|
464
467
|
cwd: workspaceResolved,
|
|
465
468
|
cwd_dashed: workspaceResolved.replace(/\//g, '-'),
|
|
469
|
+
cwd_claude_project: claudeProjectDirName(workspaceResolved),
|
|
466
470
|
session_id: input.providerSessionId || input.sessionId || input.historySessionId || '',
|
|
467
471
|
yyyy: String(day.getFullYear()),
|
|
468
472
|
mm: String(day.getMonth() + 1).padStart(2, '0'),
|