Repository navigation
Description
Before submitting
- I searched existing issues and did not find a duplicate.
- I included enough detail to reproduce or investigate the problem.
Area
Server: MCP orchestration / Linked environments (remote delegate_task)
Steps to reproduce
- On machine A (Windows, v0.1.5), run a thread in Auto runtime mode.
- Link machine B (macOS) and choose the Approval required (supervised) access when approving the link.
t3_environment_linkson A then reports B as reachable withaccess: "approval-required". - From the Auto thread on A, call
delegate_taskwithruntimeMode: "auto"andtarget: { environmentId: <B>, projectId: <project on B>, ... }.
Expected behavior
The call is refused, which is correct: the link's access caps what A's agents can do on B. But the error should say that the link's access is the limit, for example:
Linked environment "" was linked with approval-required access, so a task there cannot run in auto. Omit runtimeMode to run it at approval-required, or link it again with broader access.
Ideally A checks this before forwarding, since A already knows the link's access.
Actual behavior
{"code":"runtime_mode_escalation_denied","message":"Child runtime mode auto is broader than parent mode approval-required."}No child is created. The parent thread is in Auto, so "parent mode approval-required" is wrong from where the agent stands. Agents and users then go looking for a parent-mode or inheritance bug, or ask the user to switch a thread to Auto that is already Auto. Calling orchestrator_capabilities with B's environmentId adds to the confusion: it returns parentThreadId: null, inheritedProviderInstanceId: null, inheritedModel: null, runtimeMode: "approval-required", which looks like the caller's context was dropped. It is actually B's view of the link client, which has no thread.
Cause (from source, unchanged on main at 8970a32)
RemoteDelegation.delegate(apps/server/src/peer/RemoteDelegation.ts) checksresolveRuntimeMode(parent.thread.runtimeMode, input.runtimeMode)against A's parent (auto, so it passes), then forwardst3_thread_launchwithruntimeMode: "auto".- On B, the caller is the link's OAuth client with no thread. So
limits = clientModeCeiling(scope.client), which is the link's approved access (approval-required), narrowed byT3-Mode-Limit(McpInvocationContext.ts). startsThreadsthen callsresolveRuntimeMode(caller.limits.runtimeMode, "auto"). The message in apps/server/src/mcp/delegatedTaskModes.ts always says "parent mode", even when the limit is a client or link ceiling.PeerMcpClient.callre-raises B's failure code and message as-is, so nothing says the refusal came from the link's access.
Suggested fix
- In
RemoteDelegation.delegate(and other forwarded launches), also check the requested mode against the link'saccessbefore forwarding, and fail with a message that names the link and its access. - Make
resolveRuntimeMode/resolveInteractionModetake a label for the limit's source (parent thread, client approval, link access), so the message isn't always "parent mode". This overlaps with the wording point in A lower-mode thread can't report back to the thread that launched it, and the refused send is invisible #26293. - Optionally, let
orchestrator_capabilitieswith anenvironmentIdsay that itsruntimeModeis the link's ceiling, not an inherited parent mode.
Impact
Misleading error (not a security bypass): remote delegation works as a security boundary, but the refusal points at the wrong cause and leads to misdiagnosis.
Version or commit
Desktop + server 0.1.5 (current Latest). Code paths unchanged on main 8970a32.
Environment
Parent on Windows 11 (desktop app 0.1.5) in Auto, linked to a macOS machine with approval-required link access.
Workaround
- Omit
runtimeMode(or pass"inherit"). Going by the source (not tested), the task then runs on B at the link's ceiling (approval-required), and B asks for approvals. - Or have the user link B again with Auto access if they want Auto there. The parent being Auto doesn't help, because the link's access is the limit.
Activity