Problem or Use Case
Problem: The current delegate_task uses delegation.model as a single global config for all subagents. You cannot run one subagent on OpenAI GPT-4o and another on Anthropic Claude Sonnet 4.6 simultaneously in the same session — the model field inside each task is ignored.
Proposed Solution
patou:
J'ai toutes les infos pour rédiger la solution technique. Voici le texte ready-to-paste :
Proposed Solution: Per-Task model Override
Files to modify
tools/delegate_tool.py — 2 targeted changes
Change 1 — Loop around line 2061
Current (line 2061-2083):
for i, t in enumerate(task_list):
task_acp_args = t.get("acp_args") if "acp_args" in t else None
effective_role = _normalize_role(t.get("role") or top_role)
child = _build_child_agent(
task_index=i,
goal=t["goal"],
context=t.get("context"),
toolsets=t.get("toolsets") or toolsets,
model=creds["model"], # ← all tasks get same model
max_iterations=effective_max_iter,
task_count=n_tasks,
parent_agent=parent_agent,
override_provider=creds["provider"],
override_base_url=creds["base_url"],
override_api_key=creds["api_key"],
override_api_mode=creds["api_mode"],
override_acp_command=...,
override_acp_args=...,
role=effective_role,
)
Proposed (add per-task model resolution):
for i, t in enumerate(task_list):
task_acp_args = t.get("acp_args") if "acp_args" in t else None
effective_role = _normalize_role(t.get("role") or top_role)
# ── Per-task model override ──────────────────────────────────────
# Per-task model object: {"provider": "openai", "model": "gpt-4o"}
# wins over the global delegation config.
task_model_obj = t.get("model")
if isinstance(task_model_obj, dict):
# Extract from {"provider": ..., "model": ...} dict (batch mode)
per_task_model = task_model_obj.get("model") or creds["model"]
per_task_provider = task_model_obj.get("provider") or creds["provider"]
per_task_base_url = task_model_obj.get("base_url") or creds["base_url"]
per_task_api_key = task_model_obj.get("api_key") or creds["api_key"]
per_task_api_mode = task_model_obj.get("api_mode") or creds["api_mode"]
elif isinstance(task_model_obj, str) and task_model_obj.strip():
# Backwards-compatible string shorthand: "openai/gpt-4o"
per_task_model = task_model_obj
per_task_provider = creds["provider"] # inherit provider from delegation config
per_task_base_url = creds["base_url"]
per_task_api_key = creds["api_key"]
per_task_api_mode = creds["api_mode"]
else:
# No override — fall back to delegation config
per_task_model = creds["model"]
per_task_provider = creds["provider"]
per_task_base_url = creds["base_url"]
per_task_api_key = creds["api_key"]
per_task_api_mode = creds["api_mode"]
child = _build_child_agent(
task_index=i,
goal=t["goal"],
context=t.get("context"),
toolsets=t.get("toolsets") or toolsets,
model=per_task_model, # ← per-task wins now
max_iterations=effective_max_iter,
task_count=n_tasks,
parent_agent=parent_agent,
override_provider=per_task_provider,
override_base_url=per_task_base_url,
override_api_key=per_task_api_key,
override_api_mode=per_task_api_mode,
override_acp_command=...,
override_acp_args=...,
role=effective_role,
)
Change 2 — Nothing else needed
_build_child_agent already accepts model as a parameter and propagates it to AIAgent. The existing override chain (override_provider, override_base_url, override_api_key) already handles credential routing per-provider.
Backwards Compatibility
delegate_task(goal="...") (single)
• Scenario: delegate_task(goal="...") (single)
• Behavior: Uses creds["model"] (unchanged)
delegate_task(tasks=[{"goal": "...", "model": {"provider": "openai", "model": "gpt-4o"}}])
• Scenario: delegate_task(tasks=[{"goal": "...", "model": {"provider": "openai", "model": "gpt-4o"}}])
• Behavior: Per-task override wins
(1/2)
patou:
delegate_task(tasks=[{"goal": "..."}]) (batch, no model)
• Scenario: delegate_task(tasks=[{"goal": "..."}]) (batch, no model)
• Behavior: Uses creds["model"] (unchanged)
delegate_task(tasks=[{"goal": "...", "model": "openai/gpt-4o"}]) (string shorthand)
• Scenario: delegate_task(tasks=[{"goal": "...", "model": "openai/gpt-4o"}]) (string shorthand)
• Behavior: Parsed as "provider/model" fallback
Testing hint
The existing test suite (tests/tools/test_delegate.py) already mocks child.model. Add a test that passes tasks=[{"goal": "A", "model": {"provider": "openai", "model": "gpt-4o"}}, {"goal": "B", "model": {"provider": "anthropic", "model": "claude-sonnet-4-6"}}] and asserts that two children get different models.
Summary: ~30 lines added, zero breaking changes, enables genuine multi-model parallel subagents. The implementation is already halfway there — _build_child_agent already accepts model as a param, it just needed per-task resolution before passing it. (2/2)
Alternatives Considered
No response
Feature Type
New tool
Scope
None
Contribution
Debug Report (optional)
Problem or Use Case
Problem: The current delegate_task uses delegation.model as a single global config for all subagents. You cannot run one subagent on OpenAI GPT-4o and another on Anthropic Claude Sonnet 4.6 simultaneously in the same session — the model field inside each task is ignored.
Proposed Solution
Proposed Solution: Per-Task model Override
Files to modify
tools/delegate_tool.py — 2 targeted changes
Change 1 — Loop around line 2061
Current (line 2061-2083):
for i, t in enumerate(task_list):
task_acp_args = t.get("acp_args") if "acp_args" in t else None
effective_role = _normalize_role(t.get("role") or top_role)
child = _build_child_agent(
task_index=i,
goal=t["goal"],
context=t.get("context"),
toolsets=t.get("toolsets") or toolsets,
model=creds["model"], # ← all tasks get same model
max_iterations=effective_max_iter,
task_count=n_tasks,
parent_agent=parent_agent,
override_provider=creds["provider"],
override_base_url=creds["base_url"],
override_api_key=creds["api_key"],
override_api_mode=creds["api_mode"],
override_acp_command=...,
override_acp_args=...,
role=effective_role,
)
Proposed (add per-task model resolution):
for i, t in enumerate(task_list):
task_acp_args = t.get("acp_args") if "acp_args" in t else None
effective_role = _normalize_role(t.get("role") or top_role)
Change 2 — Nothing else needed
_build_child_agent already accepts model as a parameter and propagates it to AIAgent. The existing override chain (override_provider, override_base_url, override_api_key) already handles credential routing per-provider.
Backwards Compatibility
delegate_task(goal="...") (single)
• Scenario: delegate_task(goal="...") (single)
• Behavior: Uses creds["model"] (unchanged)
delegate_task(tasks=[{"goal": "...", "model": {"provider": "openai", "model": "gpt-4o"}}])
• Scenario: delegate_task(tasks=[{"goal": "...", "model": {"provider": "openai", "model": "gpt-4o"}}])
• Behavior: Per-task override wins
(1/2)
• Scenario: delegate_task(tasks=[{"goal": "..."}]) (batch, no model)
• Behavior: Uses creds["model"] (unchanged)
delegate_task(tasks=[{"goal": "...", "model": "openai/gpt-4o"}]) (string shorthand)
• Scenario: delegate_task(tasks=[{"goal": "...", "model": "openai/gpt-4o"}]) (string shorthand)
• Behavior: Parsed as "provider/model" fallback
Testing hint
The existing test suite (tests/tools/test_delegate.py) already mocks child.model. Add a test that passes tasks=[{"goal": "A", "model": {"provider": "openai", "model": "gpt-4o"}}, {"goal": "B", "model": {"provider": "anthropic", "model": "claude-sonnet-4-6"}}] and asserts that two children get different models.
Summary: ~30 lines added, zero breaking changes, enables genuine multi-model parallel subagents. The implementation is already halfway there — _build_child_agent already accepts model as a param, it just needed per-task resolution before passing it. (2/2)
Alternatives Considered
No response
Feature Type
New tool
Scope
None
Contribution
Debug Report (optional)