Least privilege for subagents
A child agent should get exactly the tools its job needs — nothing more. Delegation scopes make that enforceable instead of aspirational.
Agents spawn subagents. It's how complex work gets decomposed: the parent breaks the job down, hands pieces to children, and folds the results back in. The problem is what the child inherits. In most systems, a subagent gets the parent's tools — all of them — because nobody built the machinery to give it fewer. A child tasked with 'summarize this document' can, in principle, reach the deploy tool. In practice it won't. 'In principle' is doing a lot of work in that sentence.
Why it matters
Subagents are where least privilege goes to die. The parent was carefully scoped — someone thought about what it may touch. Then it spawns three children, each with the full toolset, and the careful scoping evaporates. The blast radius of a compromised or confused child is the parent's entire permission set, multiplied by the number of children, for a task that needed two tools.
There's a subtler issue: scope staleness. A parent's permissions change over the run — grants expire, scopes get revoked. If the child's scope was copied at spawn time and never re-checked, it can outlive the parent's authority. The child keeps acting on permissions the parent no longer has. That's not delegation, it's a loophole.
What the fix looks like
Delegation scopes: when a parent spawns a child, it declares the child's scope — the exact set of tools and data the child may touch, which must be a subset of the parent's own. The registry enforces it the same way it enforces everything else: admission checks against the child's scope identity, not the parent's. The child never sees tools outside its scope; discovery itself is scoped.
Two rules keep it honest. First, the newest active scope wins: if scopes change mid-run, the child's effective scope is recomputed — no stale permissions surviving past their revocation. An older, broader scope never shadows a newer, narrower one. Second, scope is declared, not inherited: the default child scope is minimal, and anything beyond that has to be explicitly granted. The lazy path must be the safe path.
The mental model is simple: every agent, parent or child, gets exactly what its job needs and nothing more. Least privilege isn't a policy document. It's an admission check that runs before every call.
A useful rule of thumb for scope design: if you can't state in one sentence why the child needs a tool, it doesn't get it. 'Summarize this document' needs read access to the document. It doesn't need the shell, the deploy tool, or the parent's API keys. Scopes stay small when someone has to justify every entry.