16 Ciclo di vita dei hook16 Ciclo di vita dei hook
17</h2>17</h2>
18 18
19Gli hook si attivano in punti specifici durante una sessione di Claude Code. Quando un evento si attiva e un matcher corrisponde, Claude Code passa il contesto JSON dell'evento al gestore del hook. Per i hook di comando, l'input arriva su stdin. Per i hook HTTP, arriva come corpo della richiesta POST. Il gestore può quindi ispezionare l'input, intraprendere un'azione e facoltativamente restituire una decisione. Gli eventi si dividono in tre cadenze: una volta per sessione (`SessionStart`, `SessionEnd`), una volta per turno (`UserPromptSubmit`, `Stop`, `StopFailure`) e ad ogni chiamata dello strumento all'interno del ciclo agentico (`PreToolUse`, `PostToolUse`):19Gli hook si attivano in punti specifici durante una sessione di Claude Code. Quando un evento si attiva e un matcher corrisponde, Claude Code passa il contesto JSON dell'evento al gestore del hook. Per i hook di comando, l'input arriva su stdin. Per i hook HTTP, arriva come corpo della richiesta POST. Il gestore può quindi ispezionare l'input, intraprendere un'azione e facoltativamente restituire una decisione.
20
21Gli eventi si dividono in tre cadenze:
22
23* una volta per sessione: `SessionStart` e `SessionEnd`
24* una volta per turno: `UserPromptSubmit`, `Stop` e `StopFailure`
25* ad ogni chiamata dello strumento all'interno del ciclo agentico: `PreToolUse` e `PostToolUse`
20 26
21<div style={{maxWidth: "500px", margin: "0 auto"}}>27<div style={{maxWidth: "500px", margin: "0 auto"}}>
22 <Frame>28 <Frame>
214| `SessionStart` | come è iniziata la sessione | `startup`, `resume`, `clear`, `compact` |220| `SessionStart` | come è iniziata la sessione | `startup`, `resume`, `clear`, `compact` |
215| `Setup` | quale flag CLI ha attivato la configurazione | `init`, `maintenance` |221| `Setup` | quale flag CLI ha attivato la configurazione | `init`, `maintenance` |
216| `SessionEnd` | perché è terminata la sessione | `clear`, `resume`, `logout`, `prompt_input_exit`, `bypass_permissions_disabled`, `other` |222| `SessionEnd` | perché è terminata la sessione | `clear`, `resume`, `logout`, `prompt_input_exit`, `bypass_permissions_disabled`, `other` |
217| `Notification` | tipo di notifica | `permission_prompt`, `idle_prompt`, `auth_success`, `elicitation_dialog`, `elicitation_complete`, `elicitation_response` |223| `Notification` | tipo di notifica | `permission_prompt`, `idle_prompt`, `auth_success`, `elicitation_dialog`, `elicitation_complete`, `elicitation_response`, `agent_needs_input`, `agent_completed` |
218| `SubagentStart` | tipo di agente | `general-purpose`, `Explore`, `Plan`, nomi di agenti personalizzati, o nomi con ambito plugin come `^my-plugin:reviewer$` |224| `SubagentStart` | tipo di agente | `general-purpose`, `Explore`, `Plan`, nomi di agenti personalizzati, o nomi con ambito plugin come `^my-plugin:reviewer$` |
219| `PreCompact`, `PostCompact` | cosa ha attivato la compattazione | `manual`, `auto` |225| `PreCompact`, `PostCompact` | cosa ha attivato la compattazione | `manual`, `auto` |
220| `SubagentStop` | tipo di agente | stessi valori di `SubagentStart` |226| `SubagentStop` | tipo di agente | stessi valori di `SubagentStart` |
317 323
318Tutti gli hook corrispondenti vengono eseguiti in parallelo e i gestori identici vengono automaticamente deduplicati. I command hook vengono deduplicati per stringa di comando e `args`, e gli HTTP hook vengono deduplicati per URL.324Tutti gli hook corrispondenti vengono eseguiti in parallelo e i gestori identici vengono automaticamente deduplicati. I command hook vengono deduplicati per stringa di comando e `args`, e gli HTTP hook vengono deduplicati per URL.
319 325
320I gestori vengono eseguiti nella directory corrente con l'ambiente di Claude Code. La variabile di ambiente `$CLAUDE_CODE_REMOTE` è impostata su `"true"` negli ambienti web remoti e non è impostata nella CLI locale.326I gestori vengono eseguiti nella directory corrente con l'ambiente di Claude Code. La variabile di ambiente `$CLAUDE_CODE_REMOTE` è impostata su `"true"` negli ambienti web remoti e non è impostata nella CLI locale. {/* min-version: 2.1.199 */}A partire da v2.1.199, [`$CLAUDE_CODE_BRIDGE_SESSION_ID`](/it/env-vars) è impostato sull'ID della sessione [Remote Control](/it/remote-control) mentre la sessione locale ha una connessione Remote Control attiva.
321 327
322<h4 id="common-fields">328<h4 id="common-fields">
323 Campi comuni329 Campi comuni
704Il codice di uscita 2 è il modo in cui un hook segnala "fermarsi, non farlo". L'effetto dipende dall'evento, perché alcuni eventi rappresentano azioni che possono essere bloccate (come una chiamata dello strumento che non è ancora accaduta) e altri rappresentano cose che sono già accadute o non possono essere prevenute.710Il codice di uscita 2 è il modo in cui un hook segnala "fermarsi, non farlo". L'effetto dipende dall'evento, perché alcuni eventi rappresentano azioni che possono essere bloccate (come una chiamata dello strumento che non è ancora accaduta) e altri rappresentano cose che sono già accadute o non possono essere prevenute.
705 711
706| Hook event | Può bloccare? | Cosa accade su exit 2 |712| Hook event | Può bloccare? | Cosa accade su exit 2 |
707| :-------------------- | :------------ | :---------------------------------------------------------------------------------------------------------------------------------------------------------------- |713| :-------------------- | :------------ | :--------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
708| `PreToolUse` | Sì | Blocca la chiamata dello strumento |714| `PreToolUse` | Sì | Blocca la chiamata dello strumento |
709| `PermissionRequest` | Sì | Nega l'autorizzazione |715| `PermissionRequest` | Sì | Nega l'autorizzazione |
710| `UserPromptSubmit` | Sì | Blocca l'elaborazione del prompt e cancella il prompt |716| `UserPromptSubmit` | Sì | Blocca l'elaborazione del prompt e cancella il prompt |
711| `UserPromptExpansion` | Sì | Blocca l'espansione |717| `UserPromptExpansion` | Sì | Blocca l'espansione |
712| `Stop` | Sì | Impedisce a Claude di fermarsi, continua la conversazione |718| `Stop` | Sì | Impedisce a Claude di fermarsi, continua la conversazione |
713| `SubagentStop` | Sì | Impedisce al subagent di fermarsi |719| `SubagentStop` | Sì | Impedisce al subagent di fermarsi |
714| `TeammateIdle` | Sì | Impedisce al compagno di squadra di andare inattivo (il compagno di squadra continua a lavorare) |720| `TeammateIdle` | Sì | Impedisce al compagno di squadra di andare inattivo, quindi continua a lavorare |
715| `TaskCreated` | Sì | Annulla la creazione dell'attività |721| `TaskCreated` | Sì | Annulla la creazione dell'attività |
716| `TaskCompleted` | Sì | Impedisce che l'attività sia contrassegnata come completata |722| `TaskCompleted` | Sì | Impedisce che l'attività sia contrassegnata come completata |
717| `ConfigChange` | Sì | Blocca la modifica della configurazione dall'avere effetto (tranne `policy_settings`) |723| `ConfigChange` | Sì | Blocca la modifica della configurazione dall'avere effetto (tranne `policy_settings`) |
718| `StopFailure` | No | L'output e il codice di uscita vengono ignorati |724| `StopFailure` | No | L'output e il codice di uscita vengono ignorati |
719| `PostToolUse` | No | Mostra stderr a Claude (lo strumento è già stato eseguito) |725| `PostToolUse` | No | Mostra stderr a Claude; lo strumento è già stato eseguito |
720| `PostToolUseFailure` | No | Mostra stderr a Claude (lo strumento è già fallito) |726| `PostToolUseFailure` | No | Mostra stderr a Claude; lo strumento è già fallito |
721| `PostToolBatch` | Sì | Interrompe il loop agentico prima della prossima chiamata del modello |727| `PostToolBatch` | Sì | Interrompe il loop agentico prima della prossima chiamata del modello |
722| `PermissionDenied` | No | Il codice di uscita e stderr vengono ignorati (il rifiuto è già avvenuto). Utilizzare JSON `hookSpecificOutput.retry: true` per dire al modello che può riprovare |728| `PermissionDenied` | No | Il codice di uscita e stderr vengono ignorati perché il rifiuto è già avvenuto. Utilizzare JSON `hookSpecificOutput.retry: true` per dire al modello che può riprovare |
723| `Notification` | No | Mostra stderr solo all'utente |729| `Notification` | No | Mostra stderr solo all'utente |
724| `SubagentStart` | No | Mostra stderr solo all'utente |730| `SubagentStart` | No | Mostra stderr solo all'utente |
725| `SessionStart` | No | Mostra stderr solo all'utente |731| `SessionStart` | No | Mostra stderr solo all'utente |
736| `InstructionsLoaded` | No | Il codice di uscita viene ignorato |742| `InstructionsLoaded` | No | Il codice di uscita viene ignorato |
737| `MessageDisplay` | No | Il testo originale viene visualizzato |743| `MessageDisplay` | No | Il testo originale viene visualizzato |
738 744
745Per `SessionStart`, `Setup` e `SubagentStart`, lo stderr del codice di uscita 2 viene visualizzato nella trascrizione come un avviso `<hook name> hook error`, nello stesso modo di un [errore non bloccante](#exit-code-output). Claude non lo vede e la sessione o il subagent procede. Per `SubagentStart`, l'avviso appare nella trascrizione del subagent stesso, non nella conversazione padre.
746
747A partire da Claude Code v2.1.199, `SessionStart`, `Setup` e `SubagentStart` mostrano lo stderr del codice di uscita 2 nella trascrizione. Le versioni precedenti lo scrivevano solo nel log di debug.
748
739<h3 id="http-response-handling">749<h3 id="http-response-handling">
740 Gestione della risposta HTTP750 Gestione della risposta HTTP
741</h3>751</h3>
963 Input di SessionStart973 Input di SessionStart
964</h4>974</h4>
965 975
966Oltre ai [campi di input comuni](#common-input-fields), gli hook SessionStart ricevono `source` e facoltativamente `model`, `agent_type` e `session_title`. Il campo `source` indica come è iniziata la sessione: `"startup"` per le nuove sessioni, `"resume"` per le sessioni riprese, `"clear"` dopo `/clear` o `"compact"` dopo la compattazione. Il campo `model` contiene l'identificatore del modello attivo. Può essere omesso, ad esempio dopo `/clear` o quando una sessione viene ripristinata attraverso il recupero della conversazione, quindi controllare il campo prima di leggerlo. Se si avvia Claude Code con `claude --agent <name>`, un campo `agent_type` contiene il nome dell'agente. Il campo `session_title` contiene il titolo della sessione corrente se uno è già impostato, ad esempio tramite `--name` o `/rename`. Un hook che emette `sessionTitle` può controllare prima `session_title` per evitare di sovrascrivere un titolo impostato esplicitamente dall'utente.976Oltre ai [campi di input comuni](#common-input-fields), gli hook SessionStart ricevono `source` e facoltativamente `model`, `agent_type` e `session_title`:
977
978| Campo | Descrizione |
979| :-------------- | :----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
980| `source` | Come è iniziata la sessione: `"startup"` per le nuove sessioni, `"resume"` per le sessioni riprese, `"clear"` dopo `/clear` o `"compact"` dopo la compattazione |
981| `model` | L'identificatore del modello attivo. Può essere omesso, ad esempio dopo `/clear` o quando una sessione viene ripristinata attraverso il recupero della conversazione, quindi controllare il campo prima di leggerlo |
982| `agent_type` | Il nome dell'agente, presente quando si avvia Claude Code con `claude --agent <name>` |
983| `session_title` | Il titolo della sessione corrente se uno è già impostato, ad esempio tramite `--name` o `/rename`. Un hook che emette `sessionTitle` può controllare prima `session_title` per evitare di sovrascrivere un titolo impostato esplicitamente dall'utente |
967 984
968```json theme={null}985```json theme={null}
969{986{
983Qualsiasi testo che lo script del hook stampa su stdout viene aggiunto come contesto per Claude. Oltre ai [campi di output JSON](#json-output) disponibili per tutti gli hook, è possibile restituire questi campi specifici dell'evento:1000Qualsiasi testo che lo script del hook stampa su stdout viene aggiunto come contesto per Claude. Oltre ai [campi di output JSON](#json-output) disponibili per tutti gli hook, è possibile restituire questi campi specifici dell'evento:
984 1001
985| Campo | Descrizione |1002| Campo | Descrizione |
986| :------------------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |1003| :------------------- | :----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
987| `additionalContext` | Stringa aggiunta al contesto di Claude all'inizio della conversazione, prima del primo prompt. Consultare [Aggiungere contesto per Claude](#add-context-for-claude) per come il testo viene consegnato e cosa inserirvi |1004| `additionalContext` | Stringa aggiunta al contesto di Claude all'inizio della conversazione, prima del primo prompt. Consultare [Aggiungere contesto per Claude](#add-context-for-claude) per come il testo viene consegnato e cosa inserirvi |
988| `initialUserMessage` | Stringa utilizzata come primo messaggio dell'utente della sessione. Si applica in [modalità non interattiva](/it/headless) (`-p`), dove diventa il primo turno anche se non viene fornito alcun prompt. Se viene fornito un prompt, segue come turno successivo. A differenza di `additionalContext`, che si allega a un turno esistente, questo crea il turno |1005| `initialUserMessage` | Stringa utilizzata come primo messaggio dell'utente della sessione. Si applica in [modalità non interattiva](/it/headless) con il flag `-p`, dove diventa il primo turno anche se non viene fornito alcun prompt. Se viene fornito un prompt, segue come turno successivo. A differenza di `additionalContext`, che si allega a un turno esistente, questo crea il turno |
989| `sessionTitle` | Imposta il titolo della sessione, con lo stesso effetto di `/rename`. Utilizzare per denominare automaticamente le sessioni dalla cartella di avvio, dal ramo git o dal nome del worktree. Si applica solo quando `source` è `"startup"` o `"resume"`; ignorato su `"clear"` e `"compact"` |1006| `sessionTitle` | Imposta il titolo della sessione, con lo stesso effetto di `/rename`. Utilizzare per denominare automaticamente le sessioni dalla cartella di avvio, dal ramo git o dal nome del worktree. Si applica solo quando `source` è `"startup"` o `"resume"`; ignorato su `"clear"` e `"compact"` |
990| `watchPaths` | Array di percorsi assoluti da monitorare per gli eventi [FileChanged](#filechanged) durante questa sessione |1007| `watchPaths` | Array di percorsi assoluti da monitorare per gli eventi [FileChanged](#filechanged) durante questa sessione |
991| `reloadSkills` | Booleano. Quando `true`, Claude Code esegue nuovamente la scansione delle directory [skill](/it/skills) e dei comandi dopo il completamento degli hook SessionStart, in modo che le skill installate dall'hook siano disponibili nella stessa sessione, a partire dal primo prompt |1008| `reloadSkills` | Booleano. Quando `true`, Claude Code esegue nuovamente la scansione delle directory [skill](/it/skills) e dei comandi dopo il completamento degli hook SessionStart, in modo che le skill installate dall'hook siano disponibili nella stessa sessione, a partire dal primo prompt |
1062 Setup1079 Setup
1063</h3>1080</h3>
1064 1081
1065Si attiva solo quando si avvia Claude Code con `--init-only`, o con `--init` o `--maintenance` in modalità stampa (`-p`). Non si attiva all'avvio normale. Utilizzarlo per l'installazione di dipendenze una tantum o la pulizia pianificata che si attiva esplicitamente da CI o script, separato dall'avvio della sessione normale. Per l'inizializzazione per sessione, utilizzare [SessionStart](#sessionstart) invece.1082Si attiva solo quando si avvia Claude Code con `--init-only`, o con `--init` o `--maintenance` in [modalità non interattiva](/it/headless) con il flag `-p`. Non si attiva all'avvio normale. Utilizzarlo per l'installazione di dipendenze una tantum o la pulizia pianificata che si attiva esplicitamente da CI o script, separato dall'avvio della sessione normale. Per l'inizializzazione per sessione, utilizzare [SessionStart](#sessionstart) invece.
1066 1083
1067Il valore del matcher corrisponde al flag CLI che ha attivato l'hook:1084Il valore del matcher corrisponde al flag CLI che ha attivato l'hook:
1068 1085
1071| `init` | `claude --init-only` o `claude -p --init` |1088| `init` | `claude --init-only` o `claude -p --init` |
1072| `maintenance` | `claude -p --maintenance` |1089| `maintenance` | `claude -p --maintenance` |
1073 1090
1074`--init-only` esegue gli hook Setup e gli hook SessionStart con il matcher `startup`, quindi esce senza avviare una conversazione. `--init` e `--maintenance` attivano gli hook Setup solo quando combinati con `-p` (modalità stampa); in una sessione interattiva questi due flag attualmente non attivano gli hook Setup.1091`--init-only` esegue gli hook Setup e gli hook SessionStart con il matcher `startup`, quindi esce senza avviare una conversazione. `--init` e `--maintenance` attivano gli hook Setup solo quando combinati con `-p`; in una sessione interattiva questi due flag attualmente non attivano gli hook Setup.
1075 1092
1076Poiché Setup non si attiva ad ogni avvio, un plugin che ha bisogno di una dipendenza installata non può fare affidamento solo su Setup. Il modello pratico è controllare la dipendenza al primo utilizzo e installare se assente, ad esempio un hook o una skill che testa per `${CLAUDE_PLUGIN_DATA}/node_modules` ed esegue `npm install` se assente. Consultare la [directory dei dati persistenti](/it/plugins-reference#persistent-data-directory) per dove archiviare le dipendenze installate.1093Poiché Setup non si attiva ad ogni avvio, un plugin che ha bisogno di una dipendenza installata non può fare affidamento solo su Setup. Il modello pratico è controllare la dipendenza al primo utilizzo e installare se assente, ad esempio un hook o una skill che testa per `${CLAUDE_PLUGIN_DATA}/node_modules` ed esegue `npm install` se assente. Consultare la [directory dei dati persistenti](/it/plugins-reference#persistent-data-directory) per dove archiviare le dipendenze installate.
1077 1094
1095 Controllo della decisione di Setup1112 Controllo della decisione di Setup
1096</h4>1113</h4>
1097 1114
1098Gli hook Setup non possono bloccare. Su exit code 2, stderr viene mostrato all'utente; su qualsiasi altro exit code non zero, stderr appare solo quando si avvia con `--verbose`. In entrambi i casi l'esecuzione continua. Per passare informazioni nel contesto di Claude, restituire `additionalContext` nell'output JSON; lo stdout semplice viene scritto solo nel log di debug. Oltre ai [campi di output JSON](#json-output) disponibili per tutti gli hook, è possibile restituire questi campi specifici dell'evento:1115Gli hook Setup non possono bloccare. Su exit code 2, stderr viene mostrato all'utente come avviso `<hook name> hook error`; su qualsiasi altro exit code non zero, stderr appare solo quando si avvia con `--verbose`. In entrambi i casi l'esecuzione continua. Per passare informazioni nel contesto di Claude, restituire `additionalContext` nell'output JSON; lo stdout semplice viene scritto solo nel log di debug. Oltre ai [campi di output JSON](#json-output) disponibili per tutti gli hook, è possibile restituire questi campi specifici dell'evento:
1099 1116
1100| Campo | Descrizione |1117| Campo | Descrizione |
1101| :------------------ | :------------------------------------------------------------------------------- |1118| :------------------ | :------------------------------------------------------------------------------- |
1191* **Stdout di testo semplice**: qualsiasi testo non-JSON scritto su stdout viene aggiunto come contesto1208* **Stdout di testo semplice**: qualsiasi testo non-JSON scritto su stdout viene aggiunto come contesto
1192* **JSON con `additionalContext`**: utilizzare il formato JSON seguente per un controllo maggiore. Il campo `additionalContext` viene aggiunto come contesto1209* **JSON con `additionalContext`**: utilizzare il formato JSON seguente per un controllo maggiore. Il campo `additionalContext` viene aggiunto come contesto
1193 1210
1194Lo stdout semplice viene mostrato come output del hook nella trascrizione. Il campo `additionalContext` viene aggiunto più discretamente.1211Lo stdout semplice viene mostrato come output del hook nella trascrizione. Il valore `additionalContext` viene iniettato come un promemoria di sistema che Claude legge senza una voce di trascrizione visibile.
1195 1212
1196Per bloccare un prompt, restituire un oggetto JSON con `decision` impostato su `"block"`:1213Per bloccare un prompt, restituire un oggetto JSON con `decision` impostato su `"block"`:
1197 1214
1215}1232}
1216```1233```
1217 1234
1218<Note>
1219 Il formato JSON non è obbligatorio per i casi semplici. Per aggiungere contesto, è possibile stampare testo semplice su stdout con exit code 0. Utilizzare JSON quando è necessario bloccare i prompt o si desidera un controllo più strutturato.
1220</Note>
1221
1222<h3 id="userpromptexpansion">1235<h3 id="userpromptexpansion">
1223 UserPromptExpansion1236 UserPromptExpansion
1224</h3>1237</h3>
1545In `PostToolUse`, `tool_response` per una chiamata Agent completata contiene il testo finale del subagent insieme alla telemetria di utilizzo. Leggere questi campi per registrare il costo per subagent da un hook:1558In `PostToolUse`, `tool_response` per una chiamata Agent completata contiene il testo finale del subagent insieme alla telemetria di utilizzo. Leggere questi campi per registrare il costo per subagent da un hook:
1546 1559
1547| Campo | Tipo | Esempio | Descrizione |1560| Campo | Tipo | Esempio | Descrizione |
1548| :------------------ | :----- | :---------------------------------------------------- | :----------------------------------------------------------------------------------------------------------------------------------------------------------- |1561| :------------------ | :----- | :---------------------------------------------------- | :----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
1549| `status` | string | `"completed"` | `"completed"` per le chiamate sincrone, `"async_launched"` per `run_in_background: true` |1562| `status` | string | `"completed"` | `"completed"` per le chiamate sincrone, `"async_launched"` per le chiamate in background. {/* min-version: 2.1.198 */}A partire da v2.1.198, i subagent vengono eseguiti in background per impostazione predefinita, quindi un `run_in_background` omesso produce anche `"async_launched"` |
1550| `agentId` | string | `"a4d2c8f1e0b3a297"` | Identificatore per l'esecuzione del subagent |1563| `agentId` | string | `"a4d2c8f1e0b3a297"` | Identificatore per l'esecuzione del subagent |
1551| `content` | array | `[{"type": "text", "text": "Found 12 endpoints..."}]` | I blocchi di testo finali del subagent |1564| `content` | array | `[{"type": "text", "text": "Found 12 endpoints..."}]` | I blocchi di testo finali del subagent |
1552| `resolvedModel` | string | `"claude-sonnet-4-5"` | Modello su cui è stato eseguito il subagent, che può differire dal modello richiesto. {/* min-version: 2.1.174 */}Richiede Claude Code v2.1.174 o successivo |1565| `resolvedModel` | string | `"claude-sonnet-4-5"` | Modello su cui è stato eseguito il subagent, che può differire dal modello richiesto. {/* min-version: 2.1.174 */}Richiede Claude Code v2.1.174 o successivo |
1555| `totalToolUseCount` | number | `7` | Conteggio delle chiamate dello strumento effettuate dal subagent |1568| `totalToolUseCount` | number | `7` | Conteggio delle chiamate dello strumento effettuate dal subagent |
1556| `usage` | object | `{"input_tokens": 8320, ...}` | Suddivisione dei token per tipo: `input_tokens`, `output_tokens`, `cache_creation_input_tokens`, `cache_read_input_tokens` |1569| `usage` | object | `{"input_tokens": 8320, ...}` | Suddivisione dei token per tipo: `input_tokens`, `output_tokens`, `cache_creation_input_tokens`, `cache_read_input_tokens` |
1557 1570
1558Per le chiamate `run_in_background: true`, lo strumento ritorna immediatamente dopo il lancio del subagent, quindi `tool_response` non contiene campi di utilizzo. Ha `status: "async_launched"`, `agentId`, `description`, `prompt`, `outputFile` e `resolvedModel` invece.1571Per le chiamate in background, lo strumento ritorna immediatamente dopo il lancio del subagent, quindi `tool_response` non contiene campi di utilizzo. Ha `status: "async_launched"`, `agentId`, `description`, `prompt`, `outputFile` e `resolvedModel` invece.
1559 1572
1560Il campo `resolvedModel` nomina il modello su cui il subagent effettivamente viene eseguito, che può differire dal valore `model` in `tool_input`. Richiede Claude Code v2.1.174 o successivo.1573Il campo `resolvedModel` nomina il modello su cui il subagent effettivamente viene eseguito, che può differire dal valore `model` in `tool_input`, ad esempio quando `availableModels` o un altro override si applica. Richiede Claude Code v2.1.174 o successivo.
1561 1574
1562<a id="askuserquestion" />1575<a id="askuserquestion" />
1563 1576
1587In `PostToolUse`, `tool_response` è un oggetto con i campi `plan` e `filePath` che contengono il piano approvato, più flag di stato interni. Leggere `tool_response.plan` per il contenuto del piano piuttosto che rileggere il file da disco.1600In `PostToolUse`, `tool_response` è un oggetto con i campi `plan` e `filePath` che contengono il piano approvato, più flag di stato interni. Leggere `tool_response.plan` per il contenuto del piano piuttosto che rileggere il file da disco.
1588 1601
1589<h4 id="pretooluse-decision-control">1602<h4 id="pretooluse-decision-control">
1590 PreToolUse decision control1603 Controllo della decisione di PreToolUse
1591</h4>1604</h4>
1592 1605
1593Gli hook `PreToolUse` possono controllare se una chiamata dello strumento procede. A differenza di altri hook che utilizzano un campo `decision` di livello superiore, PreToolUse restituisce la sua decisione all'interno di un oggetto `hookSpecificOutput`. Ciò gli dà un controllo più ricco: quattro risultati (consentire, negare, chiedere o rinviare) più la capacità di modificare l'input dello strumento prima dell'esecuzione.1606Gli hook `PreToolUse` possono controllare se una chiamata dello strumento procede. A differenza di altri hook che utilizzano un campo `decision` di livello superiore, PreToolUse restituisce la sua decisione all'interno di un oggetto `hookSpecificOutput`. Ciò gli dà un controllo più ricco: quattro risultati (consentire, negare, chiedere o rinviare) più la capacità di modificare l'input dello strumento prima dell'esecuzione.
1594 1607
1595| Campo | Descrizione |1608| Campo | Descrizione |
1596| :------------------------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |1609| :------------------------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
1597| `permissionDecision` | `"allow"` bypassa il prompt di autorizzazione. `"deny"` impedisce la chiamata dello strumento. `"ask"` richiede all'utente di confermare. `"defer"` esce correttamente in modo che lo strumento possa essere ripreso in seguito. Le regole [Deny and ask](/it/permissions#manage-permissions) si applicano ancora indipendentemente da quello che l'hook restituisce |1610| `permissionDecision` | `"allow"` bypassa il prompt di autorizzazione, tranne per [strumenti che richiedono l'interazione dell'utente](#pretooluse-decision-control). `"deny"` impedisce la chiamata dello strumento. `"ask"` richiede all'utente di confermare. `"defer"` esce correttamente in modo che lo strumento possa essere ripreso in seguito. Le regole [Deny and ask](/it/permissions#manage-permissions) si applicano ancora indipendentemente da quello che l'hook restituisce |
1598| `permissionDecisionReason` | Per `"allow"` e `"ask"`, mostrato all'utente ma non a Claude. Per `"deny"`, mostrato a Claude. Per `"defer"`, ignorato |1611| `permissionDecisionReason` | Per `"allow"` e `"ask"`, mostrato all'utente ma non a Claude. Per `"deny"`, mostrato a Claude. Per `"defer"`, ignorato |
1599| `updatedInput` | Modifica i parametri di input dello strumento prima dell'esecuzione. Sostituisce l'intero oggetto di input, quindi includere i campi invariati insieme a quelli modificati. Combinare con `"allow"` per l'approvazione automatica o `"ask"` per mostrare l'input modificato all'utente. Per `"defer"`, ignorato |1612| `updatedInput` | Modifica i parametri di input dello strumento prima dell'esecuzione. Sostituisce l'intero oggetto di input, quindi includere i campi invariati insieme a quelli modificati. Combinare con `"allow"` per l'approvazione automatica o `"ask"` per mostrare l'input modificato all'utente. Per `"defer"`, ignorato |
1600| `additionalContext` | Stringa aggiunta al contesto di Claude insieme al risultato dello strumento. Ignorato quando `permissionDecision` è `"defer"`. Consultare [Aggiungere contesto per Claude](#add-context-for-claude) |1613| `additionalContext` | Stringa aggiunta al contesto di Claude insieme al risultato dello strumento. Ignorato quando `permissionDecision` è `"defer"`. Consultare [Aggiungere contesto per Claude](#add-context-for-claude) |
1619 1632
1620`AskUserQuestion` e `ExitPlanMode` richiedono l'interazione dell'utente e normalmente bloccano in [modalità non interattiva](/it/headless) con il flag `-p`. Restituire `permissionDecision: "allow"` insieme a `updatedInput` soddisfa quel requisito: l'hook legge l'input dello strumento da stdin, raccoglie la risposta attraverso la propria interfaccia utente e la restituisce in `updatedInput` in modo che lo strumento venga eseguito senza richiedere. Restituire `"allow"` da solo non è sufficiente per questi strumenti. Per `AskUserQuestion`, ripetere l'array `questions` originale e aggiungere un oggetto [`answers`](#askuserquestion) che mappa il testo di ogni domanda alla risposta scelta.1633`AskUserQuestion` e `ExitPlanMode` richiedono l'interazione dell'utente e normalmente bloccano in [modalità non interattiva](/it/headless) con il flag `-p`. Restituire `permissionDecision: "allow"` insieme a `updatedInput` soddisfa quel requisito: l'hook legge l'input dello strumento da stdin, raccoglie la risposta attraverso la propria interfaccia utente e la restituisce in `updatedInput` in modo che lo strumento venga eseguito senza richiedere. Restituire `"allow"` da solo non è sufficiente per questi strumenti. Per `AskUserQuestion`, ripetere l'array `questions` originale e aggiungere un oggetto [`answers`](#askuserquestion) che mappa il testo di ogni domanda alla risposta scelta.
1621 1634
1635A partire da v2.1.199, uno strumento MCP il cui server lo contrassegna con [`_meta["anthropic/requiresUserInteraction"]`](/it/mcp#require-approval-for-a-specific-tool) è più rigoroso: un hook non può saltare il suo prompt di approvazione con `"allow"`, con o senza `updatedInput`, perché Claude Code non può confermare che l'hook ha raccolto l'interazione di cui lo strumento ha bisogno.
1636
1622<Note>1637<Note>
1623 PreToolUse in precedenza utilizzava i campi `decision` e `reason` di livello superiore, ma questi sono deprecati per questo evento. Utilizzare invece `hookSpecificOutput.permissionDecision` e `hookSpecificOutput.permissionDecisionReason`. I valori deprecati `"approve"` e `"block"` si mappano a `"allow"` e `"deny"` rispettivamente. Gli altri eventi come PostToolUse e Stop continuano a utilizzare `decision` e `reason` di livello superiore come formato corrente.1638 PreToolUse in precedenza utilizzava i campi `decision` e `reason` di livello superiore, ma questi sono deprecati per questo evento. Utilizzare invece `hookSpecificOutput.permissionDecision` e `hookSpecificOutput.permissionDecisionReason`. I valori deprecati `"approve"` e `"block"` si mappano a `"allow"` e `"deny"` rispettivamente. Gli altri eventi come PostToolUse e Stop continuano a utilizzare `decision` e `reason` di livello superiore come formato corrente.
1624</Note>1639</Note>
2016 Notification2031 Notification
2017</h3>2032</h3>
2018 2033
2019Viene eseguito quando Claude Code invia notifiche. Corrisponde al tipo di notifica: `permission_prompt`, `idle_prompt`, `auth_success`, `elicitation_dialog`, `elicitation_complete`, `elicitation_response`. Omettere il matcher per eseguire gli hook per tutti i tipi di notifica.2034Viene eseguito quando Claude Code invia notifiche. Corrisponde al tipo di notifica. Omettere il matcher per eseguire gli hook per tutti i tipi di notifica.
2035
2036| Matcher | Quando si attiva |
2037| :--------------------- | :--------------------------------------------------------------------------------------------------------------------------------------- |
2038| `permission_prompt` | Claude ha bisogno dell'approvazione di uno strumento |
2039| `idle_prompt` | Claude è terminato e in attesa del prompt successivo |
2040| `auth_success` | L'autenticazione è completata |
2041| `elicitation_dialog` | Un server MCP apre un modulo di elicitazione |
2042| `elicitation_complete` | Un modulo di elicitazione MCP viene inviato o chiuso |
2043| `elicitation_response` | Una risposta di elicitazione MCP viene inviata al server |
2044| `agent_needs_input` | Una sessione in background inizia ad attendere l'input. Si attiva solo mentre la [vista agente](/it/agent-view) è aperta in un terminale |
2045| `agent_completed` | Una sessione in background termina o non riesce. Si attiva solo mentre la [vista agente](/it/agent-view) è aperta in un terminale |
2046
2047I tipi `agent_needs_input` e `agent_completed` richiedono Claude Code v2.1.198 o successivo.
2020 2048
2021Utilizzare matcher separati per eseguire gestori diversi a seconda del tipo di notifica. Questa configurazione attiva uno script di avviso specifico per l'autorizzazione quando Claude ha bisogno dell'approvazione dell'autorizzazione e una notifica diversa quando Claude è stato inattivo:2049Utilizzare matcher separati per eseguire gestori diversi a seconda del tipo di notifica. Questa configurazione attiva uno script di avviso specifico per l'autorizzazione quando Claude ha bisogno dell'approvazione dell'autorizzazione e una notifica diversa quando Claude è stato inattivo:
2022 2050
2079 Input di SubagentStart2107 Input di SubagentStart
2080</h4>2108</h4>
2081 2109
2082Oltre ai [campi di input comuni](#common-input-fields), gli hook SubagentStart ricevono `agent_id` con l'identificatore univoco per il subagent e `agent_type` con il nome dell'agente (agenti incorporati come `"general-purpose"`, `"Explore"`, `"Plan"` o nomi di agenti personalizzati).2110Oltre ai [campi di input comuni](#common-input-fields), gli hook SubagentStart ricevono `agent_id` con l'identificatore univoco per il subagent e `agent_type` con il nome dell'agente che il matcher filtra.
2083 2111
2084```json theme={null}2112```json theme={null}
2085{2113{
2559Oltre ai [campi di output JSON](#json-output) disponibili per tutti gli hook, gli hook CwdChanged possono restituire `watchPaths` per impostare dinamicamente quali percorsi di file [FileChanged](#filechanged) monitora:2587Oltre ai [campi di output JSON](#json-output) disponibili per tutti gli hook, gli hook CwdChanged possono restituire `watchPaths` per impostare dinamicamente quali percorsi di file [FileChanged](#filechanged) monitora:
2560 2588
2561| Campo | Descrizione |2589| Campo | Descrizione |
2562| :----------- | :---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |2590| :----------- | :--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
2563| `watchPaths` | Array di percorsi assoluti. Sostituisce l'elenco di monitoraggio dinamico corrente (i percorsi dalla configurazione del `matcher` vengono sempre monitorati). Restituire un array vuoto cancella l'elenco dinamico, che è tipico quando si entra in una nuova directory |2591| `watchPaths` | Array di percorsi assoluti. Sostituisce l'elenco di monitoraggio dinamico corrente. I percorsi dalla configurazione del `matcher` vengono sempre monitorati. Restituire un array vuoto cancella l'elenco dinamico, che è tipico quando si entra in una nuova directory |
2564 2592
2565Gli hook CwdChanged non hanno controllo della decisione. Non possono bloccare il cambio di directory.2593Gli hook CwdChanged non hanno controllo della decisione. Non possono bloccare il cambio di directory.
2566 2594
2584Oltre ai [campi di input comuni](#common-input-fields), gli hook FileChanged ricevono `file_path` e `event`.2612Oltre ai [campi di input comuni](#common-input-fields), gli hook FileChanged ricevono `file_path` e `event`.
2585 2613
2586| Campo | Descrizione |2614| Campo | Descrizione |
2587| :---------- | :------------------------------------------------------------------------------------------------- |2615| :---------- | :---------------------------------------------------------------------------------------------------------------- |
2588| `file_path` | Percorso assoluto al file che è cambiato |2616| `file_path` | Percorso assoluto al file che è cambiato |
2589| `event` | Cosa è accaduto: `"change"` (file modificato), `"add"` (file creato) o `"unlink"` (file eliminato) |2617| `event` | Cosa è accaduto: `"change"` per un file modificato, `"add"` per un file creato o `"unlink"` per un file eliminato |
2590 2618
2591```json theme={null}2619```json theme={null}
2592{2620{
2606Oltre ai [campi di output JSON](#json-output) disponibili per tutti gli hook, gli hook FileChanged possono restituire `watchPaths` per aggiornare dinamicamente quali percorsi di file vengono monitorati:2634Oltre ai [campi di output JSON](#json-output) disponibili per tutti gli hook, gli hook FileChanged possono restituire `watchPaths` per aggiornare dinamicamente quali percorsi di file vengono monitorati:
2607 2635
2608| Campo | Descrizione |2636| Campo | Descrizione |
2609| :----------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |2637| :----------- | :----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
2610| `watchPaths` | Array di percorsi assoluti. Sostituisce l'elenco di monitoraggio dinamico corrente (i percorsi dalla configurazione del `matcher` vengono sempre monitorati). Utilizzare questo quando lo script del hook scopre file aggiuntivi da monitorare in base al file modificato |2638| `watchPaths` | Array di percorsi assoluti. Sostituisce l'elenco di monitoraggio dinamico corrente. I percorsi dalla configurazione del `matcher` vengono sempre monitorati. Utilizzare questo quando lo script del hook scopre file aggiuntivi da monitorare in base al file modificato |
2611 2639
2612Gli hook FileChanged non hanno controllo della decisione. Non possono bloccare il cambio di file dall'occorrenza.2640Gli hook FileChanged non hanno controllo della decisione. Non possono bloccare il cambio di file dall'occorrenza.
2613 2641
2615 WorktreeCreate2643 WorktreeCreate
2616</h3>2644</h3>
2617 2645
2618Quando si esegue `claude --worktree` o un [subagent utilizza `isolation: "worktree"`](/it/sub-agents#choose-the-subagent-scope), Claude Code crea una copia di lavoro isolata utilizzando `git worktree`. Se si configura un hook WorktreeCreate, sostituisce il comportamento git predefinito, consentendo di utilizzare un sistema di controllo della versione diverso come SVN, Perforce o Mercurial.2646Viene eseguito quando un worktree sta per essere creato, sia da `claude --worktree` che da un [subagent che utilizza `isolation: "worktree"`](/it/sub-agents#choose-the-subagent-scope). Per impostazione predefinita Claude Code crea la copia di lavoro isolata con `git worktree`. Configurando un hook WorktreeCreate si sostituisce quel comportamento git predefinito, consentendo di utilizzare un sistema di controllo della versione diverso come SVN, Perforce o Mercurial.
2619 2647
2620Poiché l'hook sostituisce completamente il comportamento predefinito, [`.worktreeinclude`](/it/worktrees#copy-gitignored-files-into-worktrees) non viene elaborato. Se è necessario copiare i file di configurazione locali come `.env` nel nuovo worktree, farlo all'interno dello script del hook.2648Poiché l'hook sostituisce completamente il comportamento predefinito, [`.worktreeinclude`](/it/worktrees#copy-gitignored-files-into-worktrees) non viene elaborato. Se è necessario copiare i file di configurazione locali come `.env` nel nuovo worktree, farlo all'interno dello script del hook.
2621 2649
2646 Input di WorktreeCreate2674 Input di WorktreeCreate
2647</h4>2675</h4>
2648 2676
2649Oltre ai [campi di input comuni](#common-input-fields), gli hook WorktreeCreate ricevono il campo `name`. Questo è un identificatore slug per il nuovo worktree, specificato dall'utente o generato automaticamente (ad esempio, `bold-oak-a3f2`).2677Oltre ai [campi di input comuni](#common-input-fields), gli hook WorktreeCreate ricevono il campo `name`. Questo è un identificatore slug per il nuovo worktree, specificato dall'utente o generato automaticamente, ad esempio `bold-oak-a3f2`.
2650 2678
2651```json theme={null}2679```json theme={null}
2652{2680{
2673 WorktreeRemove2701 WorktreeRemove
2674</h3>2702</h3>
2675 2703
2676La controparte di pulizia di [WorktreeCreate](#worktreecreate). Questo hook si attiva quando un worktree viene rimosso, sia quando si esce da una sessione `--worktree` e si sceglie di rimuoverla, sia quando un subagent con `isolation: "worktree"` termina. Per i worktree basati su git, Claude gestisce la pulizia automaticamente con `git worktree remove`. Se si è configurato un hook WorktreeCreate per un sistema di controllo della versione non-git, accoppiarlo con un hook WorktreeRemove per gestire la pulizia. Senza uno, la directory del worktree viene lasciata su disco.2704Viene eseguito quando un worktree sta per essere rimosso, sia quando si esce da una sessione `--worktree` e si sceglie di rimuoverla, sia quando un subagent con `isolation: "worktree"` termina. Questa è la controparte di pulizia di [WorktreeCreate](#worktreecreate).
2705
2706Per i worktree basati su git, Claude Code gestisce la pulizia automaticamente con `git worktree remove`. Se si è configurato un hook WorktreeCreate per un sistema di controllo della versione non-git, accoppiarlo con un hook WorktreeRemove per gestire la pulizia. Senza uno, la directory del worktree viene lasciata su disco.
2677 2707
2678Claude Code passa il percorso restituito da WorktreeCreate come `worktree_path` nell'input del hook. Questo esempio legge quel percorso e rimuove la directory:2708Claude Code passa il percorso restituito da WorktreeCreate come `worktree_path` nell'input del hook. Questo esempio legge quel percorso e rimuove la directory:
2679 2709
3062 3092
3063Se hai bisogno di un controllo più fine su qualsiasi evento, utilizza un [hook di comando](#command-hook-fields) con i campi per evento descritti in [Controllo delle decisioni](#decision-control).3093Se hai bisogno di un controllo più fine su qualsiasi evento, utilizza un [hook di comando](#command-hook-fields) con i campi per evento descritti in [Controllo delle decisioni](#decision-control).
3064 3094
3065<h3 id="example-multi-criteria-stop-hook">3095<h3 id="check-multiple-conditions-before-stopping">
3066 Esempio: Hook Stop con criteri multipli3096 Controllare più condizioni prima di fermarsi
3067</h3>3097</h3>
3068 3098
3069Questo hook `Stop` utilizza un prompt dettagliato per controllare tre condizioni prima di consentire a Claude di fermarsi. Se `"ok"` è `false`, Claude continua a lavorare con il motivo fornito come sua prossima istruzione. Gli hook `SubagentStop` utilizzano lo stesso formato per valutare se un [subagent](/it/sub-agents) dovrebbe fermarsi:3099Questo hook `Stop` utilizza un prompt dettagliato per controllare tre condizioni prima di consentire a Claude di fermarsi. Gli hook `SubagentStop` utilizzano lo stesso formato per valutare se un [subagent](/it/sub-agents) dovrebbe fermarsi. Se `"ok"` è `false`, Claude continua a lavorare con il motivo fornito come sua prossima istruzione:
3070 3100
3071```json theme={null}3101```json theme={null}
3072{3102{
3190 3220
3191Le notifiche di completamento degli hook asincroni sono soppresse per impostazione predefinita. Per vederle, abilitare la modalità verbose con `Ctrl+O` o avviare Claude Code con `--verbose`.3221Le notifiche di completamento degli hook asincroni sono soppresse per impostazione predefinita. Per vederle, abilitare la modalità verbose con `Ctrl+O` o avviare Claude Code con `--verbose`.
3192 3222
3193<h3 id="example-run-tests-after-file-changes">3223<h3 id="run-tests-after-file-changes">
3194 Esempio: eseguire i test dopo le modifiche ai file3224 Eseguire i test dopo le modifiche ai file
3195</h3>3225</h3>
3196 3226
3197Questo hook avvia una suite di test in background ogni volta che Claude scrive un file, quindi segnala i risultati a Claude quando i test terminano. Salvare questo script in `.claude/hooks/run-tests-async.sh` nel progetto e renderlo eseguibile con `chmod +x`:3227Questo hook avvia una suite di test in background ogni volta che Claude scrive un file, quindi segnala i risultati a Claude quando i test terminano. Salvare questo script in `.claude/hooks/run-tests-async.sh` nel progetto e renderlo eseguibile con `chmod +x`:
3285 Strumento Windows PowerShell3315 Strumento Windows PowerShell
3286</h2>3316</h2>
3287 3317
3288Su Windows, è possibile eseguire singoli hook in PowerShell impostando `"shell": "powershell"` su un command hook. Gli hook generano PowerShell direttamente, quindi questo funziona indipendentemente dal fatto che `CLAUDE_CODE_USE_POWERSHELL_TOOL` sia impostato. Claude Code rileva automaticamente `pwsh.exe` (PowerShell 7+) con un fallback a `powershell.exe` (5.1).3318Su Windows, è possibile eseguire singoli hook in PowerShell impostando `"shell": "powershell"` su un command hook. Gli hook generano PowerShell direttamente, quindi questo funziona indipendentemente dal fatto che `CLAUDE_CODE_USE_POWERSHELL_TOOL` sia impostato. Claude Code rileva automaticamente `pwsh.exe`, l'eseguibile di PowerShell 7 e versioni successive, e ricade su `powershell.exe` per Windows PowerShell 5.1.
3289 3319
3290```json theme={null}3320```json theme={null}
3291{3321{
3306}3336}
3307```3337```
3308 3338
3309Per fare riferimento alla directory radice del progetto da un comando in forma shell di PowerShell, leggerla come variabile di ambiente con `$env:CLAUDE_PROJECT_DIR`. PowerShell tratta la forma nuda `${CLAUDE_PROJECT_DIR}` come una variabile locale, non come una ricerca di ambiente, e Claude Code sostituisce quel segnaposto in forma shell solo per [hook di plugin](#reference-scripts-by-path). Per un hook definito in `settings.json`, utilizzare la forma `$env:` oppure passare a [forma exec](#exec-form-and-shell-form), dove `${CLAUDE_PROJECT_DIR}` viene sostituito in ogni elemento `args` indipendentemente da dove l'hook è definito.3339Per fare riferimento alla directory radice del progetto da un comando in forma shell di PowerShell, scrivere `${CLAUDE_PROJECT_DIR}` o `$env:CLAUDE_PROJECT_DIR`. A partire dalla v2.1.198, Claude Code riscrive i segnaposti `${CLAUDE_PROJECT_DIR}`, `${CLAUDE_PLUGIN_ROOT}` e `${CLAUDE_PLUGIN_DATA}` in un comando in forma shell di PowerShell nella forma `${env:NAME}` di PowerShell, indipendentemente dal fatto che l'hook sia definito in `settings.json`, un plugin o una skill. PowerShell quindi risolve il valore dall'ambiente esportato dopo l'analisi, quindi il segnaposto funziona all'interno di stringhe tra virgolette doppie ma non all'interno di stringhe tra virgolette singole, dove PowerShell non espande mai le variabili.
3340
3341Prima della v2.1.198, questa riscrittura si applicava solo agli hook dei plugin. Nelle versioni precedenti, un hook `settings.json` necessita della forma `$env:` o della [forma exec](#exec-form-and-shell-form), dove `${CLAUDE_PROJECT_DIR}` viene sostituito in ogni elemento `args` indipendentemente da dove l'hook è definito.
3342
3343Non scrivere la forma nuda `$CLAUDE_PROJECT_DIR` in un hook di PowerShell. PowerShell la analizza come una variabile locale non definita e la risolve in `$null`, il che lascia il percorso dello script senza il prefisso della directory radice del progetto. Claude Code non riscrive quella forma; invece registra un avviso nel [log di debug](#debug-hooks).
3310 3344
3311L'esempio seguente mostra un hook `settings.json` che esegue uno script di progetto con la forma `$env:`:3345L'esempio seguente mostra un hook `settings.json` che esegue uno script di progetto con la forma `$env:`, che funziona su ogni versione:
3312 3346
3313```json theme={null}3347```json theme={null}
3314{3348{