opencode icon indicating copy to clipboard operation
opencode copied to clipboard

feat: subagents allow-list (global + per-agent wildcard control)

Open malhashemi opened this issue 3 months ago • 1 comments

Summary

Adds configuration-driven allow/deny control over subagent invocation using a global subagents map plus per-agent subagents overrides. Supports wildcard patterns, precedence (longer literal prefix first, later definition wins on ties), and default-deny mode via "*": false.

Key Changes

  • config: Added subagents to global schema and per-agent schema (packages/opencode/src/config/config.ts).
  • logic: New helper packages/opencode/src/agent/subagents.ts providing accessibleSubagents() and isSubagentEnabled() with wildcard + specificity resolution.
  • task tool: Enforces subagent allow list and errors with guidance when a disallowed subagent is requested (packages/opencode/src/tool/task.ts).
  • auto escalation: SessionPrompt.command() now checks allow list before auto-invoking a subagent (packages/opencode/src/session/prompt.ts).
  • tests: Added packages/opencode/test/agent/subagents.test.ts covering default allow, global deny + per-agent allow, wildcard group enable, override, specificity precedence.
  • docs: Updated agents.mdx and config.mdx with usage patterns, resolution rules, and examples.

Behavior

  • If no subagents maps are defined, all subagents remain available (backwards compatible).
  • Adding { "*": false } globally switches to default deny; selectively re-enable with explicit patterns or names.
  • Per-agent map evaluated after global map.
  • Wildcards use simple * → greedy match; specificity = index of first * (longer literal prefix wins), then later definition wins.
  • Disabled subagents do not appear as allowed for Task tool invocation; attempts result in a clear error message pointing to config.

Tests

subagents.test.ts passes (all 5 cases). Existing unrelated failing tests (tool registry initialization ReferenceError and some EditTool replacer cases) are pre-existing and unchanged by this PR.

Typecheck & Build

All packages pass bun turbo typecheck after removing unused variables introduced during development.

Follow-up (Not in Scope Here)

  • Optional: Lightweight advisory on manual @mention of disabled subagent.
  • Optional: Enumerate accessible subagents dynamically in Task tool description.
  • Optional: Fix ToolRegistry cyclic initialization (separate PR).

Migration

No action required. Omit subagents to retain prior behavior.

Risk

Low. Additive config; defaults preserve existing behavior.

malhashemi avatar Sep 19 '25 21:09 malhashemi

Solves #2693

malhashemi avatar Sep 19 '25 21:09 malhashemi