@zq-silk/yui 0.15.6 → 0.15.8
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/ARCHITECTURE.md +192 -399
- package/README.md +127 -1149
- package/dist/agent/adapterCatalog.js +15 -2
- package/dist/agent/agent.js +23 -3
- package/dist/agent/argumentPolicy.js +7 -1
- package/dist/agent/connectionPlan.js +62 -0
- package/dist/agent/executionComponents.js +158 -0
- package/dist/agent/launchEnvironment.js +31 -3
- package/dist/agent/managedRuntimeEnvironment.js +3 -5
- package/dist/{turn/turn.js → agentRun/agentRun.js} +166 -109
- package/dist/{turn/turnIdentity.js → agentRun/runIdentity.js} +4 -4
- package/dist/brief/taskBrief.js +12 -0
- package/dist/cli/agentConfigurationPicker.js +13 -0
- package/dist/cli/commandCatalog.js +167 -70
- package/dist/cli/interactionCandidates.js +5 -5
- package/dist/cli/interactionPolicy.js +38 -8
- package/dist/cli/invocationRouter.js +1 -1
- package/dist/cli/managedDiagnostics.js +28 -0
- package/dist/cli/operatorWizard.js +1 -7
- package/dist/cli/roleOptionOrder.js +27 -0
- package/dist/cli/roleWizard.js +50 -14
- package/dist/cli/updateOrchestrator.js +1 -1
- package/dist/cli/updatePorts.js +3 -4
- package/dist/cli.js +188 -95
- package/dist/commands/agentCommands.js +72 -14
- package/dist/commands/capabilityCommands.js +57 -0
- package/dist/commands/configCommands.js +20 -20
- package/dist/commands/deliveryGuardPreflight.js +2 -2
- package/dist/commands/executionAuditCommands.js +24 -24
- package/dist/commands/globalRoleCommands.js +1 -1
- package/dist/commands/grantCommands.js +4 -4
- package/dist/commands/operatorCommands.js +1 -7
- package/dist/commands/projectCommands.js +4 -4
- package/dist/commands/resourcesCommands.js +2 -2
- package/dist/commands/roleConfiguration.js +25 -5
- package/dist/commands/roleRuntimeGuard.js +4 -5
- package/dist/commands/sessionCommands.js +3 -7
- package/dist/commands/taskActivationCommands.js +259 -0
- package/dist/commands/taskActor.js +28 -49
- package/dist/commands/taskCommands.js +1216 -730
- package/dist/commands/taskContextCommand.js +39 -583
- package/dist/commands/taskExecutionCommands.js +32 -32
- package/dist/commands/taskInputCommands.js +40 -104
- package/dist/commands/taskIntegrationCommands.js +3 -2
- package/dist/commands/taskIntegrationQueueCommands.js +1 -1
- package/dist/commands/taskNextActionCommand.js +8 -8
- package/dist/commands/taskOverviewCommand.js +33 -45
- package/dist/commands/taskRemoteDeliveryCommand.js +2 -2
- package/dist/commands/taskRoleRuntimeStatus.js +133 -102
- package/dist/commands/telemetryCommands.js +36 -38
- package/dist/config/configCatalog.js +4 -4
- package/dist/config/yuiConfig.js +8 -8
- package/dist/context/contextSnapshot.js +10 -10
- package/dist/context/dispatchContext.js +11 -11
- package/dist/context/roleSessionContext.js +6 -3
- package/dist/context/{turnContextPack.js → runContextPack.js} +146 -81
- package/dist/context/{turnInputContract.js → runInputContract.js} +73 -60
- package/dist/context/sessionBootstrapManifest.js +21 -2
- package/dist/context/sourceRunContext.js +30 -0
- package/dist/context/taskContext.js +458 -0
- package/dist/context/wakeNotification.js +27 -27
- package/dist/controller/agentRuntimeObserver.js +21 -24
- package/dist/controller/capabilityBridge.js +77 -0
- package/dist/controller/clientRuntime.js +65 -92
- package/dist/controller/controller.js +127 -188
- package/dist/controller/fileSchedulerStoreAdapter.js +787 -887
- package/dist/controller/jobControl.js +54 -85
- package/dist/controller/resourceInventory.js +8 -27
- package/dist/controller/resourceInventoryLinux.js +12 -13
- package/dist/controller/runtime.js +530 -476
- package/dist/controller/runtimeEventInbox.js +55 -25
- package/dist/controller/runtimeEventProcessor.js +22 -31
- package/dist/controller/{runtimeHookTurnFence.js → runtimeHookRunFence.js} +91 -115
- package/dist/controller/runtimeLaunchCoordinator.js +80 -426
- package/dist/controller/runtimeObservationHook.js +14 -18
- package/dist/controller/sessionNotify.js +16 -24
- package/dist/controller/sessionOwnerReconciliation.js +168 -50
- package/dist/controller/structuredProviderObservation.js +138 -99
- package/dist/coordination/workMailbox.js +3 -3
- package/dist/coordination/workMailboxQueue.js +36 -33
- package/dist/core/boundedRpc.js +8 -1
- package/dist/core/controllerClient.js +20 -1
- package/dist/core/controllerServer.js +4 -4
- package/dist/doctor/doctor.js +13 -2
- package/dist/domain/agentResultTransport.js +9 -9
- package/dist/execution/codexThreadNaming.js +2 -8
- package/dist/execution/executionHealth.js +51 -63
- package/dist/execution/reviewMainRun.js +137 -0
- package/dist/execution/workItemExecution.js +28 -29
- package/dist/execution/workItemExecutionProjection.js +99 -107
- package/dist/execution/workItemMainRun.js +141 -0
- package/dist/executor/agentAdapter.js +227 -20
- package/dist/executor/agentConfigurationCatalog.js +126 -4
- package/dist/executor/agentConfigurationProbe.js +162 -4
- package/dist/executor/agentExecutor.js +79 -78
- package/dist/executor/effectiveLaunch.js +105 -18
- package/dist/executor/executorRegistry.js +29 -44
- package/dist/executor/fileRoleLaunchPlanner.js +229 -154
- package/dist/executor/workspacePreflightClassification.js +16 -16
- package/dist/grant/capabilityGrant.js +6 -3
- package/dist/input/inputRequest.js +12 -10
- package/dist/integration/gitIntegrationService.js +4 -11
- package/dist/integration/integrationQueueService.js +4 -4
- package/dist/interaction/operatorPresentation.js +1 -1
- package/dist/kernel/builtinCapabilities.js +423 -0
- package/dist/kernel/capabilityRegistry.js +314 -0
- package/dist/kernel/capabilitySchema.js +91 -0
- package/dist/kernel/instanceHost.js +18 -1
- package/dist/kernel/kernelPorts.js +4 -1
- package/dist/lifecycle/canonicalLifecycleEvent.js +44 -49
- package/dist/lifecycle/exactRunTerminalization.js +449 -0
- package/dist/message/message.js +62 -6
- package/dist/message/messageContinuation.js +204 -0
- package/dist/observability/executionAudit.js +70 -72
- package/dist/observability/faultClassification.js +2 -2
- package/dist/observability/orchestrationMetrics.js +8 -8
- package/dist/operator/operatorSessionHistory.js +1 -7
- package/dist/output/agentConfigurationPresentation.js +8 -3
- package/dist/output/agentRunConfigurationPresentation.js +128 -0
- package/dist/output/rolePresentation.js +54 -3
- package/dist/plugins/pluginChild.js +104 -0
- package/dist/plugins/pluginIntent.js +26 -0
- package/dist/plugins/pluginInterpreter.js +43 -0
- package/dist/plugins/pluginPackage.js +101 -0
- package/dist/plugins/pluginProcess.js +112 -0
- package/dist/plugins/pluginService.js +380 -0
- package/dist/profile/agentProfile.js +1 -1
- package/dist/repository/gitWorkspace.js +26 -4
- package/dist/repository/project.js +19 -4
- package/dist/repository/taskBaseFreshness.js +13 -13
- package/dist/repository/taskWorkspaceCoordinator.js +20 -27
- package/dist/repository/taskWorkspacePreparer.js +344 -83
- package/dist/resources/autoResourceGc.js +3 -3
- package/dist/resources/liveReferences.js +3 -3
- package/dist/resources/projectResource.js +123 -0
- package/dist/resources/projectResourceService.js +421 -0
- package/dist/resources/resourceDiscovery.js +6 -6
- package/dist/resources/resourceGc.js +1 -1
- package/dist/resources/resourceRegistrar.js +1 -1
- package/dist/resources/resourceTypes.js +1 -1
- package/dist/review/deltaRecheck.js +3 -3
- package/dist/review/reviewAcceptance.js +16 -16
- package/dist/review/reviewDecision.js +7 -7
- package/dist/review/reviewRound.js +21 -20
- package/dist/review/reviewerAvailability.js +2 -2
- package/dist/role/role.js +51 -7
- package/dist/role/taskRoleUpdate.js +30 -0
- package/dist/runtime/acpProtocol.js +425 -0
- package/dist/runtime/acpSession.js +731 -0
- package/dist/runtime/acpSessionConfiguration.js +260 -0
- package/dist/runtime/agentDriver.js +30 -11
- package/dist/runtime/agentEndpoint.js +278 -0
- package/dist/runtime/agentEndpointIdentity.js +86 -0
- package/dist/runtime/agentEndpointOwnership.js +239 -0
- package/dist/runtime/agentError.js +2 -10
- package/dist/runtime/agentHost.js +565 -314
- package/dist/runtime/agentRunConfiguration.js +258 -0
- package/dist/runtime/builtinAgentDrivers.js +134 -18
- package/dist/runtime/builtinAgentErrorMappers.js +55 -3
- package/dist/runtime/builtinTranscriptUsage.js +1 -1
- package/dist/runtime/claude-process-owner +0 -0
- package/dist/runtime/codexAppServerRuntime.js +38 -30
- package/dist/runtime/codexInteractiveHost.js +41 -6
- package/dist/runtime/continuationManager.js +2 -6
- package/dist/runtime/executionEnvironment.js +30 -0
- package/dist/runtime/firstProgressAdvisory.js +11 -11
- package/dist/runtime/index.js +4 -3
- package/dist/runtime/jsonLineChannel.js +109 -0
- package/dist/runtime/launchBroker.js +91 -16
- package/dist/runtime/launchDiagnostics.js +2 -2
- package/dist/runtime/lifecycleReservation.js +10 -18
- package/dist/runtime/managedCaller.js +61 -17
- package/dist/runtime/nativeSessionControl.js +102 -0
- package/dist/runtime/ports.js +6 -21
- package/dist/runtime/processExitObservation.js +8 -7
- package/dist/runtime/promptEnvelope.js +17 -6
- package/dist/runtime/providerContinuation.js +3 -9
- package/dist/runtime/providerContinuationReconciliationService.js +4 -13
- package/dist/runtime/providerControl.js +2 -7
- package/dist/runtime/providerRuntimeIdentity.js +110 -222
- package/dist/runtime/providerRuntimeReconciler.js +5 -9
- package/dist/runtime/runtimeBinding.js +0 -1
- package/dist/runtime/runtimeContinuationProjection.js +4 -7
- package/dist/runtime/runtimeDeadlines.js +9 -0
- package/dist/runtime/runtimeHealthPolicy.js +1 -1
- package/dist/runtime/runtimeObservation.js +29 -65
- package/dist/runtime/runtimeProjection.js +43 -51
- package/dist/runtime/runtimeSessionCandidate.js +1 -3
- package/dist/runtime/sessionLaunchRequest.js +3 -7
- package/dist/runtime/sessionOwnerIdentity.js +7 -54
- package/dist/runtime/sessionOwnerRegistry.js +22 -17
- package/dist/runtime/sessionReconciliation.js +4 -8
- package/dist/runtime/sessionTerminationGuard.js +70 -259
- package/dist/runtime/sessionTokenMetrics.js +5 -16
- package/dist/runtime/structuredProviderHost.js +237 -117
- package/dist/runtime/taskRuntimeIsolation.js +39 -122
- package/dist/runtime/tmuxAdapters.js +39 -86
- package/dist/scheduler/activeRoleRunDelivery.js +354 -0
- package/dist/scheduler/leaderWakeupProcessor.js +75 -266
- package/dist/scheduler/operatorInputNotificationProcessor.js +1 -1
- package/dist/scheduler/ports.js +80 -9
- package/dist/scheduler/{roleTurnLiveness.js → roleRunLiveness.js} +26 -30
- package/dist/scheduler/{roleTurnStall.js → roleRunStall.js} +128 -139
- package/dist/scheduler/taskExecutionProjection.js +120 -124
- package/dist/scheduler/taskObservabilityProjection.js +29 -29
- package/dist/scheduler/taskWake.js +11 -4
- package/dist/scheduler/wakeReason.js +9 -1
- package/dist/setup/setupCommand.js +1 -0
- package/dist/storage/migrations/agentRunContract.js +159 -0
- package/dist/storage/migrations/removeRuntimeGeneration.js +207 -0
- package/dist/storage/sqliteSchema.js +431 -5
- package/dist/storage/sqliteStore.js +375 -220
- package/dist/storage/storageVersions.js +1 -1
- package/dist/storage/storeRpc.js +10 -5
- package/dist/storage/taskStore.js +13 -11
- package/dist/storage/upgrade/upgradeOrchestrator.js +5 -7
- package/dist/surface/surfaceContributions.js +102 -0
- package/dist/task/completionReadiness.js +32 -6
- package/dist/task/deliveryGuard.js +16 -16
- package/dist/task/draftPlan.js +72 -12
- package/dist/task/nextAction.js +144 -128
- package/dist/task/remoteDelivery.js +6 -6
- package/dist/task/task.js +184 -18
- package/dist/task/taskActivation.js +301 -0
- package/dist/task/taskActivationService.js +392 -0
- package/dist/task/taskRecordReference.js +5 -4
- package/dist/task/taskRecordRetirement.js +1 -1
- package/dist/telemetry/sqliteTelemetryStore.js +55 -68
- package/dist/telemetry/telemetryConfig.js +14 -14
- package/dist/telemetry/telemetryWiring.js +2 -2
- package/dist/web/assets/assetManifest.js +2 -0
- package/dist/web/assets/client/app.js +120 -20
- package/dist/web/assets/client/components.js +87 -54
- package/dist/web/assets/client/i18n.js +83 -41
- package/dist/web/assets/client/markdown.js +1 -1
- package/dist/web/assets/client/taskSurface.js +353 -0
- package/dist/web/assets/client/view.js +49 -44
- package/dist/web/assets/shell.js +1 -1
- package/dist/web/assets/styles/cards.js +22 -4
- package/dist/web/controllerWeb.js +60 -0
- package/dist/web/webMutation.js +28 -0
- package/dist/web/webServer.js +118 -8
- package/dist/web/webSnapshot.js +81 -74
- package/dist/web/webTaskSurface.js +64 -0
- package/dist/workItem/dependencyGate.js +1 -1
- package/dist/workItem/workItem.js +80 -48
- package/dist/workspace/workItemChangeSetManager.js +16 -9
- package/docs/agent-result-consumption.md +94 -0
- package/docs/agent-runtime-drivers.md +91 -0
- package/docs/architecture/README.md +38 -0
- package/docs/architecture/capabilities-and-resources.md +79 -0
- package/docs/managed-turn-and-session-runtime.md +222 -0
- package/docs/observability/README.md +81 -0
- package/docs/plugin-sdk.md +290 -0
- package/docs/provider-runtime.md +163 -0
- package/docs/release-workflow.md +303 -0
- package/docs/roles-and-configuration.md +113 -0
- package/docs/sqlite-control-plane-design.md +76 -0
- package/docs/task-dag-semantics.md +57 -0
- package/docs/task-delivery.md +103 -0
- package/docs/task-local-identity.md +6 -6
- package/docs/testing/verification-levels.md +86 -0
- package/i18n/README.zh-CN.md +98 -739
- package/package.json +5 -5
- package/skills/yui-leader/SKILL.md +130 -103
- package/skills/yui-leader/references/integration.md +39 -0
- package/skills/yui-leader/references/replicated-execution.md +42 -0
- package/skills/yui-leader/references/task-plugins.md +33 -0
- package/skills/yui-operator/SKILL.md +30 -59
- package/skills/yui-reviewer/SKILL.md +35 -36
- package/skills/yui-runtime/SKILL.md +88 -24
- package/skills/yui-runtime/references/publication.md +22 -0
- package/skills/yui-runtime/references/recovery.md +64 -0
- package/skills/yui-worker/SKILL.md +37 -39
- package/dist/cli/roleOptionCatalog.js +0 -68
- package/dist/context/sourceTurnContext.js +0 -30
- package/dist/execution/reviewMainTurn.js +0 -161
- package/dist/execution/workItemMainTurn.js +0 -164
- package/dist/lifecycle/exactTurnTerminalization.js +0 -407
- package/dist/runtime/preallocatedNativeSession.js +0 -13
- package/dist/runtime/runtimeStopReceipt.js +0 -42
- package/dist/scheduler/activeRoleTurnDelivery.js +0 -315
package/dist/cli.js
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import { spawnSync } from "node:child_process";
|
|
3
|
+
import { randomUUID } from "node:crypto";
|
|
4
|
+
import { agentAdapterLabel as adapterLabel } from "./agent/adapterCatalog.js";
|
|
3
5
|
import { readFileSync } from "node:fs";
|
|
4
6
|
import { resolve } from "node:path";
|
|
5
7
|
import { createInterface } from "node:readline/promises";
|
|
@@ -24,6 +26,7 @@ import { nativeAgentEnvironmentNames } from "./agent/launchEnvironment.js";
|
|
|
24
26
|
import { runAgentCommand } from "./commands/agentCommands.js";
|
|
25
27
|
import { runGlobalRoleCommand } from "./commands/globalRoleCommands.js";
|
|
26
28
|
import { runConfigCommand } from "./commands/configCommands.js";
|
|
29
|
+
import { runCapabilityCommand } from "./commands/capabilityCommands.js";
|
|
27
30
|
import { CONFIG_DOMAINS } from "./config/configCatalog.js";
|
|
28
31
|
import { runConfigOverview } from "./commands/configOverview.js";
|
|
29
32
|
import { parseControllerCleanupOptions, parseControllerStatusOptions, parseControllerRuntimeSnapshot, renderControllerResourceStatus, renderRuntimeIdentitySection, summarizeDurablePhysicalMismatch, runInteractiveControllerCleanup } from "./commands/controllerCommands.js";
|
|
@@ -42,7 +45,7 @@ import { assertTaskRemoteDeliveryIntegrated, createTaskRemoteDeliveryProof } fro
|
|
|
42
45
|
import { runTaskPublicationVerifyCommand } from "./commands/taskPublicationVerifyCommand.js";
|
|
43
46
|
import { createGitHubCliPublicationVerifier } from "./external/githubPublicationVerifier.js";
|
|
44
47
|
import { createGitLabCliPublicationVerifier } from "./external/gitlabPublicationVerifier.js";
|
|
45
|
-
import {
|
|
48
|
+
import { taskLocalActor, assertTaskDeliveryAuthority } from "./commands/taskActor.js";
|
|
46
49
|
import { parseTaskExecutionStartRequest, parseTaskExecutionStopRequest, finalizeStoppedTaskExecution, startTaskExecutionCommand, stopTaskExecutionCommand } from "./commands/taskExecutionCommands.js";
|
|
47
50
|
import { runTaskIntegrationCommand } from "./commands/taskIntegrationCommands.js";
|
|
48
51
|
import { runTaskChangeSetCommand } from "./commands/taskChangeSetCommands.js";
|
|
@@ -71,7 +74,8 @@ import { runRuntimeObservationHookCommand } from "./controller/runtimeObservatio
|
|
|
71
74
|
import { buildDoctorReport, renderDoctor, runDoctorCommand } from "./doctor/doctor.js";
|
|
72
75
|
import { agentNotFound, CliError, runtimeError, usageError } from "./errors/cliError.js";
|
|
73
76
|
import { FileRoleLaunchPlanner } from "./executor/fileRoleLaunchPlanner.js";
|
|
74
|
-
import { AGENT_HOST_CONTROL_PROTOCOL, runAgentHost, sendAgentHostAuthorityControl } from "./runtime/agentHost.js";
|
|
77
|
+
import { AGENT_HOST_CONTROL_PROTOCOL, inspectAgentHost, runAgentHost, sendAgentHostAuthorityControl } from "./runtime/agentHost.js";
|
|
78
|
+
import { unknownAgentRunConfiguration } from "./runtime/agentRunConfiguration.js";
|
|
75
79
|
import { TaskWorkspaceCoordinator, WorkspaceCleanupBlockedError } from "./repository/taskWorkspaceCoordinator.js";
|
|
76
80
|
import { FileTaskWorkspacePreparer } from "./repository/taskWorkspacePreparer.js";
|
|
77
81
|
import { inspectStorageSchema } from "./storage/storageSchema.js";
|
|
@@ -84,15 +88,15 @@ import { NodeCommandExecutor } from "./tmux/commandExecutor.js";
|
|
|
84
88
|
import { TmuxManager } from "./tmux/tmuxManager.js";
|
|
85
89
|
import { WorkItemChangeSetManager } from "./workspace/workItemChangeSetManager.js";
|
|
86
90
|
import { workspaceProjectEntry } from "./worktree/managedWorkspace.js";
|
|
87
|
-
import { parseWebCommandOptions
|
|
91
|
+
import { parseWebCommandOptions } from "./web/webServer.js";
|
|
88
92
|
import { AgentConfigurationCatalogService, validateAgentLaunchConfiguration } from "./executor/agentConfigurationCatalog.js";
|
|
89
93
|
import { resolveAgentProfileView } from "./profile/agentProfileRuntime.js";
|
|
90
|
-
import { TmuxWebTerminalService } from "./web/tmuxWebTerminal.js";
|
|
91
94
|
import { listOperatorSessions, operatorSessionRef } from "./operator/operatorSessionHistory.js";
|
|
92
95
|
import { YUI_VERSION, yuiVersionIdentity } from "./version.js";
|
|
93
96
|
import { SqliteSchemaMigrationError } from "./storage/sqliteSchema.js";
|
|
94
|
-
import { assertRuntimeCoherence
|
|
95
|
-
import { requireManagedTaskCaller } from "./runtime/managedCaller.js";
|
|
97
|
+
import { assertRuntimeCoherence } from "./runtime/runtimeCoherence.js";
|
|
98
|
+
import { requireManagedTaskCaller, resolveManagedTaskReader } from "./runtime/managedCaller.js";
|
|
99
|
+
import { operatorOfflineCommand, taskDiagnosticTarget } from "./cli/managedDiagnostics.js";
|
|
96
100
|
import { readSessionBootstrapManifest, refreshManagedSessionCliWrappers } from "./context/sessionBootstrapManifest.js";
|
|
97
101
|
import { createTaskFinalReviewContract, extractTaskFinalReviewRequest } from "./review/taskFinalReviewContract.js";
|
|
98
102
|
import { resolveRecordedTaskFinalReviewContract } from "./review/taskFinalReviewContractResolution.js";
|
|
@@ -145,7 +149,7 @@ export async function main() {
|
|
|
145
149
|
|| routedForFence?.kind === "help"
|
|
146
150
|
|| routedForFence?.kind === "path-error"
|
|
147
151
|
|| routedForFence?.kind === "incomplete";
|
|
148
|
-
if (
|
|
152
|
+
if (!homeFreeInvocation) {
|
|
149
153
|
assertCliHomeReleaseFence({
|
|
150
154
|
home,
|
|
151
155
|
packageRoot: fileURLToPath(new URL("../", import.meta.url)),
|
|
@@ -169,7 +173,6 @@ export async function main() {
|
|
|
169
173
|
process.exitCode = delegated.status ?? 5;
|
|
170
174
|
return;
|
|
171
175
|
}
|
|
172
|
-
const { contract: taskFinalReviewContract, verifiedStore } = await preflightManagedTaskControlPlane();
|
|
173
176
|
if (args.length === 0) {
|
|
174
177
|
emit(renderCommandHelp((await import("./cli/commandCatalog.js")).ROOT_COMMAND, VERSION));
|
|
175
178
|
return;
|
|
@@ -191,6 +194,7 @@ export async function main() {
|
|
|
191
194
|
}
|
|
192
195
|
if (args[0] === "version")
|
|
193
196
|
throw usageError("Version usage: yui version");
|
|
197
|
+
const { contract: taskFinalReviewContract, verifiedStore } = await preflightManagedTaskControlPlane();
|
|
194
198
|
if (args[0] === "update") {
|
|
195
199
|
if (jsonOutput)
|
|
196
200
|
throw usageError("Update does not support --json.");
|
|
@@ -249,6 +253,15 @@ export async function main() {
|
|
|
249
253
|
emit(renderCommandHelp(target, VERSION), false, describeCommandTree(target));
|
|
250
254
|
return;
|
|
251
255
|
}
|
|
256
|
+
if (args[0] === "capability") {
|
|
257
|
+
const result = await runCapabilityCommand(args.slice(1), home, process.env);
|
|
258
|
+
emit(JSON.stringify(result, null, 2), false, result);
|
|
259
|
+
const kind = result?.kind;
|
|
260
|
+
if (typeof result === "object" && result !== null && !Array.isArray(result)
|
|
261
|
+
&& typeof kind === "string" && !["value", "operation"].includes(kind))
|
|
262
|
+
process.exitCode = 5;
|
|
263
|
+
return;
|
|
264
|
+
}
|
|
252
265
|
if (args[0] === "setup") {
|
|
253
266
|
if (jsonOutput)
|
|
254
267
|
throw usageError("Setup does not support --json.");
|
|
@@ -318,11 +331,10 @@ export async function main() {
|
|
|
318
331
|
+ `${result.current} already current, ${result.skipped} skipped.`, false, result);
|
|
319
332
|
return;
|
|
320
333
|
}
|
|
321
|
-
if (args[1] === "agent-host" && args.length ===
|
|
334
|
+
if (args[1] === "agent-host" && args.length === 3) {
|
|
322
335
|
process.exitCode = await runAgentHost({
|
|
323
336
|
home,
|
|
324
|
-
|
|
325
|
-
ticket: args[3]
|
|
337
|
+
ticket: args[2]
|
|
326
338
|
});
|
|
327
339
|
return;
|
|
328
340
|
}
|
|
@@ -333,7 +345,7 @@ export async function main() {
|
|
|
333
345
|
if (args[1] === "runtime-hook" && args.length === 2) {
|
|
334
346
|
// Provider lifecycle Hooks are observation channels, never execution
|
|
335
347
|
// gates. A late/stale Hook must not make Claude reject an otherwise
|
|
336
|
-
// valid Session or
|
|
348
|
+
// valid Session or AgentRun; its exact fence is revalidated before any
|
|
337
349
|
// inbox fact is written, so dropping an invalid observation is safe.
|
|
338
350
|
try {
|
|
339
351
|
await runRuntimeObservationHookCommand(readFileSync(0, "utf8"), process.env);
|
|
@@ -539,7 +551,8 @@ export async function main() {
|
|
|
539
551
|
emit(result.output, false, result.data);
|
|
540
552
|
return;
|
|
541
553
|
}
|
|
542
|
-
|
|
554
|
+
if (!operatorOfflineCommand(args))
|
|
555
|
+
await assertFileTaskControllerStorageCompatible(home);
|
|
543
556
|
// Reuse the store the exact runtime preflight already opened and read for
|
|
544
557
|
// this same Home. Opening a second store would parse the unchanged large
|
|
545
558
|
// state a second time; the per-instance fingerprint cache still invalidates
|
|
@@ -576,46 +589,37 @@ export async function main() {
|
|
|
576
589
|
});
|
|
577
590
|
const workspaceCoordinator = new TaskWorkspaceCoordinator(store, workspacePreparer, runtime);
|
|
578
591
|
if (resolved[0] === "web") {
|
|
592
|
+
if (managedInvocation || process.env.YUI_ROLE || process.env.YUI_NATIVE_SESSION_ID) {
|
|
593
|
+
throw usageError("The Web user ingress must be started from a local user terminal, not a managed Session.");
|
|
594
|
+
}
|
|
595
|
+
if (resolved.length === 2 && (resolved[1] === "--status" || resolved[1] === "--stop")) {
|
|
596
|
+
const status = await callController(home, "web.status", {});
|
|
597
|
+
if (resolved[1] === "--status")
|
|
598
|
+
emit(status ? `Yui web control room: ${status.url}\n` : "Web is not running.\n", false, status);
|
|
599
|
+
else {
|
|
600
|
+
if (status)
|
|
601
|
+
await callController(home, "web.stop", { id: status.id });
|
|
602
|
+
emit("Web listener stopped; Controller and Agents are unchanged.\n");
|
|
603
|
+
}
|
|
604
|
+
return;
|
|
605
|
+
}
|
|
579
606
|
if (jsonOutput)
|
|
580
|
-
throw usageError("Web does not support --json.");
|
|
607
|
+
throw usageError("Web start does not support --json; use --status.");
|
|
581
608
|
const options = parseWebCommandOptions(resolved.slice(1));
|
|
582
|
-
const
|
|
583
|
-
|
|
584
|
-
tmuxBin: resolveTmuxBin(store.getConfig().tmuxBin),
|
|
585
|
-
tmux,
|
|
586
|
-
prepareGlobalRole: (roleName) => runtime.prepareGlobalRoleEnter(roleName),
|
|
587
|
-
environment: process.env,
|
|
588
|
-
onError: (error) => {
|
|
589
|
-
const message = error instanceof Error ? error.message : String(error);
|
|
590
|
-
process.stderr.write(`Web terminal cleanup error: ${message}\n`);
|
|
591
|
-
}
|
|
592
|
-
});
|
|
593
|
-
await startYuiWebServer(store, options, {
|
|
594
|
-
terminal,
|
|
595
|
-
answerInput: async ({ taskId, inputId, answer }) => {
|
|
596
|
-
const command = [
|
|
597
|
-
"input", "answer", inputId, "--task", taskId,
|
|
598
|
-
...("choiceKey" in answer
|
|
599
|
-
? ["--choice", answer.choiceKey]
|
|
600
|
-
: ["--text", answer.text])
|
|
601
|
-
];
|
|
602
|
-
const result = runTaskCommand(command, store, {
|
|
603
|
-
runtime,
|
|
604
|
-
environment: {},
|
|
605
|
-
yuiHome: home
|
|
606
|
-
});
|
|
607
|
-
if (result.kind !== "output") {
|
|
608
|
-
throw new Error("Input answer returned an invalid control result.");
|
|
609
|
-
}
|
|
610
|
-
const data = result.data;
|
|
611
|
-
if (data?.request === undefined) {
|
|
612
|
-
throw new Error("Input answer did not return the updated request.");
|
|
613
|
-
}
|
|
614
|
-
return data.request;
|
|
615
|
-
}
|
|
616
|
-
});
|
|
609
|
+
const id = randomUUID();
|
|
610
|
+
await callController(home, "web.start", { ...options, id });
|
|
617
611
|
const displayHost = options.host === "::1" ? "[::1]" : options.host;
|
|
618
612
|
process.stdout.write(`Yui web control room: http://${displayHost}:${options.port}\n`);
|
|
613
|
+
await new Promise((resolve) => {
|
|
614
|
+
const stop = () => {
|
|
615
|
+
process.off("SIGINT", stop);
|
|
616
|
+
process.off("SIGTERM", stop);
|
|
617
|
+
resolve();
|
|
618
|
+
};
|
|
619
|
+
process.once("SIGINT", stop);
|
|
620
|
+
process.once("SIGTERM", stop);
|
|
621
|
+
});
|
|
622
|
+
await callController(home, "web.stop", { id });
|
|
619
623
|
return;
|
|
620
624
|
}
|
|
621
625
|
if (resolved[0] === "config") {
|
|
@@ -793,7 +797,7 @@ export async function main() {
|
|
|
793
797
|
if (task === null)
|
|
794
798
|
throw usageError(`Task not found: ${taskId}.`);
|
|
795
799
|
// Reject managed Task callers before inspecting or starting runtime resources.
|
|
796
|
-
if (
|
|
800
|
+
if (taskLocalActor(store, process.env, taskId) === "leader") {
|
|
797
801
|
throw usageError("Task execution stop/start requires the global Operator or a human user.");
|
|
798
802
|
}
|
|
799
803
|
if (task.executionGate.state === "stopped") {
|
|
@@ -835,7 +839,7 @@ export async function main() {
|
|
|
835
839
|
},
|
|
836
840
|
candidateForTask: async (taskId) => {
|
|
837
841
|
const status = store.getTask(taskId)?.status;
|
|
838
|
-
return status === "active" || status === "
|
|
842
|
+
return status === "active" || status === "cancelled"
|
|
839
843
|
? snapshotActualTaskReviewCandidate(taskId, store, workspacePreparer)
|
|
840
844
|
: null;
|
|
841
845
|
},
|
|
@@ -901,7 +905,7 @@ export async function main() {
|
|
|
901
905
|
throw usageError("Task work capture usage: yui task work capture <task>/<work>.");
|
|
902
906
|
}
|
|
903
907
|
const reference = cliWorkItemReference(workItemId, process.env);
|
|
904
|
-
|
|
908
|
+
assertTaskDeliveryAuthority(store, process.env, reference.taskId);
|
|
905
909
|
const changeSets = await new WorkItemChangeSetManager(store).capture(reference.taskId, reference.localId, taskFinalReviewContract === undefined
|
|
906
910
|
? {}
|
|
907
911
|
: { taskFinalReviewContract });
|
|
@@ -922,7 +926,7 @@ export async function main() {
|
|
|
922
926
|
}
|
|
923
927
|
const reference = cliWorkItemReference(workItemId, process.env);
|
|
924
928
|
const qualified = `${reference.taskId}/${reference.localId}`;
|
|
925
|
-
|
|
929
|
+
assertTaskDeliveryAuthority(store, process.env, reference.taskId);
|
|
926
930
|
if (disposition === "--runtime-only") {
|
|
927
931
|
let runtimeCleanup;
|
|
928
932
|
try {
|
|
@@ -1014,7 +1018,7 @@ export async function main() {
|
|
|
1014
1018
|
.flatMap(({ owner }) => owner.type === "work-item" ? [owner.workItemId] : []);
|
|
1015
1019
|
for (const workItemId of workItemIds) {
|
|
1016
1020
|
const item = store.getWorkItem(task.id, workItemId);
|
|
1017
|
-
if (item?.status !== "
|
|
1021
|
+
if (item?.status !== "accepted" || disposition !== "integrated")
|
|
1018
1022
|
continue;
|
|
1019
1023
|
try {
|
|
1020
1024
|
await new WorkItemChangeSetManager(store).assertIntegrated(task.id, item.id);
|
|
@@ -1061,15 +1065,15 @@ export async function main() {
|
|
|
1061
1065
|
if (item !== null && task !== null) {
|
|
1062
1066
|
// Authority and pure Lane-shape checks precede every physical or
|
|
1063
1067
|
// durable workspace preparation performed for dispatch.
|
|
1064
|
-
|
|
1068
|
+
assertTaskDeliveryAuthority(store, process.env, task.id);
|
|
1065
1069
|
if (item.assignee !== undefined) {
|
|
1066
1070
|
workItemDispatchLanePlan(resolved, store, item);
|
|
1067
1071
|
}
|
|
1068
1072
|
}
|
|
1069
1073
|
// A rejected Candidate starts a new execution iteration. Release every
|
|
1070
1074
|
// terminal Lane Role runtime before preparing the new Lane workspaces;
|
|
1071
|
-
// durable
|
|
1072
|
-
if (item?.status === "
|
|
1075
|
+
// durable AgentRuns, Groups, Candidates, and workspace owners remain intact.
|
|
1076
|
+
if (item?.status === "open"
|
|
1073
1077
|
&& currentWorkItemExecutionGroup(item)?.lanes.every(({ disposition }) => disposition !== "open")) {
|
|
1074
1078
|
await workspaceCoordinator.cleanupWorkItemRuntime(item.taskId, item.id);
|
|
1075
1079
|
}
|
|
@@ -1108,7 +1112,7 @@ export async function main() {
|
|
|
1108
1112
|
try {
|
|
1109
1113
|
const reference = cliWorkItemReference(workItemId, process.env);
|
|
1110
1114
|
workItemIntegrationProof = await new WorkItemChangeSetManager(store)
|
|
1111
|
-
.assertIntegrated(reference.taskId, reference.localId) ?? undefined;
|
|
1115
|
+
.assertIntegrated(reference.taskId, reference.localId, optionValue(resolved, "--candidate")) ?? undefined;
|
|
1112
1116
|
}
|
|
1113
1117
|
catch (error) {
|
|
1114
1118
|
throw usageError(error instanceof Error ? error.message : String(error));
|
|
@@ -1194,6 +1198,11 @@ export async function main() {
|
|
|
1194
1198
|
? await actualTaskReviewCandidateForTaskCommand(resolved, store, workspacePreparer, process.env)
|
|
1195
1199
|
: archiveTaskReviewCandidate;
|
|
1196
1200
|
const deltaRecheckPreflight = await deltaRecheckPreflightForTaskCommand(resolved.slice(1), store, actualTaskReviewCandidate);
|
|
1201
|
+
// Read-only, and only for a Session inspect. The command itself stays
|
|
1202
|
+
// synchronous over persisted state; this is the live reading it prints
|
|
1203
|
+
// beside those facts, prepared here because the Host is reached over a
|
|
1204
|
+
// socket.
|
|
1205
|
+
const liveRunConfiguration = await liveRunConfigurationForTaskCommand(resolved, store, home);
|
|
1197
1206
|
// Physical preparation may precede the durable write, but Task status,
|
|
1198
1207
|
// workspace identity/cwd, and ManagedWorkspace ownership are adopted by
|
|
1199
1208
|
// one transaction. A failed attempt therefore leaves the Task Draft and
|
|
@@ -1203,7 +1212,8 @@ export async function main() {
|
|
|
1203
1212
|
const taskId = resolved[2];
|
|
1204
1213
|
const task = taskId === undefined ? null : store.getTask(taskId);
|
|
1205
1214
|
if (task !== null && task.status === "draft") {
|
|
1206
|
-
|
|
1215
|
+
taskLocalActor(store, process.env, task.id);
|
|
1216
|
+
taskWorkspaceActivation = await workspacePreparer.activateTaskWorkspace(task.id, process.env);
|
|
1207
1217
|
}
|
|
1208
1218
|
}
|
|
1209
1219
|
const result = runTaskCommand(resolved.slice(1), store, {
|
|
@@ -1232,6 +1242,9 @@ export async function main() {
|
|
|
1232
1242
|
...(deltaRecheckPreflight === undefined
|
|
1233
1243
|
? {}
|
|
1234
1244
|
: { deltaRecheckPreflight }),
|
|
1245
|
+
...(liveRunConfiguration === undefined
|
|
1246
|
+
? {}
|
|
1247
|
+
: { liveRunConfiguration }),
|
|
1235
1248
|
...(taskRetirementProof === undefined ? {} : { taskRetirementProof }),
|
|
1236
1249
|
...(validateAgentConfiguration === undefined
|
|
1237
1250
|
? {}
|
|
@@ -1253,13 +1266,13 @@ export async function main() {
|
|
|
1253
1266
|
let reviewData;
|
|
1254
1267
|
const resumesReviewDispatch = (resolved[1] === "review" && resolved[2] === "request")
|
|
1255
1268
|
|| (resolved[1] === "work" && resolved[2] === "review")
|
|
1256
|
-
|| (resolved[1] === "
|
|
1269
|
+
|| (resolved[1] === "run" && resolved[2] === "retry");
|
|
1257
1270
|
const reviewDispatchNeeded = requestedRound?.status === "pending"
|
|
1258
1271
|
|| (requestedRound?.status === "running"
|
|
1259
1272
|
&& resumesReviewDispatch
|
|
1260
1273
|
&& persistedRequestedRound?.executionGroup?.lanes.some((lane) => (lane.disposition === "open"
|
|
1261
|
-
&& (lane.
|
|
1262
|
-
|| store.
|
|
1274
|
+
&& (lane.currentRunId === undefined
|
|
1275
|
+
|| store.getRun(requestedRound.taskId, lane.currentRunId)?.status === "failed"))) === true);
|
|
1263
1276
|
if (reviewDispatchNeeded) {
|
|
1264
1277
|
try {
|
|
1265
1278
|
const workspace = requestedRound.status === "running"
|
|
@@ -1309,7 +1322,7 @@ export async function main() {
|
|
|
1309
1322
|
kind: "started",
|
|
1310
1323
|
reviewerRoleName: requestedRound.reviewerRoleName,
|
|
1311
1324
|
reviewRoundId: requestedRound.id,
|
|
1312
|
-
|
|
1325
|
+
runId: run.id
|
|
1313
1326
|
},
|
|
1314
1327
|
reviewRound: store.getReviewRound(requestedRound.taskId, requestedRound.id),
|
|
1315
1328
|
...(run === null ? {} : { reviewRun: run }),
|
|
@@ -1362,7 +1375,6 @@ export async function main() {
|
|
|
1362
1375
|
agentId: result.agentId,
|
|
1363
1376
|
adapterId: result.adapterId,
|
|
1364
1377
|
nativeSessionId: result.nativeSessionId,
|
|
1365
|
-
...(result.runtimeGenerationId === undefined ? {} : { runtimeGenerationId: result.runtimeGenerationId }),
|
|
1366
1378
|
sessionUpdatedAt: result.sessionUpdatedAt
|
|
1367
1379
|
});
|
|
1368
1380
|
}
|
|
@@ -1436,7 +1448,7 @@ export async function main() {
|
|
|
1436
1448
|
}
|
|
1437
1449
|
finally {
|
|
1438
1450
|
const currentTask = store.getTask(result.taskId);
|
|
1439
|
-
// Completing or retiring the Task from inside the takeover
|
|
1451
|
+
// Completing or retiring the Task from inside the takeover AgentRun owns
|
|
1440
1452
|
// Provider shutdown and clears the live binding. Do not turn that
|
|
1441
1453
|
// successful terminal transition into a failing best-effort release.
|
|
1442
1454
|
if (currentTask?.status === "active") {
|
|
@@ -1520,21 +1532,38 @@ async function preflightManagedTaskControlPlane() {
|
|
|
1520
1532
|
&& ["agent-host", "session-notify", "runtime-hook"].includes(args[1] ?? "");
|
|
1521
1533
|
const home = resolveYuiHome(process.env);
|
|
1522
1534
|
const manifest = assertManagedSessionManifest(home, "task");
|
|
1535
|
+
const diagnosticTarget = taskDiagnosticTarget(args);
|
|
1536
|
+
const diagnostic = diagnosticTarget !== undefined
|
|
1537
|
+
&& diagnosticTarget === process.env.YUI_TASK_ID;
|
|
1538
|
+
if (diagnosticTarget !== undefined && !diagnostic) {
|
|
1539
|
+
throw usageError("Diagnostics must remain within this Session's Task.");
|
|
1540
|
+
}
|
|
1523
1541
|
// One gate for every managed command: the current CLI, Home, and Controller
|
|
1524
1542
|
// must agree. Internal callbacks must still be able to append their immutable
|
|
1525
1543
|
// fact while the Controller is offline.
|
|
1526
|
-
await assertRuntimeCoherence({ actualHome: home }, { checkController: !internalCallback });
|
|
1544
|
+
await assertRuntimeCoherence({ actualHome: home }, { checkController: !internalCallback && !diagnostic });
|
|
1527
1545
|
const verifiedStore = openCurrentTaskStore(home);
|
|
1528
1546
|
// One authority for "may this process act as this Task Role?". Yui's own
|
|
1529
1547
|
// internal callbacks run inside the Host process Yui itself launched; an Agent
|
|
1530
1548
|
// command proves it is the Role's current runtime with its per-Session caller
|
|
1531
1549
|
// key. Nothing here
|
|
1532
|
-
// gates on the current
|
|
1550
|
+
// gates on the current AgentRun: which AgentRun is active is durable state that the
|
|
1533
1551
|
// command needing it reads, never a fact frozen into a process environment.
|
|
1534
1552
|
const runtime = internalCallback
|
|
1535
1553
|
? undefined
|
|
1536
|
-
:
|
|
1554
|
+
: diagnostic
|
|
1555
|
+
? resolveManagedTaskReader(verifiedStore, process.env)
|
|
1556
|
+
: requireManagedTaskCaller(verifiedStore, process.env);
|
|
1557
|
+
if (diagnostic && runtime?.roleName !== "leader"
|
|
1558
|
+
&& !(args[1] === "show"
|
|
1559
|
+
|| (args[1] === "role" && args[2] === "session" && args[3] === "inspect"
|
|
1560
|
+
&& args[5] === runtime?.roleName))) {
|
|
1561
|
+
// Non-Leaders keep their Assignment-scoped read authorization.
|
|
1562
|
+
requireManagedTaskCaller(verifiedStore, process.env);
|
|
1563
|
+
}
|
|
1537
1564
|
const request = taskFinalReviewInvocation.request;
|
|
1565
|
+
if (request !== undefined && diagnostic)
|
|
1566
|
+
requireManagedTaskCaller(verifiedStore, process.env);
|
|
1538
1567
|
if (request === undefined) {
|
|
1539
1568
|
return { contract: undefined, verifiedStore };
|
|
1540
1569
|
}
|
|
@@ -1569,7 +1598,14 @@ async function preflightManagedGlobalControlPlane() {
|
|
|
1569
1598
|
|| manifest.roleKind !== expectedRoleKind) {
|
|
1570
1599
|
throw new Error("Managed global invocation does not match its Session Manifest.");
|
|
1571
1600
|
}
|
|
1572
|
-
|
|
1601
|
+
if (expectedRoleKind === "operator" && ["doctor", "upgrade", "update"].includes(args[0] ?? "")) {
|
|
1602
|
+
// These commands inspect/adopt the storage contract themselves. Requiring
|
|
1603
|
+
// current storage before reaching upgrade would make recovery impossible.
|
|
1604
|
+
return { contract: undefined, verifiedStore: undefined };
|
|
1605
|
+
}
|
|
1606
|
+
await assertRuntimeCoherence({ actualHome: home }, {
|
|
1607
|
+
checkController: !(expectedRoleKind === "operator" && operatorOfflineCommand(args))
|
|
1608
|
+
});
|
|
1573
1609
|
return { contract: undefined, verifiedStore: openCurrentTaskStore(home) };
|
|
1574
1610
|
}
|
|
1575
1611
|
/**
|
|
@@ -1633,7 +1669,7 @@ function cliTaskRecordReference(value, kind, environment) {
|
|
|
1633
1669
|
try {
|
|
1634
1670
|
return resolveTaskRecordReference(value, {
|
|
1635
1671
|
kind,
|
|
1636
|
-
label: kind === "
|
|
1672
|
+
label: kind === "run" ? "AgentRun reference" : "ReviewRound reference",
|
|
1637
1673
|
...(environment.YUI_TASK_ID === undefined
|
|
1638
1674
|
? {}
|
|
1639
1675
|
: { contextTaskId: environment.YUI_TASK_ID })
|
|
@@ -1650,12 +1686,12 @@ function assertWorkItemExecutionDependenciesForCommand(args, store, environment)
|
|
|
1650
1686
|
const reference = cliWorkItemReference(args[3], environment);
|
|
1651
1687
|
item = store.getWorkItem(reference.taskId, reference.localId) ?? undefined;
|
|
1652
1688
|
}
|
|
1653
|
-
else if (args[0] === "task" && args[1] === "
|
|
1689
|
+
else if (args[0] === "task" && args[1] === "run" && args[2] === "retry"
|
|
1654
1690
|
&& args[3] !== undefined) {
|
|
1655
|
-
const reference = cliTaskRecordReference(args[3], "
|
|
1656
|
-
const
|
|
1657
|
-
item =
|
|
1658
|
-
? store.getWorkItem(
|
|
1691
|
+
const reference = cliTaskRecordReference(args[3], "run", environment);
|
|
1692
|
+
const run = store.getRun(reference.taskId, reference.localId);
|
|
1693
|
+
item = run?.purpose === "execution" && run.workItemId !== undefined
|
|
1694
|
+
? store.getWorkItem(run.taskId, run.workItemId) ?? undefined
|
|
1659
1695
|
: undefined;
|
|
1660
1696
|
}
|
|
1661
1697
|
if (item === undefined)
|
|
@@ -1710,7 +1746,7 @@ async function prepareExecutionLaneWorkspacesForCommand(args, store, preparer, e
|
|
|
1710
1746
|
if (store.getRole(item.taskId, roleName) === null) {
|
|
1711
1747
|
throw usageError(`Task Role not found: ${item.taskId}/${roleName}.`);
|
|
1712
1748
|
}
|
|
1713
|
-
if (store.
|
|
1749
|
+
if (store.getActiveRun(item.taskId, roleName) !== null) {
|
|
1714
1750
|
throw usageError(`${item.taskId}/${roleName} already has an active turn.`);
|
|
1715
1751
|
}
|
|
1716
1752
|
}
|
|
@@ -1749,7 +1785,7 @@ function workItemDispatchLanePlan(args, store, item) {
|
|
|
1749
1785
|
const roles = args.flatMap((value, index) => (value === "--lane-role" && args[index + 1] !== undefined
|
|
1750
1786
|
? [args[index + 1]]
|
|
1751
1787
|
: []));
|
|
1752
|
-
const groupId = `execution-group-${store.
|
|
1788
|
+
const groupId = `execution-group-${store.peekNextRunId(item.taskId)}`;
|
|
1753
1789
|
return {
|
|
1754
1790
|
groupId,
|
|
1755
1791
|
...planReplicatedWorkItemLanes(item.assignee, roles, groupId)
|
|
@@ -1845,11 +1881,11 @@ async function actualTaskReviewCandidateForTaskCommand(args, store, preparer, en
|
|
|
1845
1881
|
taskId = reference.taskId;
|
|
1846
1882
|
}
|
|
1847
1883
|
}
|
|
1848
|
-
else if (args[1] === "
|
|
1884
|
+
else if (args[1] === "run"
|
|
1849
1885
|
&& (args[2] === "retry" || args[2] === "settle")
|
|
1850
1886
|
&& args[3] !== undefined) {
|
|
1851
|
-
const reference = cliTaskRecordReference(args[3], "
|
|
1852
|
-
const run = store.
|
|
1887
|
+
const reference = cliTaskRecordReference(args[3], "run", environment);
|
|
1888
|
+
const run = store.getRun(reference.taskId, reference.localId);
|
|
1853
1889
|
const round = run?.reviewRoundId === undefined
|
|
1854
1890
|
? null
|
|
1855
1891
|
: store.getReviewRound(reference.taskId, run.reviewRoundId);
|
|
@@ -1865,7 +1901,6 @@ async function actualTaskReviewCandidateForTaskCommand(args, store, preparer, en
|
|
|
1865
1901
|
taskId = store.getTask(args[2])?.id;
|
|
1866
1902
|
}
|
|
1867
1903
|
else if ((args[1] === "show"
|
|
1868
|
-
|| args[1] === "context"
|
|
1869
1904
|
|| args[1] === "next-action"
|
|
1870
1905
|
|| args[1] === "remote-delivery")
|
|
1871
1906
|
&& args[2] !== undefined) {
|
|
@@ -1873,10 +1908,10 @@ async function actualTaskReviewCandidateForTaskCommand(args, store, preparer, en
|
|
|
1873
1908
|
decisionSupportRead = true;
|
|
1874
1909
|
}
|
|
1875
1910
|
const status = taskId === undefined ? undefined : store.getTask(taskId)?.status;
|
|
1876
|
-
if (taskId === undefined || (status !== "active" && status !== "
|
|
1911
|
+
if (taskId === undefined || (status !== "active" && status !== "cancelled"))
|
|
1877
1912
|
return undefined;
|
|
1878
1913
|
try {
|
|
1879
|
-
return await snapshotActualTaskReviewCandidate(taskId, store, preparer);
|
|
1914
|
+
return await snapshotActualTaskReviewCandidate(taskId, store, preparer, !decisionSupportRead);
|
|
1880
1915
|
}
|
|
1881
1916
|
catch (error) {
|
|
1882
1917
|
if (decisionSupportRead && error instanceof CliError)
|
|
@@ -1884,16 +1919,18 @@ async function actualTaskReviewCandidateForTaskCommand(args, store, preparer, en
|
|
|
1884
1919
|
throw error;
|
|
1885
1920
|
}
|
|
1886
1921
|
}
|
|
1887
|
-
async function snapshotActualTaskReviewCandidate(taskId, store, preparer) {
|
|
1922
|
+
async function snapshotActualTaskReviewCandidate(taskId, store, preparer, prepareWorkspace = true) {
|
|
1888
1923
|
const task = store.getTask(taskId);
|
|
1889
1924
|
if (task === null)
|
|
1890
1925
|
throw usageError(`Task not found: ${taskId}.`);
|
|
1891
1926
|
if (task.projectBindings.length === 0) {
|
|
1892
1927
|
throw usageError(`Final Task Review requires a Project-backed Task: ${task.id}.`);
|
|
1893
1928
|
}
|
|
1894
|
-
//
|
|
1895
|
-
//
|
|
1896
|
-
|
|
1929
|
+
// Mutation preflights reconcile before freezing a candidate. A decision-
|
|
1930
|
+
// support read only observes existing heads; it must not migrate Sessions,
|
|
1931
|
+
// create worktrees or acquire workspace ownership as a side effect.
|
|
1932
|
+
if (prepareWorkspace)
|
|
1933
|
+
await preparer.prepareTaskWorkspace(task.id);
|
|
1897
1934
|
const workspace = store.getTaskWorkspace(task.id);
|
|
1898
1935
|
if (workspace === null
|
|
1899
1936
|
|| workspace.owner.type !== "task"
|
|
@@ -2065,13 +2102,6 @@ async function executeOperatorSessionControl(control, home, store, runtime, tmux
|
|
|
2065
2102
|
await runtime.prepareGlobalRoleEnter(role.name);
|
|
2066
2103
|
tmux.attachRole("operator", role.name, "auto");
|
|
2067
2104
|
}
|
|
2068
|
-
function adapterLabel(adapterId) {
|
|
2069
|
-
return adapterId === "codex"
|
|
2070
|
-
? "Codex"
|
|
2071
|
-
: adapterId === "claude"
|
|
2072
|
-
? "Claude"
|
|
2073
|
-
: adapterId;
|
|
2074
|
-
}
|
|
2075
2105
|
function renderControllerResult(method, value) {
|
|
2076
2106
|
if (typeof value !== "object" || value === null || Array.isArray(value)) {
|
|
2077
2107
|
return JSON.stringify(value);
|
|
@@ -2254,6 +2284,65 @@ async function warmLegacyRoleConfigurationMutation(commandArgs, store, catalogs)
|
|
|
2254
2284
|
cwd: store.getConfig().defaultWorkspace ?? process.cwd()
|
|
2255
2285
|
});
|
|
2256
2286
|
}
|
|
2287
|
+
/**
|
|
2288
|
+
* Ask the live Agent Host what the Session is running under, for a Session
|
|
2289
|
+
* inspect.
|
|
2290
|
+
*
|
|
2291
|
+
* Only for `task role session inspect`. Every other command reads persisted
|
|
2292
|
+
* state and must keep doing so: a query that reached into a running Session
|
|
2293
|
+
* would make reading a Task's records depend on whether an Agent happened to be
|
|
2294
|
+
* up.
|
|
2295
|
+
*
|
|
2296
|
+
* The request is the Host's existing `status` control, which reads state the
|
|
2297
|
+
* Host already holds. It creates no Session, sends no prompt and changes nothing
|
|
2298
|
+
* — which is what lets a read-only inspect use it at all.
|
|
2299
|
+
*
|
|
2300
|
+
* Every failure resolves to `unknown` with the reason rather than propagating:
|
|
2301
|
+
* no Host is running for most Sessions ever inspected, and the persisted facts
|
|
2302
|
+
* the command prints are worth showing regardless of whether a live one answered.
|
|
2303
|
+
*/
|
|
2304
|
+
async function liveRunConfigurationForTaskCommand(args, store, home) {
|
|
2305
|
+
if (args[0] !== "task" || args[1] !== "role" || args[2] !== "session"
|
|
2306
|
+
|| args[3] !== "inspect" || args.length !== 6) {
|
|
2307
|
+
return undefined;
|
|
2308
|
+
}
|
|
2309
|
+
const taskId = args[4];
|
|
2310
|
+
const roleName = args[5];
|
|
2311
|
+
if (taskId === undefined || roleName === undefined)
|
|
2312
|
+
return undefined;
|
|
2313
|
+
// A Session must be recorded as active before asking. Probing a socket for a
|
|
2314
|
+
// Role that never ran would report a reach failure as if it were a fact about
|
|
2315
|
+
// that Role's Agent.
|
|
2316
|
+
const sessions = store.getTaskRoleSessionSet(taskId, roleName);
|
|
2317
|
+
const active = sessions === null
|
|
2318
|
+
? undefined
|
|
2319
|
+
: sessions.sessions[sessions.activeAgentId];
|
|
2320
|
+
if (active === undefined)
|
|
2321
|
+
return undefined;
|
|
2322
|
+
if (active.status !== "active") {
|
|
2323
|
+
return unknownAgentRunConfiguration(`This Session is ${active.status}, so there is no live Agent to report what it `
|
|
2324
|
+
+ "is running under.");
|
|
2325
|
+
}
|
|
2326
|
+
try {
|
|
2327
|
+
const snapshot = await inspectAgentHost({
|
|
2328
|
+
home,
|
|
2329
|
+
scope: "task",
|
|
2330
|
+
taskId,
|
|
2331
|
+
roleName
|
|
2332
|
+
});
|
|
2333
|
+
if (snapshot.nativeSessionId !== active.nativeSessionId
|
|
2334
|
+
|| snapshot.adapterId !== active.adapterId
|
|
2335
|
+
|| snapshot.state === "exited" || snapshot.state === "failed") {
|
|
2336
|
+
return unknownAgentRunConfiguration("The Agent Host has no live connection matching the recorded Session.");
|
|
2337
|
+
}
|
|
2338
|
+
return snapshot.runConfiguration ?? unknownAgentRunConfiguration("The Agent Host is running but has no Provider Session open, so no Agent "
|
|
2339
|
+
+ "has reported a configuration yet.");
|
|
2340
|
+
}
|
|
2341
|
+
catch (error) {
|
|
2342
|
+
return unknownAgentRunConfiguration("The Agent Host for this Session could not be reached, so its live "
|
|
2343
|
+
+ `configuration is unavailable: ${error instanceof Error ? error.message : String(error)}`);
|
|
2344
|
+
}
|
|
2345
|
+
}
|
|
2257
2346
|
function hasModelOrEffortMutation(args) {
|
|
2258
2347
|
const operation = (args[0] === "config" && args[1] === "role")
|
|
2259
2348
|
|| (args[0] === "task" && args[1] === "role");
|
|
@@ -2326,7 +2415,7 @@ function selectionCall(store, catalogs, method, params) {
|
|
|
2326
2415
|
: store.listInputRequests(taskId);
|
|
2327
2416
|
return params.all === true ? requests : requests.filter((request) => request.status === "open");
|
|
2328
2417
|
}
|
|
2329
|
-
case "task.turn.list": return callOptional(reader, "
|
|
2418
|
+
case "task.turn.list": return callOptional(reader, "listRuns", [params.taskId]);
|
|
2330
2419
|
case "task.decision.list": return callOptional(reader, "listDecisions", [params.taskId]);
|
|
2331
2420
|
case "task.milestone.list": return presentSelectionTimes(callOptional(reader, "listMilestones", [params.taskId]), store);
|
|
2332
2421
|
case "task.event.list": return presentSelectionTimes(callOptional(reader, "listEvents", [params.taskId]), store);
|
|
@@ -2424,6 +2513,10 @@ export function cliIdentity(env) {
|
|
|
2424
2513
|
}
|
|
2425
2514
|
function normalizeAliases(input) {
|
|
2426
2515
|
const normalized = [...input];
|
|
2516
|
+
// Existing immutable Session Manifests (through 0.15.8) name this entry.
|
|
2517
|
+
// Remove once those Sessions are retired; both names share one handler.
|
|
2518
|
+
if (normalized[0] === "task" && normalized[1] === "turn")
|
|
2519
|
+
normalized[1] = "run";
|
|
2427
2520
|
if (normalized.length === 1 && (normalized[0] === "-v" || normalized[0] === "--version")) {
|
|
2428
2521
|
return ["version"];
|
|
2429
2522
|
}
|