mirror of
https://github.com/openai/codex.git
synced 2026-11-08 20:40:33 +00:00
Reload Multi-Agent V2 children through their parent (#40477)
## Why Multi-Agent V2 children are owned by their parent at runtime. Resuming an unloaded child directly could rebuild it from caller-provided settings instead of the parent's current authority. ## What changed - Route child reloads through their loaded immediate parent and reject direct cold resume when that parent is unavailable. - Preserve the child's recorded model, provider, reasoning effort, and role while inheriting the parent's execution policy and MCP extensions. - Validate cached environments against the parent, intersect local permission profiles, and reject stale remote or workspace-root configurations. - Keep paginated cold-resume token usage attribution when attaching to the reloaded child. ## Testing Add coverage for owner validation, nested-parent reloads, permission and environment changes, role instruction restoration, paginated usage replay, and app-server child resume behavior. GitOrigin-RevId: 84014762bcdb57f94fc23974c9c1af55dc1babf1
This commit is contained in:
@@ -52,7 +52,7 @@ impl Handler {
|
||||
session
|
||||
.services
|
||||
.agent_control
|
||||
.ensure_v2_agent_loaded(resume_config, receiver_thread_id)
|
||||
.ensure_v2_agent_loaded(resume_config, receiver_thread_id, /*parent*/ None)
|
||||
.await
|
||||
.map_err(|err| collab_agent_error(receiver_thread_id, err))?;
|
||||
}
|
||||
|
||||
@@ -86,7 +86,7 @@ pub(crate) async fn handle_message_string_tool(
|
||||
session
|
||||
.services
|
||||
.agent_control
|
||||
.ensure_v2_agent_loaded(resume_config, receiver_thread_id)
|
||||
.ensure_v2_agent_loaded(resume_config, receiver_thread_id, /*parent*/ None)
|
||||
.await
|
||||
.map_err(|err| collab_agent_error(receiver_thread_id, err))?;
|
||||
let author = turn
|
||||
|
||||
@@ -150,11 +150,20 @@ async fn handle_spawn_agent(
|
||||
.await?;
|
||||
apply_spawn_agent_runtime_overrides(&mut config, turn.as_ref())?;
|
||||
|
||||
// Remember an applied configured default so cold reload reapplies its restrictions.
|
||||
let persisted_role_name = role_name.or_else(|| {
|
||||
(!is_full_history_fork
|
||||
&& config
|
||||
.agent_roles
|
||||
.get(DEFAULT_ROLE_NAME)
|
||||
.is_some_and(|role| role.config_file.is_some()))
|
||||
.then_some(DEFAULT_ROLE_NAME)
|
||||
});
|
||||
let spawn_source = thread_spawn_source(
|
||||
session.thread_id,
|
||||
&turn.session_source,
|
||||
child_depth,
|
||||
role_name,
|
||||
persisted_role_name,
|
||||
Some(args.task_name.clone()),
|
||||
)?;
|
||||
let new_agent_path = spawn_source.get_agent_path().ok_or_else(|| {
|
||||
|
||||
Reference in New Issue
Block a user