Mentre gli agenti affrontano compiti sempre più ambiziosi, incontrano difficoltà in due aree principali:
- Completare il lavoro in modo affidabile su larga scala
- Gestire il proprio contesto
Abbiamo sperimentato come affrontare queste sfide con ciò che chiamiamo sottoagenti dinamici: invece di assegnare compiti ai sottoagenti attraverso chiamate generiche a strumenti, l'agente scrive un breve script che guida l'esecuzione dei sottoagenti. Questo permette ai modelli di sfruttare pattern di codice in cui sono bravi (come cicli, ramificazioni o concorrenza) per scrivere una logica di orchestrazione adatta al compito.
Perché i sottoagenti dinamici?
Deep Agents supporta già i sottoagenti. Isolano il contesto, permettono all'agente principale di delegare unità di lavoro discrete e mantengono i risultati intermedi fuori dalla finestra di contesto principale. Allora perché servono i sottoagenti dinamici?
Con i sottoagenti normali, vengono chiamati uno alla volta, invocati direttamente dal modello principale. Funziona su piccola scala. Si rompe quando è necessario generare centinaia di sottoagenti, o quando la logica di orchestrazione è condizionale o multifase.
I sottoagenti dinamici risolvono questo problema con l'orchestrazione programmatica. Invece di effettuare chiamate a strumenti passo dopo passo, l'agente scrive un breve script che orchestra e chiama i sottoagenti, e lo esegue in un interprete leggero.
L'esempio canonico: un sottoagente per pagina di un documento di 300 pagine. Invece di chiamare lo strumento sottoagente 300 volte, l'agente scrive un ciclo:
1const results = await Promise.all(pages.map(page =>2 task({ description: `Summarize page ${page.number}`, subagentType: "summarizer" })3));
Questo sblocca due cose che l'orchestrazione basata su chiamate a strumenti non può fornire in modo affidabile:
Copertura deterministica su larga scala. Senza struttura, gli agenti prendono decisioni discrezionali sull'ambito, esaminando 75 elementi su 500 e dichiarando il lavoro finito. Un ciclo di dispatch no. La copertura diventa una garanzia strutturale, non un problema di prompt engineering.
Orchestrazione complessa affidabile. Scrivere l'orchestrazione come codice è più affidabile che far riprodurre al modello una sequenza di chiamate a strumenti, specialmente per fan-out + sintesi, pipeline multifase o ramificazioni condizionali.
Questa è la stessa idea alla base dei workflow in Claude Code e dei Recursive Language Models (RLMs): un modello scrive codice, e quel codice distribuisce più agenti.
Guida rapida
I sottoagenti dinamici richiedono due cose: sottoagenti a cui distribuire il lavoro e un interprete di codice: un runtime sicuro e leggero dove il modello scrive ed esegue il codice di orchestrazione. Deep Agents include un interprete di codice opzionale basato su QuickJS. Per usarlo, installa il pacchetto middleware QuickJS, quindi passa CodeInterpreterMiddleware tramite l'argomento middleware su create_deep_agent.
1pip install -U "deepagents[quickjs]"
1from deepagents import create_deep_agent2from langchain_quickjs import CodeInterpreterMiddleware34agent = create_deep_agent(5 model="openai:gpt-5.5",6 middleware=[CodeInterpreterMiddleware()],7)
Deep Agents include un sottoagente generico preconfigurato, quindi c'è già un profilo di sottoagente generale che può essere utilizzato nei workflow. Per workflow specializzati, configura sottoagenti personalizzati con i propri nomi, descrizioni e prompt di sistema: i nomi e le descrizioni sono il modo in cui l'agente sa quale ruolo utilizzare.
Per attivare i sottoagenti dinamici, dai al tuo agente un prompt con la parola "workflow", in questo modo:
1result = await agent.ainvoke({2 "messages": [{"role": "user", "content": "Esegui un workflow che esamina ogni file in src/routes/ e riassume i rischi principali."}]3})
Utilizzo con un agente di codifica
Il modo più veloce per provare i sottoagenti dinamici è con dcode, il nostro agente di codifica da terminale costruito utilizzando un Deep Agent. Viene fornito con l'interprete di codice abilitato, quindi non c'è niente da configurare: i sottoagenti dinamici funzionano subito.
Installa
1curl -LsSf https://langch.in/dcode | bash
Esegui
1dcode
Per attivare i sottoagenti dinamici, chiedi semplicemente un "workflow". Invece di svolgere il lavoro da solo, o di cercare di gestire la distribuzione dei sottoagenti con il suo strumento task nativo, l'agente scrive uno script di orchestrazione che chiama il task() globale integrato e lo esegue nell'interprete di codice. Ad esempio: "esegui un workflow per esaminare ogni file in src/ per individuare vulnerabilità di SQL injection."
Man mano che i sottoagenti vengono generati, dcode li mostra in tempo reale nel pannello dei sottoagenti dinamici, raggruppati in fasi per dispatch.

Puoi provarlo più velocemente con dcode, ma puoi anche usarlo nel tuo strumento preferito tramite ACP (come Zed)
Come funziona
All'agente viene fornito uno strumento eval. Scrive JavaScript che viene eseguito in modo sicuro all'interno dell'interprete. Quando i sottoagenti sono configurati, l'interprete espone un task() globale integrato che li distribuisce dal codice. In base al compito da svolgere, il modello scrive codice diverso — un ciclo, una ramificazione, un Promise.all — e l'interprete lo esegue in modo deterministico.

task() accetta una descrizione, un subagentType e un responseSchema opzionale — quando fornito, il risultato è già un oggetto tipizzato, pronto per essere filtrato o passato al passaggio successivo.
1const result = await task({2 description: "Esamina src/auth/login.ts per problemi di sicurezza.",3 subagentType: "reviewer",4 responseSchema: {5 type: "object",6 properties: {7 severity: { type: "string", enum: ["high", "medium", "low"] },8 issues: { type: "array", items: { type: "string" } },9 },10 },11});1213const critical = result.severity === "high" ? result.issues : [];14critical; // il modello vede l'ultima riga
Per maggiori informazioni, consulta Sottoagenti programmatici e Interpreti nella documentazione.
Pattern di orchestrazione comuni
I workflow dinamici di Anthropic hanno reso popolare un insieme di pattern di orchestrazione per il lavoro parallelo degli agenti. Non sono funzionalità da attivare. Sono forme che emergono naturalmente dal lavoro, e l'agente si adatta a una diversa man mano che il compito cambia. La tabella seguente mappa ogni forma al tipo di lavoro a cui si adatta.

Di seguito vedremo come funziona ciascun pattern in Deep Agents, con tracce dal vivo. Abbiamo anche preparato un video che spiega questi sei pattern, che puoi vedere qui.
Classifica e agisci
Gli elementi vengono prima classificati, poi ciascun elemento viene gestito da un sottoagente specializzato in base alla sua classificazione. Questo permette di elaborare input misti dove elementi diversi richiedono competenze diverse.

Casi d'uso: Smistamento di ticket di supporto, log di errori, feedback degli utenti, o qualsiasi lotto di elementi che necessita di una gestione diversa a seconda del tipo.
Esempio: smistamento di un arretrato di ticket di supporto. L'agente legge i ticket e classifica ciascuno come bug, richiesta di funzionalità o domanda. I bug a un investigatore di bug, le richieste di funzionalità a un analista di funzionalità e le domande a un risponditore di supporto. Il risultato è un riepilogo raggruppato per categoria.
Visualizza la traccia qui.
Fan-out e sintesi
L'agente distribuisce lo stesso tipo di lavoro su molti elementi in parallelo, quindi combina i risultati.

Casi d'uso: Revisione del codice in una directory, analisi di un lotto di documenti, elaborazione di file di log, esecuzione dello stesso controllo su più servizi.
Esempio: una revisione della sicurezza per file in un albero di origine. L'agente scopre ogni file TypeScript sotto src/ e distribuisce un revisore di sicurezza per file in parallelo. Quindi unisce i risultati in un unico report prioritizzato con valutazioni di gravità e le righe che devono essere modificate.
Visualizza la traccia qui.
Verifica adversarial
Un pattern a due passaggi. Il primo passaggio produce risultati. Il secondo passaggio invia ogni risultato a verificatori indipendenti, e vengono mantenuti solo i risultati che superano la verifica. Questo riduce i falsi positivi quando la fiducia è più importante della velocità.

Casi d'uso: Audit di sicurezza dove i falsi positivi sono costosi, controlli di conformità, qualsiasi revisione in cui è necessaria un'elevata fiducia nei risultati.
Esempio: un audit di sicurezza dove i falsi positivi sono inaccettabili. Un revisore getta una rete ampia per potenziali vulnerabilità, poi ogni risultato viene passato a un verificatore indipendente che legge il codice da zero e restituisce un verdetto CONFERMATO o CONFUTATO. Solo i risultati confermati sopravvivono nel report finale.
Visualizza la traccia qui.
Genera e filtra
Più sottoagenti generano soluzioni indipendenti allo stesso problema. L'agente confronta, valuta e filtra i risultati nel codice, mantenendo solo i migliori.

Casi d'uso: Proposte di architettura, strategie di refactoring, variazioni di contenuto, qualsiasi compito in cui esplorare più opzioni prima di impegnarsi produce un risultato migliore.
Esempio: riprogettazioni concorrenti di un rate-limiter, classificate. L'agente ha un architetto per produrre diverse riprogettazioni indipendenti di rate-limiter.ts, ciascuna scritta in un proprio file in modo che non si sovrascrivano a vicenda. Quindi le valuta in base alla correttezza sotto burst, supporto multi-istanza e complessità. La più forte vince, con una motivazione del perché.
Visualizza la traccia qui.
Torneo
Le variazioni vengono confrontate testa a testa da un sottoagente giudice, con i vincitori che avanzano attraverso turni di eliminazione.

Casi d'uso: Ottimizzazione basata su criteri soggettivi, selezione di stili, scelta tra implementazioni concorrenti.
Esempio: un bracket a coppie su riscritture di un disordinato gestore createOrder. Diversi scrittori producono ciascuno una riscrittura candidata con priorità diverse, poi un giudice le confronta testa a testa, facendo avanzare i vincitori turno dopo turno finché un campione non emerge. Il risultato include la motivazione del giudice.
Visualizza la traccia qui.
Cicla fino al completamento
L'agente esegue un ciclo di scoperta, deduplicando rispetto a ciò che ha già trovato, fino a quando non compaiono nuovi risultati. Utile quando l'ambito del lavoro non è noto in anticipo.

Casi d'uso: Ricerca esaustiva, rilevamento di codice morto, audit delle dipendenze, qualsiasi scansione in cui si desidera completezza invece di un numero fisso di risultati.
Esempio: una scansione di sicurezza basata su passaggi. L'agente esegue un passaggio di scansione, ispeziona ciò che ha trovato nel codice e avvia un altro passaggio solo se quello precedente ha scoperto nuovi problemi. Si ferma quando un passaggio non trova nulla di nuovo. Riporta i risultati consolidati e il numero di passaggi necessari.
Visualizza la traccia qui.
Conclusione
I sottoagenti dinamici sono il modo per dare agli agenti più autonomia e maggiore affidabilità. Il codice gestisce la copertura e il contesto intermedio, mentre il modello si occupa ancora del lavoro pesante di giudizio. I pattern sopra descritti sono un punto di partenza. In pratica, gli agenti compongono e mescolano questi pattern in base a ciò che il compito richiede.
Questa è l'idea del Recursive Language Model nella sua forma più semplice. Un agente che scrive codice, e quel codice distribuisce più agenti. È un agente che chiama se stesso ricorsivamente e non è limitato da una finestra di contesto né racchiuso in un workflow fisso. Un agente può scomporre il problema quanto necessario e riassemblare i pezzi nella forma più adatta. I pattern di orchestrazione evidenziati sopra sono primi scorci di ciò che è possibile, ma il tetto continuerà solo a salire man mano che i modelli miglioreranno nello scrivere codice.
I sottoagenti dinamici sono il modo in cui Deep Agents mette questo nelle tue mani oggi. Inizia aggiungendo un interprete di codice al tuo agente, oppure usa dcode dove i sottoagenti dinamici funzionano subito.
Riconoscimenti
Co-scritto da @colifran_ e @huntlovell. Grazie a @hwchase17, @masondrxy e @chester_curme per la attenta revisione.





