u-foo 2.3.32 → 2.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +157 -213
- package/README.zh-CN.md +151 -197
- package/SKILLS/ufoo/SKILL.md +8 -8
- package/bin/uagy.js +69 -0
- package/bin/uclaude.js +2 -2
- package/bin/ucode.js +4 -4
- package/bin/ucodex.js +2 -2
- package/bin/ufoo.js +5 -23
- package/modules/AGENTS.template.md +1 -1
- package/modules/bus/SKILLS/ubus/SKILL.md +35 -10
- package/package.json +5 -5
- package/scripts/chat-app-smoke.js +1 -1
- package/scripts/global-chat-switch-benchmark.js +5 -5
- package/scripts/ink-demo.js +1 -1
- package/scripts/ink-smoke.js +1 -1
- package/scripts/ucode-app-smoke.js +1 -1
- package/src/{agent → agents/activity}/activityDetector.js +39 -2
- package/src/{agent → agents/activity}/activityStatePublisher.js +1 -1
- package/src/{agent → agents/activity}/activityStateWriter.js +2 -2
- package/src/{agent → agents/activity}/activityTracker.js +1 -1
- package/src/agents/activity/index.js +8 -0
- package/src/{agent → agents/controller}/controllerToolExecutor.js +4 -4
- package/src/agents/controller/index.js +8 -0
- package/src/{agent → agents/controller}/loopObservability.js +2 -2
- package/src/{agent → agents/controller}/loopRuntime.js +1 -1
- package/src/{agent → agents/controller}/ufooAgent.js +9 -9
- package/src/agents/index.js +10 -0
- package/src/agents/internal/index.js +3 -0
- package/src/{agent → agents/internal}/internalRunner.js +45 -22
- package/src/agents/launch/agyConversation.js +159 -0
- package/src/agents/launch/index.js +12 -0
- package/src/{agent → agents/launch}/launchEnvironment.js +2 -3
- package/src/{agent → agents/launch}/launcher.js +64 -21
- package/src/{agent → agents/launch}/notifier.js +23 -12
- package/src/{agent → agents/launch}/ptyRunner.js +44 -12
- package/src/{agent → agents/launch}/ptyWrapper.js +2 -2
- package/src/{agent → agents/launch}/publisherRouting.js +1 -1
- package/src/{agent → agents/launch}/readyDetector.js +23 -0
- package/src/{agent → agents/prompts}/defaultBootstrap.js +63 -4
- package/src/{group/bootstrap.js → agents/prompts/groupBootstrap.js} +41 -6
- package/src/agents/prompts/index.js +8 -0
- package/src/{code/prompts → agents/prompts/native}/index.js +1 -1
- package/src/{agent → agents/providers}/claudeThreadProvider.js +1 -1
- package/src/{agent → agents/providers}/codexThreadProvider.js +1 -1
- package/src/{agent → agents/providers}/directAuthStatus.js +184 -1
- package/src/agents/providers/index.js +13 -0
- package/src/{agent → agents/providers}/upstreamTransport.js +2 -2
- package/src/{chat → app/chat}/agentSockets.js +1 -1
- package/src/{chat → app/chat}/commandExecutor.js +50 -26
- package/src/{chat → app/chat}/commands.js +119 -5
- package/src/{chat → app/chat}/daemonConnection.js +1 -1
- package/src/{chat → app/chat}/daemonMessageRouter.js +45 -3
- package/src/{chat → app/chat}/dashboardView.js +2 -1
- package/src/app/chat/index.js +6 -0
- package/src/{chat → app/chat}/inputSubmitHandler.js +4 -13
- package/src/{chat → app/chat}/internalAgentLogHistory.js +1 -1
- package/src/app/chat/multiWindow/index.js +268 -0
- package/src/app/chat/multiWindow/paneLayout.js +84 -0
- package/src/app/chat/multiWindow/paneManager.js +299 -0
- package/src/app/chat/multiWindow/renderer.js +384 -0
- package/src/app/chat/multiWindow/virtualTerminal.js +327 -0
- package/src/{chat → app/chat}/transport.js +1 -1
- package/src/{cli → app/cli}/ctxCoreCommands.js +3 -3
- package/src/{doctor/index.js → app/cli/features/doctor.js} +1 -1
- package/src/{init/index.js → app/cli/features/init.js} +14 -32
- package/src/{cli → app/cli}/groupCoreCommands.js +2 -2
- package/src/app/cli/index.js +9 -0
- package/src/{cli → app/cli}/onlineCoreCommands.js +5 -5
- package/src/{cli.js → app/cli/run.js} +59 -57
- package/src/app/index.js +6 -0
- package/src/code/agent.js +10 -9
- package/src/code/index.js +2 -0
- package/src/code/launcher/index.js +9 -0
- package/src/{agent → code/launcher}/ucode.js +7 -8
- package/src/{agent → code/launcher}/ucodeBootstrap.js +3 -3
- package/src/{agent → code/launcher}/ucodeBuild.js +2 -2
- package/src/{agent → code/launcher}/ucodeDoctor.js +2 -2
- package/src/{agent → code/launcher}/ucodeRuntimeConfig.js +1 -2
- package/src/code/nativeRunner.js +4 -4
- package/src/code/tui.js +3 -1454
- package/src/config.js +15 -2
- package/src/{bus → coordination/bus}/activate.js +2 -2
- package/src/{bus → coordination/bus}/daemon.js +15 -5
- package/src/coordination/bus/envelope.js +173 -0
- package/src/{bus → coordination/bus}/index.js +7 -3
- package/src/{bus → coordination/bus}/inject.js +11 -3
- package/src/{bus → coordination/bus}/message.js +1 -1
- package/src/coordination/bus/messageMeta.js +130 -0
- package/src/coordination/bus/promptEnvelope.js +65 -0
- package/src/{bus → coordination/bus}/shake.js +1 -1
- package/src/{bus → coordination/bus}/store.js +3 -3
- package/src/{bus → coordination/bus}/subscriber.js +2 -2
- package/src/{bus → coordination/bus}/utils.js +2 -2
- package/src/{history → coordination/history}/inputTimeline.js +5 -5
- package/src/coordination/index.js +10 -0
- package/src/{memory → coordination/memory}/historySearch.js +1 -1
- package/src/{memory → coordination/memory}/index.js +3 -3
- package/src/{report → coordination/report}/store.js +2 -2
- package/src/{status → coordination/status}/index.js +3 -3
- package/src/online/bridge.js +2 -2
- package/src/{controller → orchestration/controller}/flags.js +1 -1
- package/src/{controller → orchestration/controller}/gateRouter.js +1 -1
- package/src/orchestration/controller/index.js +10 -0
- package/src/{controller → orchestration/controller}/shadowGuard.js +1 -1
- package/src/orchestration/groups/bootstrap.js +3 -0
- package/src/orchestration/groups/index.js +10 -0
- package/src/orchestration/groups/promptProfiles.js +3 -0
- package/src/{group → orchestration/groups}/templates.js +1 -1
- package/src/{group → orchestration/groups}/validateTemplate.js +1 -1
- package/src/orchestration/index.js +7 -0
- package/src/orchestration/solo/index.js +3 -0
- package/src/{daemon → runtime/daemon}/agentProcessManager.js +1 -1
- package/src/{daemon → runtime/daemon}/cronOps.js +3 -2
- package/src/{daemon → runtime/daemon}/groupOrchestrator.js +26 -9
- package/src/{daemon → runtime/daemon}/index.js +105 -53
- package/src/{daemon → runtime/daemon}/ipcServer.js +1 -1
- package/src/{daemon → runtime/daemon}/nicknameScope.js +6 -3
- package/src/{daemon → runtime/daemon}/ops.js +48 -61
- package/src/{daemon → runtime/daemon}/promptLoop.js +1 -1
- package/src/{daemon → runtime/daemon}/promptRequest.js +7 -7
- package/src/runtime/daemon/providerSessions.js +230 -0
- package/src/{daemon → runtime/daemon}/reporting.js +4 -4
- package/src/{daemon → runtime/daemon}/run.js +4 -4
- package/src/{daemon → runtime/daemon}/soloBootstrap.js +7 -7
- package/src/{daemon → runtime/daemon}/status.js +5 -5
- package/src/runtime/index.js +10 -0
- package/src/{projects → runtime/projects}/registry.js +1 -1
- package/src/{terminal → runtime/terminal}/adapterRouter.js +0 -10
- package/src/{terminal → runtime/terminal}/adapters/internalAdapter.js +0 -4
- package/src/tools/handlers/common.js +1 -1
- package/src/tools/handlers/listAgents.js +1 -1
- package/src/tools/handlers/memory.js +3 -3
- package/src/tools/handlers/readBusSummary.js +1 -1
- package/src/tools/handlers/readOpenDecisions.js +1 -1
- package/src/tools/handlers/readProjectRegistry.js +1 -1
- package/src/tools/handlers/readPromptHistory.js +2 -2
- package/src/tools/schemaFixtures.js +1 -1
- package/src/ui/MIGRATION.md +42 -88
- package/src/ui/format/index.js +5 -28
- package/src/ui/index.js +1 -1
- package/src/ui/{components → ink}/ChatApp.js +812 -88
- package/src/ui/ink/DashboardBar.js +685 -0
- package/src/ui/{components → ink}/MultilineInput.js +230 -5
- package/src/ui/{components → ink}/UcodeApp.js +16 -7
- package/src/ui/{components → ink}/agentMirror.js +24 -19
- package/src/ui/{components → ink}/chatReducer.js +29 -7
- package/src/bus/messageMeta.js +0 -52
- package/src/chat/agentViewController.js +0 -1072
- package/src/chat/chatLogController.js +0 -138
- package/src/chat/completionController.js +0 -533
- package/src/chat/dashboardKeyController.js +0 -533
- package/src/chat/index.js +0 -2222
- package/src/chat/inputHistoryController.js +0 -135
- package/src/chat/inputListenerController.js +0 -470
- package/src/chat/layout.js +0 -186
- package/src/chat/pasteController.js +0 -81
- package/src/chat/statusLineController.js +0 -223
- package/src/chat/streamTracker.js +0 -156
- package/src/code/config +0 -0
- package/src/daemon/providerSessions.js +0 -488
- package/src/terminal/adapters/internalPtyAdapter.js +0 -42
- package/src/ui/components/DashboardBar.js +0 -417
- /package/src/{code/prompts → agents/prompts/native}/actions.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/efficiency.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/environment.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/identity.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/safety.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/sections.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/system.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/tasks.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/toolDescriptions/bash.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/toolDescriptions/edit.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/toolDescriptions/read.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/toolDescriptions/write.js +0 -0
- /package/src/{code/prompts → agents/prompts/native}/ufoo.js +0 -0
- /package/src/{group → agents/prompts}/promptProfiles.js +0 -0
- /package/src/{agent → agents/providers}/claudeEventTranslator.js +0 -0
- /package/src/{agent → agents/providers}/claudeOauthTokenReader.js +0 -0
- /package/src/{agent → agents/providers}/claudeSessionFiles.js +0 -0
- /package/src/{agent → agents/providers}/codexEventTranslator.js +0 -0
- /package/src/{agent → agents/providers}/credentials/claude.js +0 -0
- /package/src/{agent → agents/providers}/credentials/codex.js +0 -0
- /package/src/{agent → agents/providers}/credentials/index.js +0 -0
- /package/src/{chat → app/chat}/agentBar.js +0 -0
- /package/src/{chat → app/chat}/agentDirectory.js +0 -0
- /package/src/{chat → app/chat}/cronScheduler.js +0 -0
- /package/src/{chat → app/chat}/daemonCoordinator.js +0 -0
- /package/src/{chat → app/chat}/daemonReconnect.js +0 -0
- /package/src/{chat → app/chat}/daemonTransport.js +0 -0
- /package/src/{chat → app/chat}/daemonTransportDefaults.js +0 -0
- /package/src/{chat → app/chat}/inputMath.js +0 -0
- /package/src/{chat → app/chat}/projectCloseController.js +0 -0
- /package/src/{chat → app/chat}/rawKeyMap.js +0 -0
- /package/src/{chat → app/chat}/settingsController.js +0 -0
- /package/src/{chat → app/chat}/shellCommand.js +0 -0
- /package/src/{chat → app/chat}/text.js +0 -0
- /package/src/{chat → app/chat}/transientAgentState.js +0 -0
- /package/src/{cli → app/cli}/busCoreCommands.js +0 -0
- /package/src/{skills/index.js → app/cli/features/skills.js} +0 -0
- /package/src/{bus → coordination/bus}/nickname.js +0 -0
- /package/src/{bus → coordination/bus}/queue.js +0 -0
- /package/src/{context → coordination/context}/decisions.js +0 -0
- /package/src/{context → coordination/context}/doctor.js +0 -0
- /package/src/{context → coordination/context}/index.js +0 -0
- /package/src/{context → coordination/context}/sync.js +0 -0
- /package/src/{ufoo → coordination/state}/agentRegistryDiagnostics.js +0 -0
- /package/src/{ufoo → coordination/state}/agentsStore.js +0 -0
- /package/src/{ufoo → coordination/state}/paths.js +0 -0
- /package/src/{controller → orchestration/controller}/launchRouting.js +0 -0
- /package/src/{controller → orchestration/controller}/routerFastPath.js +0 -0
- /package/src/{controller → orchestration/controller}/routerFinalize.js +0 -0
- /package/src/{group → orchestration/groups}/diagram.js +0 -0
- /package/src/{group → orchestration/groups}/templateValidation.js +0 -0
- /package/src/{solo → orchestration/solo}/commands.js +0 -0
- /package/src/{shared → runtime/contracts}/eventContract.js +0 -0
- /package/src/{shared → runtime/contracts}/ptySocketContract.js +0 -0
- /package/src/{providerapi → runtime/privacy}/redactor.js +0 -0
- /package/src/{providerapi → runtime/privacy}/shadowDiff.js +0 -0
- /package/src/{utils → runtime/process}/nodeExecutable.js +0 -0
- /package/src/{projects → runtime/projects}/identity.js +0 -0
- /package/src/{projects → runtime/projects}/index.js +0 -0
- /package/src/{projects → runtime/projects}/projectId.js +0 -0
- /package/src/{projects → runtime/projects}/runtimes.js +0 -0
- /package/src/{terminal → runtime/terminal}/adapterContract.js +0 -0
- /package/src/{terminal → runtime/terminal}/adapters/externalAdapter.js +0 -0
- /package/src/{terminal → runtime/terminal}/adapters/hostAdapter.js +0 -0
- /package/src/{terminal → runtime/terminal}/adapters/internalQueueAdapter.js +0 -0
- /package/src/{terminal → runtime/terminal}/adapters/terminalAdapter.js +0 -0
- /package/src/{terminal → runtime/terminal}/adapters/tmuxAdapter.js +0 -0
- /package/src/{terminal → runtime/terminal}/detect.js +0 -0
- /package/src/{terminal → runtime/terminal}/index.js +0 -0
- /package/src/{terminal → runtime/terminal}/iterm2.js +0 -0
- /package/src/{utils → ui/format}/banner.js +0 -0
- /package/src/{shared → ui/format}/markdownRenderer.js +0 -0
- /package/src/ui/{components → ink}/InkDemo.js +0 -0
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
const { spawn, spawnSync } = require("child_process");
|
|
2
2
|
const fs = require("fs");
|
|
3
3
|
const path = require("path");
|
|
4
|
-
const { loadConfig } = require("
|
|
5
|
-
const { getUfooPaths } = require("
|
|
6
|
-
const { loadAgentsData, saveAgentsData } = require("
|
|
7
|
-
const { isAgentPidAlive, getTtyProcessInfo } = require("
|
|
4
|
+
const { loadConfig } = require("../../config");
|
|
5
|
+
const { getUfooPaths } = require("../../coordination/state/paths");
|
|
6
|
+
const { loadAgentsData, saveAgentsData } = require("../../coordination/state/agentsStore");
|
|
7
|
+
const { isAgentPidAlive, getTtyProcessInfo } = require("../../coordination/bus/utils");
|
|
8
8
|
const { isITerm2 } = require("../terminal/detect");
|
|
9
9
|
const { createTerminalAdapterRouter } = require("../terminal/adapterRouter");
|
|
10
10
|
const {
|
|
@@ -14,13 +14,14 @@ const {
|
|
|
14
14
|
const {
|
|
15
15
|
createSession: createHostSession,
|
|
16
16
|
} = require("../terminal/adapters/hostAdapter");
|
|
17
|
-
const { resolveDefaultManualBootstrap } = require("
|
|
18
|
-
const { detectLaunchEnvironment } = require("
|
|
17
|
+
const { resolveDefaultManualBootstrap } = require("../../agents/prompts/defaultBootstrap");
|
|
18
|
+
const { detectLaunchEnvironment } = require("../../agents/launch/launchEnvironment");
|
|
19
19
|
|
|
20
20
|
function normalizeLaunchAgent(agent = "") {
|
|
21
21
|
const value = String(agent || "").trim().toLowerCase();
|
|
22
22
|
if (value === "codex") return "codex";
|
|
23
23
|
if (value === "claude" || value === "claude-code") return "claude";
|
|
24
|
+
if (value === "agy" || value === "antigravity") return "agy";
|
|
24
25
|
if (value === "ufoo" || value === "ucode" || value === "ufoo-code") return "ufoo";
|
|
25
26
|
return "";
|
|
26
27
|
}
|
|
@@ -28,6 +29,7 @@ function normalizeLaunchAgent(agent = "") {
|
|
|
28
29
|
function toBusAgentType(agent = "") {
|
|
29
30
|
if (agent === "codex") return "codex";
|
|
30
31
|
if (agent === "claude") return "claude-code";
|
|
32
|
+
if (agent === "agy") return "agy";
|
|
31
33
|
if (agent === "ufoo") return "ufoo-code";
|
|
32
34
|
return "";
|
|
33
35
|
}
|
|
@@ -35,6 +37,7 @@ function toBusAgentType(agent = "") {
|
|
|
35
37
|
function toTerminalBinary(agent = "") {
|
|
36
38
|
if (agent === "codex") return "ucodex";
|
|
37
39
|
if (agent === "claude") return "uclaude";
|
|
40
|
+
if (agent === "agy") return "uagy";
|
|
38
41
|
if (agent === "ufoo") return "ucode";
|
|
39
42
|
return "";
|
|
40
43
|
}
|
|
@@ -42,6 +45,7 @@ function toTerminalBinary(agent = "") {
|
|
|
42
45
|
function toTmuxBinary(agent = "") {
|
|
43
46
|
if (agent === "codex") return "ucodex";
|
|
44
47
|
if (agent === "claude") return "uclaude";
|
|
48
|
+
if (agent === "agy") return "uagy";
|
|
45
49
|
if (agent === "ufoo") return "ucode";
|
|
46
50
|
return "";
|
|
47
51
|
}
|
|
@@ -84,7 +88,7 @@ function applyDefaultManagedBootstrap(projectRoot, normalizedAgent, args = [], e
|
|
|
84
88
|
}
|
|
85
89
|
|
|
86
90
|
function resolveUfooRunnerPath() {
|
|
87
|
-
return path.resolve(__dirname, "
|
|
91
|
+
return path.resolve(__dirname, "../../../bin/ufoo.js");
|
|
88
92
|
}
|
|
89
93
|
|
|
90
94
|
function normalizeLaunchScope(value, fallback = "inplace") {
|
|
@@ -165,7 +169,7 @@ function resolveNativeTerminalApp(options = {}) {
|
|
|
165
169
|
|
|
166
170
|
function resolveConfiguredLaunchMode(configuredMode = "", options = {}) {
|
|
167
171
|
const mode = normalizeOptionalString(configuredMode);
|
|
168
|
-
if (mode === "internal" || mode === "
|
|
172
|
+
if (mode === "internal" || mode === "tmux" || mode === "terminal" || mode === "host") {
|
|
169
173
|
return mode;
|
|
170
174
|
}
|
|
171
175
|
// Auto mode: defer to the unified detector. Daemon ops differs from the
|
|
@@ -462,8 +466,8 @@ function buildResumeCommand(projectRoot, agent, sessionId) {
|
|
|
462
466
|
}
|
|
463
467
|
const args = buildResumeArgs(agent, sessionId);
|
|
464
468
|
const argText = args.length > 0 ? ` ${args.map(shellEscape).join(" ")}` : "";
|
|
465
|
-
const
|
|
466
|
-
return `cd ${shellEscape(projectRoot)} && ${
|
|
469
|
+
const skipSessionResolveEnv = "UFOO_SKIP_SESSION_RESOLVE=1 ";
|
|
470
|
+
return `cd ${shellEscape(projectRoot)} && ${skipSessionResolveEnv}${binary}${argText}`;
|
|
467
471
|
}
|
|
468
472
|
|
|
469
473
|
async function tryReuseTerminal(projectRoot, subscriberId, meta, agent, sessionId) {
|
|
@@ -474,7 +478,7 @@ async function tryReuseTerminal(projectRoot, subscriberId, meta, agent, sessionI
|
|
|
474
478
|
const baseCmd = buildResumeCommand(projectRoot, agent, sessionId);
|
|
475
479
|
const command = titleCmd ? `${titleCmd} && ${baseCmd}` : baseCmd;
|
|
476
480
|
try {
|
|
477
|
-
const EventBus = require("
|
|
481
|
+
const EventBus = require("../../coordination/bus");
|
|
478
482
|
const bus = new EventBus(projectRoot);
|
|
479
483
|
bus.ensureBus();
|
|
480
484
|
await bus.inject(subscriberId, command);
|
|
@@ -541,7 +545,6 @@ async function spawnManagedHostAgent(
|
|
|
541
545
|
}
|
|
542
546
|
|
|
543
547
|
const hostContext = resolveHostLaunchContext(hostOptions);
|
|
544
|
-
const requireActivityMonitor = hostContext.requireActivityMonitor === true;
|
|
545
548
|
if (!hostContext.hostDaemonSock) {
|
|
546
549
|
throw new Error("host launch requires UFOO_HOST_DAEMON_SOCK");
|
|
547
550
|
}
|
|
@@ -555,7 +558,7 @@ async function spawnManagedHostAgent(
|
|
|
555
558
|
|
|
556
559
|
// Pre-register subscriber on the bus so waitForNewSubscriber resolves immediately
|
|
557
560
|
const crypto = require("crypto");
|
|
558
|
-
const EventBus = require("
|
|
561
|
+
const EventBus = require("../../coordination/bus");
|
|
559
562
|
const existing = listSubscribers(projectRoot, agentType);
|
|
560
563
|
let subscriberId = "";
|
|
561
564
|
let preRegistrationError = null;
|
|
@@ -584,15 +587,11 @@ async function spawnManagedHostAgent(
|
|
|
584
587
|
const argText = args.length > 0 ? ` ${args.map(shellEscape).join(" ")}` : "";
|
|
585
588
|
|
|
586
589
|
const titleCmd = buildTitleCmd(nickname);
|
|
587
|
-
const hasPreRegisteredSubscriber = !!subscriberId;
|
|
588
590
|
|
|
589
591
|
// Pass env vars to Horizon via the env parameter (Horizon will set them for the child process)
|
|
590
592
|
const env = {
|
|
591
593
|
UFOO_LAUNCH_MODE: "host",
|
|
592
594
|
};
|
|
593
|
-
if (requireActivityMonitor) {
|
|
594
|
-
env.UFOO_FORCE_PTY = "1";
|
|
595
|
-
}
|
|
596
595
|
if (subscriberId) {
|
|
597
596
|
env.UFOO_SUBSCRIBER_ID = subscriberId;
|
|
598
597
|
}
|
|
@@ -608,32 +607,18 @@ async function spawnManagedHostAgent(
|
|
|
608
607
|
}
|
|
609
608
|
}
|
|
610
609
|
|
|
611
|
-
|
|
612
|
-
|
|
613
|
-
|
|
614
|
-
|
|
615
|
-
|
|
616
|
-
|
|
617
|
-
runCmd = titleCmd
|
|
618
|
-
? `cd ${shellEscape(projectRoot)} && ${titleCmd} && ${launchCmd}`
|
|
619
|
-
: `cd ${shellEscape(projectRoot)} && ${launchCmd}`;
|
|
620
|
-
// Force PTY wrapper so ReadyDetector + ActivityDetector work for activity_state monitoring.
|
|
621
|
-
// Horizon sets UFOO_DISABLE_PTY=1 unconditionally; UFOO_FORCE_PTY=1 takes priority over it.
|
|
622
|
-
env.UFOO_FORCE_PTY = "1";
|
|
623
|
-
} else {
|
|
624
|
-
if (preRegistrationError) {
|
|
625
|
-
console.error(
|
|
626
|
-
`[host-launch] pre-registration failed for ${nickname || agentType}: ${preRegistrationError.message || String(preRegistrationError)}`
|
|
627
|
-
);
|
|
628
|
-
}
|
|
629
|
-
// Fallback launch still goes through the regular agent launcher binary.
|
|
630
|
-
// For group/bootstrap-monitored flows we also force the PTY wrapper so
|
|
631
|
-
// activity_state can progress out of "starting" after self-registration.
|
|
632
|
-
const directCmd = `${binary}${argText}`;
|
|
633
|
-
runCmd = titleCmd
|
|
634
|
-
? `cd ${shellEscape(projectRoot)} && ${titleCmd} && ${directCmd}`
|
|
635
|
-
: `cd ${shellEscape(projectRoot)} && ${directCmd}`;
|
|
610
|
+
// Launch agent binary directly; launcher.js creates inject.sock and
|
|
611
|
+
// handles activity_state monitoring internally via its own PTY wrapper.
|
|
612
|
+
if (preRegistrationError) {
|
|
613
|
+
console.error(
|
|
614
|
+
`[host-launch] pre-registration failed for ${nickname || agentType}: ${preRegistrationError.message || String(preRegistrationError)}`
|
|
615
|
+
);
|
|
636
616
|
}
|
|
617
|
+
env.UFOO_FORCE_PTY = "1";
|
|
618
|
+
const directCmd = `${binary}${argText}`;
|
|
619
|
+
const runCmd = titleCmd
|
|
620
|
+
? `cd ${shellEscape(projectRoot)} && ${titleCmd} && ${directCmd}`
|
|
621
|
+
: `cd ${shellEscape(projectRoot)} && ${directCmd}`;
|
|
637
622
|
createOptions.command = runCmd;
|
|
638
623
|
createOptions.env = env;
|
|
639
624
|
|
|
@@ -671,7 +656,7 @@ async function spawnInternalAgent(
|
|
|
671
656
|
fs.mkdirSync(logDir, { recursive: true });
|
|
672
657
|
|
|
673
658
|
const crypto = require("crypto");
|
|
674
|
-
const EventBus = require("
|
|
659
|
+
const EventBus = require("../../coordination/bus");
|
|
675
660
|
const children = [];
|
|
676
661
|
const subscriberIds = [];
|
|
677
662
|
|
|
@@ -707,10 +692,7 @@ async function spawnInternalAgent(
|
|
|
707
692
|
? (count > 1 ? `${nickname}-${i + 1}` : nickname)
|
|
708
693
|
: "";
|
|
709
694
|
const providerSessionId = typeof options.providerSessionId === "string" ? options.providerSessionId.trim() : "";
|
|
710
|
-
const
|
|
711
|
-
? options.usePty
|
|
712
|
-
: process.env.UFOO_INTERNAL_PTY !== "0";
|
|
713
|
-
const launchMode = usePty ? "internal-pty" : "internal";
|
|
695
|
+
const launchMode = "internal";
|
|
714
696
|
|
|
715
697
|
// 传递 launch_mode 和 parent PID 到 join
|
|
716
698
|
const joinResult = await bus.subscriberManager.join(sessionId, agentType, requestedNickname, {
|
|
@@ -722,10 +704,9 @@ async function spawnInternalAgent(
|
|
|
722
704
|
bus.saveBusData();
|
|
723
705
|
|
|
724
706
|
const managedBootstrap = applyDefaultManagedBootstrap(projectRoot, normalizedAgent, extraArgs, extraEnv);
|
|
725
|
-
const runnerCmd =
|
|
707
|
+
const runnerCmd = "agent-runner";
|
|
726
708
|
const args = managedBootstrap.args;
|
|
727
709
|
const child = spawn(process.execPath, [runner, runnerCmd, agent, ...args], {
|
|
728
|
-
// 关键改动:不使用 detached,daemon 作为父进程
|
|
729
710
|
detached: false,
|
|
730
711
|
stdio: ["ignore", errLog, errLog],
|
|
731
712
|
cwd: projectRoot,
|
|
@@ -733,17 +714,16 @@ async function spawnInternalAgent(
|
|
|
733
714
|
...process.env,
|
|
734
715
|
...(managedBootstrap.extraEnv && typeof managedBootstrap.extraEnv === "object" ? managedBootstrap.extraEnv : {}),
|
|
735
716
|
UFOO_INTERNAL_AGENT: "1",
|
|
736
|
-
|
|
737
|
-
UFOO_SUBSCRIBER_ID: subscriberId, // 直接传递 subscriber ID
|
|
717
|
+
UFOO_SUBSCRIBER_ID: subscriberId,
|
|
738
718
|
UFOO_NICKNAME: finalNickname,
|
|
739
|
-
UFOO_LAUNCH_MODE:
|
|
719
|
+
UFOO_LAUNCH_MODE: "internal",
|
|
740
720
|
UFOO_PARENT_PID: String(originalPid),
|
|
741
721
|
...(providerSessionId ? { UFOO_PROVIDER_SESSION_ID: providerSessionId } : {}),
|
|
742
722
|
},
|
|
743
723
|
});
|
|
744
724
|
|
|
745
725
|
// Update bus data with the actual child PID so isMetaActive
|
|
746
|
-
// can detect when the
|
|
726
|
+
// can detect when the runner process dies.
|
|
747
727
|
try {
|
|
748
728
|
bus.loadBusData();
|
|
749
729
|
if (bus.busData.agents && bus.busData.agents[subscriberId]) {
|
|
@@ -953,8 +933,7 @@ async function launchAgent(projectRoot, agent, count = 1, nickname = "", process
|
|
|
953
933
|
throw new Error(`unsupported agent type: ${agent}`);
|
|
954
934
|
}
|
|
955
935
|
|
|
956
|
-
if (mode === "internal"
|
|
957
|
-
const usePty = mode === "internal-pty";
|
|
936
|
+
if (mode === "internal") {
|
|
958
937
|
const result = await spawnInternalAgent(
|
|
959
938
|
projectRoot,
|
|
960
939
|
normalizedAgent,
|
|
@@ -963,7 +942,7 @@ async function launchAgent(projectRoot, agent, count = 1, nickname = "", process
|
|
|
963
942
|
processManager,
|
|
964
943
|
launchEnvObject,
|
|
965
944
|
extraArgs,
|
|
966
|
-
{
|
|
945
|
+
{}
|
|
967
946
|
);
|
|
968
947
|
return { mode, launchScope, subscriberIds: result.subscriberIds };
|
|
969
948
|
}
|
|
@@ -1100,6 +1079,9 @@ function buildResumeArgs(agent, sessionId) {
|
|
|
1100
1079
|
if (!sessionId) return [];
|
|
1101
1080
|
if (agent === "codex") return ["resume", sessionId];
|
|
1102
1081
|
if (agent === "claude") return ["--session-id", sessionId];
|
|
1082
|
+
// Agy resumes by conversation UUID; bin/uagy.js de-duplicates if the same
|
|
1083
|
+
// flag is already injected via provider_session_id readback.
|
|
1084
|
+
if (agent === "agy") return [`--conversation=${sessionId}`];
|
|
1103
1085
|
return [];
|
|
1104
1086
|
}
|
|
1105
1087
|
|
|
@@ -1152,7 +1134,7 @@ function collectRecoverableAgents(projectRoot, target = "") {
|
|
|
1152
1134
|
continue;
|
|
1153
1135
|
}
|
|
1154
1136
|
const agent = normalizeAgentType(meta.agent_type);
|
|
1155
|
-
if (agent !== "codex" && agent !== "claude") {
|
|
1137
|
+
if (agent !== "codex" && agent !== "claude" && agent !== "agy") {
|
|
1156
1138
|
skipped.push({ id, reason: "unsupported agent type" });
|
|
1157
1139
|
continue;
|
|
1158
1140
|
}
|
|
@@ -1196,7 +1178,7 @@ async function resumeAgents(projectRoot, target = "", processManager = null) {
|
|
|
1196
1178
|
const args = buildResumeArgs(item.agent, sessionId);
|
|
1197
1179
|
let reused = false;
|
|
1198
1180
|
let resumedId = item.id;
|
|
1199
|
-
if (mode === "internal"
|
|
1181
|
+
if (mode === "internal") {
|
|
1200
1182
|
// Internal agents have no terminal/pane to reattach. Start a fresh
|
|
1201
1183
|
// daemon-managed runner and replace the old recoverable registration.
|
|
1202
1184
|
// The provider session is still reused via the normal provider args.
|
|
@@ -1207,9 +1189,9 @@ async function resumeAgents(projectRoot, target = "", processManager = null) {
|
|
|
1207
1189
|
1,
|
|
1208
1190
|
nickname,
|
|
1209
1191
|
processManager,
|
|
1210
|
-
{
|
|
1192
|
+
{ UFOO_SKIP_SESSION_RESOLVE: "1" },
|
|
1211
1193
|
args,
|
|
1212
|
-
{ replaceAgentId: item.id, providerSessionId: sessionId
|
|
1194
|
+
{ replaceAgentId: item.id, providerSessionId: sessionId }
|
|
1213
1195
|
);
|
|
1214
1196
|
resumedId = launchResult.subscriberIds && launchResult.subscriberIds[0]
|
|
1215
1197
|
? launchResult.subscriberIds[0]
|
|
@@ -1217,7 +1199,7 @@ async function resumeAgents(projectRoot, target = "", processManager = null) {
|
|
|
1217
1199
|
} else {
|
|
1218
1200
|
reused = await tryReuseTerminal(projectRoot, item.id, item.meta, item.agent, sessionId);
|
|
1219
1201
|
if (!reused) {
|
|
1220
|
-
const envPrefix = "
|
|
1202
|
+
const envPrefix = "UFOO_SKIP_SESSION_RESOLVE=1";
|
|
1221
1203
|
if (mode === "tmux") {
|
|
1222
1204
|
// eslint-disable-next-line no-await-in-loop
|
|
1223
1205
|
await spawnTmuxWindow(projectRoot, item.agent, nickname, args, envPrefix);
|
|
@@ -1334,5 +1316,10 @@ module.exports = {
|
|
|
1334
1316
|
resolveConfiguredLaunchMode,
|
|
1335
1317
|
resolveHostLaunchContext,
|
|
1336
1318
|
resolveNativeTerminalApp,
|
|
1319
|
+
normalizeLaunchAgent,
|
|
1320
|
+
toBusAgentType,
|
|
1321
|
+
toTerminalBinary,
|
|
1322
|
+
toTmuxBinary,
|
|
1323
|
+
buildResumeArgs,
|
|
1337
1324
|
},
|
|
1338
1325
|
};
|
|
@@ -1,34 +1,34 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
|
|
3
|
-
const { IPC_RESPONSE_TYPES } = require("../
|
|
3
|
+
const { IPC_RESPONSE_TYPES } = require("../contracts/eventContract");
|
|
4
4
|
const {
|
|
5
5
|
listControllerInboxEntries,
|
|
6
6
|
consumeControllerInboxEntries,
|
|
7
|
-
} = require("
|
|
7
|
+
} = require("../../coordination/report/store");
|
|
8
8
|
const { isGlobalControllerProjectRoot } = require("../projects");
|
|
9
9
|
const {
|
|
10
10
|
resolveGateRouterConfig,
|
|
11
11
|
shouldUseGateRouter,
|
|
12
|
-
} = require("
|
|
12
|
+
} = require("../../orchestration/controller/gateRouter");
|
|
13
13
|
const {
|
|
14
14
|
CONTROLLER_MODES,
|
|
15
15
|
applyControllerModeForMessage,
|
|
16
16
|
resolveControllerMode,
|
|
17
|
-
} = require("
|
|
17
|
+
} = require("../../orchestration/controller/flags");
|
|
18
18
|
const {
|
|
19
19
|
resolveLoopRuntimeOptions,
|
|
20
20
|
runPromptWithControllerLoop,
|
|
21
|
-
} = require("
|
|
21
|
+
} = require("../../agents/controller/loopRuntime");
|
|
22
22
|
const {
|
|
23
23
|
appendShadowDiff,
|
|
24
24
|
createLoopObserver,
|
|
25
|
-
} = require("
|
|
25
|
+
} = require("../../agents/controller/loopObservability");
|
|
26
26
|
const {
|
|
27
27
|
DEFAULT_SHADOW_SAMPLING_RATE,
|
|
28
28
|
createShadowBudgetBreaker,
|
|
29
29
|
createShadowGuard,
|
|
30
30
|
shouldSampleShadow,
|
|
31
|
-
} = require("
|
|
31
|
+
} = require("../../orchestration/controller/shadowGuard");
|
|
32
32
|
|
|
33
33
|
function normalizeProjectRoute(route) {
|
|
34
34
|
if (!route || typeof route !== "object") return null;
|
|
@@ -0,0 +1,230 @@
|
|
|
1
|
+
const fs = require("fs");
|
|
2
|
+
const os = require("os");
|
|
3
|
+
const path = require("path");
|
|
4
|
+
const { loadAgentsData, saveAgentsData } = require("../../coordination/state/agentsStore");
|
|
5
|
+
const { getUfooPaths } = require("../../coordination/state/paths");
|
|
6
|
+
|
|
7
|
+
function persistProviderSession(projectRoot, subscriberId, payload) {
|
|
8
|
+
const filePath = getUfooPaths(projectRoot).agentsFile;
|
|
9
|
+
const data = loadAgentsData(filePath);
|
|
10
|
+
const meta = data.agents[subscriberId] || {};
|
|
11
|
+
data.agents[subscriberId] = {
|
|
12
|
+
...meta,
|
|
13
|
+
provider_session_id: payload.sessionId || "",
|
|
14
|
+
provider_session_source: payload.source || "",
|
|
15
|
+
provider_session_updated_at: new Date().toISOString(),
|
|
16
|
+
};
|
|
17
|
+
saveAgentsData(filePath, data);
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
function loadProviderSessionCache(projectRoot) {
|
|
21
|
+
const filePath = getUfooPaths(projectRoot).agentsFile;
|
|
22
|
+
const data = loadAgentsData(filePath);
|
|
23
|
+
const cache = new Map();
|
|
24
|
+
for (const [id, meta] of Object.entries(data.agents || {})) {
|
|
25
|
+
if (meta && meta.provider_session_id) {
|
|
26
|
+
cache.set(id, {
|
|
27
|
+
sessionId: meta.provider_session_id,
|
|
28
|
+
source: meta.provider_session_source || "",
|
|
29
|
+
updated_at: meta.provider_session_updated_at || "",
|
|
30
|
+
});
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
return cache;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
/**
|
|
37
|
+
* Resolve Claude Code session ID directly from session file.
|
|
38
|
+
* Claude writes ~/.claude/sessions/<pid>.json with { sessionId, pid, cwd, ... }
|
|
39
|
+
*/
|
|
40
|
+
function resolveClaudeSessionFromFile(pid) {
|
|
41
|
+
if (!pid) return null;
|
|
42
|
+
const filePath = path.join(os.homedir(), ".claude", "sessions", `${pid}.json`);
|
|
43
|
+
try {
|
|
44
|
+
if (!fs.existsSync(filePath)) return null;
|
|
45
|
+
const data = JSON.parse(fs.readFileSync(filePath, "utf8"));
|
|
46
|
+
const sessionId = data.sessionId || data.session_id || "";
|
|
47
|
+
if (!sessionId) return null;
|
|
48
|
+
return { sessionId, source: filePath };
|
|
49
|
+
} catch {
|
|
50
|
+
return null;
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
/**
|
|
55
|
+
* Resolve Codex session ID from session rollout files.
|
|
56
|
+
* Codex writes ~/.codex/sessions/YYYY/MM/DD/rollout-<ts>-<id>.jsonl
|
|
57
|
+
* First line contains { type: "session_meta", payload: { id, cwd, ... } }
|
|
58
|
+
*/
|
|
59
|
+
function resolveCodexSessionFromFile(cwd) {
|
|
60
|
+
if (!cwd) return null;
|
|
61
|
+
try {
|
|
62
|
+
const now = new Date();
|
|
63
|
+
// Check today and yesterday (session may have started before midnight)
|
|
64
|
+
const dates = [now];
|
|
65
|
+
const yesterday = new Date(now);
|
|
66
|
+
yesterday.setDate(yesterday.getDate() - 1);
|
|
67
|
+
dates.push(yesterday);
|
|
68
|
+
|
|
69
|
+
let bestMatch = null;
|
|
70
|
+
let bestMtime = 0;
|
|
71
|
+
|
|
72
|
+
for (const d of dates) {
|
|
73
|
+
const yyyy = String(d.getFullYear());
|
|
74
|
+
const mm = String(d.getMonth() + 1).padStart(2, "0");
|
|
75
|
+
const dd = String(d.getDate()).padStart(2, "0");
|
|
76
|
+
const dir = path.join(os.homedir(), ".codex", "sessions", yyyy, mm, dd);
|
|
77
|
+
if (!fs.existsSync(dir)) continue;
|
|
78
|
+
|
|
79
|
+
const files = fs.readdirSync(dir)
|
|
80
|
+
.filter((f) => f.startsWith("rollout-") && f.endsWith(".jsonl"));
|
|
81
|
+
|
|
82
|
+
for (const file of files) {
|
|
83
|
+
const filePath = path.join(dir, file);
|
|
84
|
+
try {
|
|
85
|
+
const stat = fs.statSync(filePath);
|
|
86
|
+
if (stat.mtimeMs <= bestMtime) continue;
|
|
87
|
+
|
|
88
|
+
// Read first line for session_meta
|
|
89
|
+
const fd = fs.openSync(filePath, "r");
|
|
90
|
+
const buf = Buffer.alloc(4096);
|
|
91
|
+
const bytesRead = fs.readSync(fd, buf, 0, 4096, 0);
|
|
92
|
+
fs.closeSync(fd);
|
|
93
|
+
const firstLine = buf.toString("utf8", 0, bytesRead).split("\n")[0];
|
|
94
|
+
if (!firstLine) continue;
|
|
95
|
+
|
|
96
|
+
const record = JSON.parse(firstLine);
|
|
97
|
+
const payload = record.payload || record;
|
|
98
|
+
const sessionCwd = payload.cwd || "";
|
|
99
|
+
const sessionId = payload.id || "";
|
|
100
|
+
|
|
101
|
+
if (sessionId && sessionCwd === cwd && stat.mtimeMs > bestMtime) {
|
|
102
|
+
bestMatch = { sessionId, source: filePath };
|
|
103
|
+
bestMtime = stat.mtimeMs;
|
|
104
|
+
}
|
|
105
|
+
} catch {
|
|
106
|
+
continue;
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
return bestMatch;
|
|
111
|
+
} catch {
|
|
112
|
+
return null;
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
/**
|
|
117
|
+
* Resolve provider session ID directly from session files.
|
|
118
|
+
* @param {string} agentType - "claude-code" or "codex"
|
|
119
|
+
* @param {object} opts - { pid, cwd }
|
|
120
|
+
*/
|
|
121
|
+
function resolveSessionFromFile(agentType, opts = {}) {
|
|
122
|
+
if (agentType === "claude-code") {
|
|
123
|
+
return resolveClaudeSessionFromFile(opts.pid);
|
|
124
|
+
}
|
|
125
|
+
if (agentType === "codex") {
|
|
126
|
+
return resolveCodexSessionFromFile(opts.cwd);
|
|
127
|
+
}
|
|
128
|
+
return null;
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
/**
|
|
132
|
+
* Retry reading session file (agent may not have written it yet)
|
|
133
|
+
*/
|
|
134
|
+
async function resolveSessionFromFileWithRetries(agentType, opts = {}, attempts = 10, intervalMs = 1000) {
|
|
135
|
+
for (let i = 0; i < attempts; i += 1) {
|
|
136
|
+
const resolved = resolveSessionFromFile(agentType, opts);
|
|
137
|
+
if (resolved && resolved.sessionId) return resolved;
|
|
138
|
+
// eslint-disable-next-line no-await-in-loop
|
|
139
|
+
await new Promise((r) => setTimeout(r, intervalMs));
|
|
140
|
+
}
|
|
141
|
+
return null;
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
/**
|
|
145
|
+
* Schedule provider session resolution.
|
|
146
|
+
* Uses provider session files only. This intentionally avoids injecting
|
|
147
|
+
* `/ufoo <nickname>` / `$ufoo <nickname>` into agent terminals.
|
|
148
|
+
*
|
|
149
|
+
* @param {Object} options
|
|
150
|
+
* @param {string} options.projectRoot - Project root directory
|
|
151
|
+
* @param {string} options.subscriberId - Subscriber ID (e.g., "claude-code:abc123")
|
|
152
|
+
* @param {string} options.agentType - Agent type ("claude-code" or "codex")
|
|
153
|
+
* @param {number} options.agentPid - Agent child process PID (for claude-code)
|
|
154
|
+
* @param {string} options.agentCwd - Agent working directory (for codex)
|
|
155
|
+
* @param {number} options.delayMs - Delay before starting resolution
|
|
156
|
+
* @param {number} options.fileAttempts - File read retry attempts
|
|
157
|
+
* @param {number} options.fileIntervalMs - File read retry interval
|
|
158
|
+
* @param {Function} options.onResolved - Callback when session ID is found
|
|
159
|
+
*/
|
|
160
|
+
function scheduleProviderSessionResolve({
|
|
161
|
+
projectRoot,
|
|
162
|
+
subscriberId,
|
|
163
|
+
agentType,
|
|
164
|
+
agentPid = 0,
|
|
165
|
+
agentCwd = "",
|
|
166
|
+
delayMs = 3000,
|
|
167
|
+
fileAttempts = 10,
|
|
168
|
+
fileIntervalMs = 1000,
|
|
169
|
+
onResolved = null,
|
|
170
|
+
}) {
|
|
171
|
+
if (!subscriberId || !agentType) return null;
|
|
172
|
+
if (agentType !== "codex" && agentType !== "claude-code") return null;
|
|
173
|
+
|
|
174
|
+
let executed = false;
|
|
175
|
+
let cancelled = false;
|
|
176
|
+
let timer = null;
|
|
177
|
+
|
|
178
|
+
const execute = async () => {
|
|
179
|
+
if (executed || cancelled) return;
|
|
180
|
+
executed = true;
|
|
181
|
+
if (timer) {
|
|
182
|
+
clearTimeout(timer);
|
|
183
|
+
timer = null;
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
// 1. Try direct file read (fast, non-invasive)
|
|
187
|
+
const fileOpts = { pid: agentPid, cwd: agentCwd || projectRoot };
|
|
188
|
+
const fileResolved = await resolveSessionFromFileWithRetries(
|
|
189
|
+
agentType, fileOpts, fileAttempts, fileIntervalMs,
|
|
190
|
+
);
|
|
191
|
+
if (cancelled) return;
|
|
192
|
+
if (fileResolved && fileResolved.sessionId) {
|
|
193
|
+
persistProviderSession(projectRoot, subscriberId, fileResolved);
|
|
194
|
+
if (typeof onResolved === "function") {
|
|
195
|
+
onResolved(subscriberId, fileResolved);
|
|
196
|
+
}
|
|
197
|
+
return;
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
// No terminal injection fallback. Session IDs are resolved from provider files only.
|
|
201
|
+
};
|
|
202
|
+
|
|
203
|
+
// Schedule delayed execution
|
|
204
|
+
timer = setTimeout(execute, delayMs);
|
|
205
|
+
|
|
206
|
+
// Return handle for early trigger or cancellation
|
|
207
|
+
return {
|
|
208
|
+
subscriberId,
|
|
209
|
+
triggerNow: execute,
|
|
210
|
+
cancel: () => {
|
|
211
|
+
cancelled = true;
|
|
212
|
+
executed = true;
|
|
213
|
+
if (timer) {
|
|
214
|
+
clearTimeout(timer);
|
|
215
|
+
timer = null;
|
|
216
|
+
}
|
|
217
|
+
},
|
|
218
|
+
};
|
|
219
|
+
}
|
|
220
|
+
|
|
221
|
+
module.exports = {
|
|
222
|
+
scheduleProviderSessionResolve,
|
|
223
|
+
resolveSessionFromFile,
|
|
224
|
+
persistProviderSession,
|
|
225
|
+
loadProviderSessionCache,
|
|
226
|
+
__private: {
|
|
227
|
+
resolveClaudeSessionFromFile,
|
|
228
|
+
resolveCodexSessionFromFile,
|
|
229
|
+
},
|
|
230
|
+
};
|
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
const fs = require("fs");
|
|
2
|
-
const EventBus = require("
|
|
3
|
-
const { BUS_STATUS_PHASES } = require("../
|
|
2
|
+
const EventBus = require("../../coordination/bus");
|
|
3
|
+
const { BUS_STATUS_PHASES } = require("../contracts/eventContract");
|
|
4
4
|
const {
|
|
5
5
|
REPORT_PHASES,
|
|
6
6
|
normalizeReportInput,
|
|
7
7
|
appendReport,
|
|
8
8
|
updateReportState,
|
|
9
9
|
appendControllerInboxEntry,
|
|
10
|
-
} = require("
|
|
11
|
-
const { getUfooPaths } = require("
|
|
10
|
+
} = require("../../coordination/report/store");
|
|
11
|
+
const { getUfooPaths } = require("../../coordination/state/paths");
|
|
12
12
|
const { resolveDisplayNickname } = require("./nicknameScope");
|
|
13
13
|
|
|
14
14
|
function resolveAgentDisplayName(projectRoot, agentId) {
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
const path = require("path");
|
|
2
2
|
const { startDaemon, stopDaemon, isRunning } = require("./index");
|
|
3
|
-
const { loadConfig, defaultAgentModelForProvider } = require("
|
|
4
|
-
const { resolveNodeExecutable } = require("../
|
|
3
|
+
const { loadConfig, defaultAgentModelForProvider } = require("../../config");
|
|
4
|
+
const { resolveNodeExecutable } = require("../process/nodeExecutable");
|
|
5
5
|
|
|
6
6
|
function runDaemonCli(argv) {
|
|
7
7
|
const cmd = argv[1] || "start";
|
|
@@ -20,7 +20,7 @@ function runDaemonCli(argv) {
|
|
|
20
20
|
if (isRunning(projectRoot)) return;
|
|
21
21
|
if (!process.env.UFOO_DAEMON_CHILD) {
|
|
22
22
|
const { spawn } = require("child_process");
|
|
23
|
-
const child = spawn(resolveNodeExecutable(), [path.join(__dirname, "..", "..", "bin", "ufoo.js"), "daemon", "start"], {
|
|
23
|
+
const child = spawn(resolveNodeExecutable(), [path.join(__dirname, "..", "..", "..", "bin", "ufoo.js"), "daemon", "start"], {
|
|
24
24
|
detached: true,
|
|
25
25
|
stdio: "ignore",
|
|
26
26
|
env: { ...process.env, UFOO_DAEMON_CHILD: "1" },
|
|
@@ -57,7 +57,7 @@ function runDaemonCli(argv) {
|
|
|
57
57
|
if (!process.env.UFOO_DAEMON_CHILD) {
|
|
58
58
|
const { spawn } = require("child_process");
|
|
59
59
|
const childEnv = { ...process.env, UFOO_DAEMON_CHILD: "1" };
|
|
60
|
-
const child = spawn(resolveNodeExecutable(), [path.join(__dirname, "..", "..", "bin", "ufoo.js"), "daemon", "start"], {
|
|
60
|
+
const child = spawn(resolveNodeExecutable(), [path.join(__dirname, "..", "..", "..", "bin", "ufoo.js"), "daemon", "start"], {
|
|
61
61
|
detached: true,
|
|
62
62
|
stdio: "ignore",
|
|
63
63
|
env: childEnv,
|
|
@@ -1,24 +1,24 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
|
|
3
3
|
const path = require("path");
|
|
4
|
-
const EventBus = require("
|
|
5
|
-
const { prepareUcodeBootstrap } = require("
|
|
6
|
-
const { isMetaActive } = require("
|
|
7
|
-
const { getUfooPaths } = require("
|
|
4
|
+
const EventBus = require("../../coordination/bus");
|
|
5
|
+
const { prepareUcodeBootstrap } = require("../../code/launcher/ucodeBootstrap");
|
|
6
|
+
const { isMetaActive } = require("../../coordination/bus/utils");
|
|
7
|
+
const { getUfooPaths } = require("../../coordination/state/paths");
|
|
8
8
|
const {
|
|
9
9
|
applyProjectNicknamePrefix,
|
|
10
10
|
resolveDisplayNickname,
|
|
11
11
|
resolveScopedNickname,
|
|
12
12
|
} = require("./nicknameScope");
|
|
13
|
-
const { loadAgentsData, saveAgentsData } = require("
|
|
13
|
+
const { loadAgentsData, saveAgentsData } = require("../../coordination/state/agentsStore");
|
|
14
14
|
const {
|
|
15
15
|
loadPromptProfileRegistry,
|
|
16
16
|
resolvePromptProfileReference,
|
|
17
|
-
} = require("
|
|
17
|
+
} = require("../../orchestration/groups/promptProfiles");
|
|
18
18
|
const {
|
|
19
19
|
buildSoloPromptMetadata,
|
|
20
20
|
composeSoloBootstrapPrompt,
|
|
21
|
-
} = require("
|
|
21
|
+
} = require("../../orchestration/groups/bootstrap");
|
|
22
22
|
|
|
23
23
|
function sleep(ms) {
|
|
24
24
|
return new Promise((resolve) => setTimeout(resolve, ms));
|