Comprendere l’utilizzo dei token
Gli SDK TypeScript e Python espongono gli stessi dati di utilizzo con nomi di campi diversi:- TypeScript fornisce suddivisioni dei token per fase su ogni messaggio dell’assistente (
message.message.id,message.message.usage), costo per modello tramitemodelUsagesul messaggio risultato, e un totale cumulativo sul messaggio risultato. - Python fornisce suddivisioni dei token per fase su ogni messaggio dell’assistente come
message.usageemessage.message_id, costo per modello tramitemodel_usagesul messaggio risultato, e il totale cumulativo sul messaggio risultato cometotal_cost_usd.
- Chiamata
query(): una singola invocazione della funzionequery()dell’SDK. Una singola chiamata può coinvolgere più fasi: Claude risponde, utilizza strumenti, ottiene risultati e risponde di nuovo. Ogni chiamata produce un messaggioresultalla fine, tranne in modalità input streaming, dove una chiamataquery()comporta più turni dell’utente e ogni turno emette il proprio messaggioresult. - Fase: un singolo ciclo richiesta/risposta all’interno di una chiamata
query(). Ogni fase produce messaggi dell’assistente con utilizzo dei token. - Sessione: una serie di chiamate
query()collegate da un ID di sessione tramite l’opzioneresume. I risultati di una chiamata ripresa segnalano la spesa totale della sessione, non solo quella della chiamata stessa. Vedere Accumulare i costi su più chiamate per come i totali si trasferiscono.
query(), con l’utilizzo dei token segnalato ad ogni fase e la stima cumulativa alla fine:
1
Ogni fase produce messaggi dell'assistente
Quando Claude risponde, invia uno o più messaggi dell’assistente. In TypeScript, ogni messaggio dell’assistente contiene un
BetaMessage annidato (accessibile tramite message.message) con un id e un oggetto usage con conteggi dei token (input_tokens, output_tokens). In Python, la dataclass AssistantMessage espone gli stessi dati direttamente tramite message.usage e message.message_id. Quando Claude utilizza più strumenti in un turno, tutti i messaggi in quel turno condividono lo stesso ID, quindi deduplicare per ID per evitare il doppio conteggio.2
Il messaggio risultato fornisce la stima cumulativa
Quando la chiamata
query() si completa, l’SDK emette un messaggio risultato con total_cost_usd e usage cumulativo, tipizzato come SDKResultMessage in TypeScript e ResultMessage in Python. Se è necessario solo il totale stimato, è possibile ignorare l’utilizzo per fase e leggere questo singolo valore.Se si effettuano più chiamate query() indipendenti, ogni risultato riflette solo il costo di quella singola chiamata. Una chiamata che riprende una sessione conta anche la spesa precedente della sessione.In modalità input streaming, ogni turno emette il proprio messaggio risultato. Vedere Tracciare i costi in modalità input streaming per come leggere i totali delle chiamate in quella modalità.Tracciare i costi in modalità di input in streaming
In modalità di input in streaming, una singola chiamataquery() contiene più turni utente e ogni turno emette il proprio messaggio di risultato. I campi del risultato differiscono in ambito:
usage: copre solo quel turno, e all’interno di esso solo il ciclo principale dell’agente, non eventuali subagenti che ha eseguito.total_cost_usdemodelUsage, omodel_usagein Python: portano il totale cumulativo per l’intera chiamata fino a quel momento, più qualsiasi spesa ripristinata quando la chiamata ha ripreso una sessione.
/clear, /reset, o /new, leggete il risultato più recente per i totali della chiamata piuttosto che sommare i risultati.
I totali cumulativi ricominciamo ogni volta che la vostra app invia uno di questi tre comandi, e all’interno di una chiamata query() nient’altro li ripristina. Tre risultati sono importanti per la vostra contabilità:
- Il risultato del turno
/clear: copre solo ciò che è stato eseguito dal ripristino, e porta un nuovosession_id. - Ogni risultato successivo: continua a contare da quel ripristino.
- L’ultimo risultato prima di ogni
/clear: contiene il totale per i turni dal ripristino precedente.
/clear al risultato finale della chiamata. Ogni altro risultato, incluso quello del turno /clear, è sostituito da uno successivo.
In TypeScript, l’SDK emette anche un SDKConversationResetMessage ad ogni ripristino, quindi potete rilevare i ripristini dal flusso. In Python, l’SDK emette analogamente un ConversationResetMessage. Prima della versione Python SDK v0.2.137, l’iteratore Python ha eliminato quel messaggio, quindi su quelle versioni contate i ripristini voi stessi dai turni /clear che la vostra app invia.
maxBudgetUsd (TypeScript) o max_budget_usd (Python) conta solo la spesa della chiamata stessa: i totali ripristinati da una sessione ripresa non contano rispetto ad esso, e un /clear avvia il budget da capo.
Ottenere il costo totale di una query
Il messaggio di risultato, tipizzato comeSDKResultMessage in TypeScript e ResultMessage in Python, segna la fine del ciclo dell’agente per una chiamata query(). Include total_cost_usd, il costo stimato cumulativo su tutti i passaggi in quella chiamata. Una chiamata che riprende una sessione conta anche la spesa precedente della sessione. Due avvertenze si applicano quando leggete il valore:
- In Python il campo è tipizzato come opzionale, quindi verificate che non sia
Noneprima di leggerlo. - I risultati di successo e di errore lo portano entrambi, anche se il risultato finale di un crash della sessione potrebbe portarlo azzerato.
modelUsage, o model_usage in Python, per la contabilità dei token dell’intero albero; il campo usage sottoconta non appena si verifica l’annidamento.
In modalità di input a messaggio singolo, quando i subagenti in background sono ancora in esecuzione alla fine del turno finale, Claude Code li attende, fino al limite descritto in background tasks at exit, prima di emettere il risultato. Il
total_cost_usd, duration_api_ms e modelUsage del risultato, o model_usage in Python, includono il lavoro svolto durante l’attesa.
I seguenti esempi iterano sul flusso di messaggi da una chiamata query() e stampano il costo totale quando arriva il messaggio result:
total_cost_usd, impostate i limiti di profondità, concorrenza e spesa sulla query.
Tracciare l’utilizzo per step e per modello
Gli esempi in questa sezione utilizzano nomi di campi TypeScript. In Python, i campi equivalenti sonoAssistantMessage.usage e AssistantMessage.message_id per l’utilizzo per step, e ResultMessage.model_usage per i dettagli per modello.
Tracciare l’utilizzo per step
Ogni messaggio dell’assistente contiene unBetaMessage annidato (accessibile tramite message.message) con un id e un oggetto usage con i conteggi dei token. Quando Claude utilizza gli strumenti in parallelo, più messaggi condividono lo stesso id con dati di utilizzo identici. Tenere traccia degli ID che hai già contato e saltare i duplicati per evitare totali gonfiati.
L’esempio seguente accumula i token di input in tutti gli step, contando ogni ID di messaggio del loop principale univoco una sola volta e saltando i messaggi dei subagent, e legge il totale di output dal messaggio di risultato, che copre il loop principale:
Dettagliare l’utilizzo per modello
Il messaggio di risultato includemodelUsage, una mappa del nome del modello ai conteggi dei token per modello e al costo. Questo è utile quando esegui più modelli (ad esempio, Haiku per i subagent e Opus per l’agente principale) e desideri vedere dove vanno i token.
Il costBasis di ogni voce indica quale tabella dei prezzi ha determinato il prezzo della richiesta più recente di quel modello: list per il prezzo di listino, managed per una tabella modelPricing, o unknown quando nessuno dei due corrisponde all’ID del modello. Il campo richiede Claude Code v2.1.246 o successivo.
L’esempio seguente esegue una query e stampa il costo e il dettaglio dei token per ogni modello utilizzato:
Accumulare i costi su più chiamate
Ogni chiamataquery() restituisce total_cost_usd sui suoi risultati. Come combinare i valori dipende dal fatto che le chiamate condividano una sessione:
- Chiamate indipendenti, senza opzione
resumeocontinue: ogni risultato copre solo la propria chiamata, quindi aggiungete i totali voi stessi, come fanno gli esempi seguenti. - Chiamate che riprendono la stessa sessione: Claude Code salva i totali della sessione nel suo transcript quando il processo esce normalmente e li ripristina quando una chiamata successiva riprende o effettua il fork della sessione. Ogni risultato include già la spesa precedente della sessione. Leggete l’ultimo risultato per il totale della sessione; sommare i risultati conta due volte la spesa ripristinata. Prima della v2.1.277, una sessione che avevate ripreso tramite l’SDK o
claude -piniziava i suoi totali a zero, quindi i risultati di ogni chiamata coprivano solo quella chiamata.
query() in sequenza, aggiungono il total_cost_usd di ogni chiamata a un totale progressivo e stampano sia il costo per singola chiamata che il costo combinato:
Gestire errori, caching e conteggi dei token di output
Per un tracciamento accurato dei costi, tenere conto del conteggio di output segnaposto sui messaggi dell’assistente, dei token che una conversazione non riuscita ha consumato e dei prezzi dei token della cache.Leggere i token di output dal messaggio di risultato
Claude Code costruisce ogni messaggio dell’assistente dall’utilizzo che l’API ha segnalato quando la risposta è iniziata, quindi iloutput_tokens del messaggio è solo il conteggio che l’API aveva segnalato a message_start, prima che la risposta fosse generata. Una risposta API può produrre diversi messaggi dell’assistente, e ognuno di essi porta lo stesso segnaposto.
L’API segnala il conteggio di output reale alla fine della risposta, e Claude Code lo aggiunge al messaggio di risultato. Leggere i token di output dal usage del risultato, o da modelUsage per una suddivisione per modello.
Per osservare il conteggio di output di una risposta crescere mentre viene trasmesso in streaming, impostare includePartialMessages, o include_partial_messages in Python, e leggere usage da ogni evento di flusso message_delta, tipizzato come SDKPartialAssistantMessage in TypeScript e StreamEvent in Python.
Tracciare i costi su conversazioni non riuscite
Sia i messaggi di risultato di successo che di errore includonousage e total_cost_usd; in Python entrambi i campi sono tipizzati come opzionali, quindi verificare che non siano None prima di leggerli.
Se una conversazione non riesce a metà strada, hai comunque consumato token fino al punto del fallimento. Leggere i dati di costo da ogni messaggio di risultato, indipendentemente dal fatto che il suo subtype sia success o uno dei sottotipi di errore. Su alcuni risultati di errore, usage segnala meno di quanto la chiamata ha speso:
error_during_executiondopo un arresto anomalo della sessione: ogni campo di costo può essere azzerato.error_max_budget_usd:usageomette la risposta che ha superato il budget, mentretotal_cost_usdemodelUsagela includono.
total_cost_usd o modelUsage piuttosto che da usage.
Recuperare i totali dopo un arresto anomalo della sessione
Quando il processo Claude Code si arresta in modo anomalo, emette un risultatoerror_during_execution finale e esce, sia in modalità input single-shot che in streaming. Quel risultato può portare usage, total_cost_usd e modelUsage azzerati, quindi recuperare i totali della chiamata da ciò che è arrivato prima. Il passaggio 1 recupera i totali completi ogni volta che esiste un risultato precedente; il fallback nel passaggio 2 recupera solo i token di input e cache del ciclo principale.
- Utilizzare il risultato del turno prima dell’arresto anomalo. In modalità input streaming, contiene il totale in esecuzione descritto in Track costs in streaming input mode. Passare al passaggio 2 invece quando quel risultato non può aiutarti:
- La chiamata era single-shot, quindi non esiste alcun risultato precedente.
- L’arresto anomalo è avvenuto al primo turno.
- Il turno prima dell’arresto anomalo era il
/clearstesso, quindi il suo risultato copre solo il ripristino.
- Sommare invece il
usagesui messaggi dell’assistente, contando ogni risposta API una volta, come fa l’esempio Track per-step usage. In modalità single-shot, sommare tutti; in modalità input streaming, sommare quelli arrivati dopo l’ultimo risultato. Questo ti dà i token di input e cache del ciclo principale. L’utilizzo dei subagent non è recuperabile in questo modo, e nemmeno i token di output o il costo in USD, perché iloutput_tokensper passaggio è un segnaposto.
Tracciare i token della cache
L’Agent SDK utilizza automaticamente prompt caching per ridurre i costi su contenuti ripetuti. Non è necessario configurare il caching da soli. L’oggetto usage include due campi aggiuntivi per il tracciamento della cache:cache_creation_input_tokens: token utilizzati per creare nuove voci della cache (addebitati a una tariffa più alta rispetto ai token di input standard).cache_read_input_tokens: token letti da voci della cache esistenti (addebitati a una tariffa ridotta).
input_tokens per comprendere i risparmi della cache. In TypeScript, questi campi sono tipizzati sull’oggetto Usage. In Python, appaiono come chiavi nel dizionario ResultMessage.usage (ad esempio, message.usage.get("cache_read_input_tokens", 0)).
Estendere il TTL della cache del prompt a un’ora
I tuoi turni rientrano nel bucket TTL della conversazione principale, insieme ai helper che Claude Code esegue inline con essi. Le richieste che Claude Code effettua al di fuori di quella conversazione, come i subagent, hanno un controllo TTL separato. Le voci della cache per i tuoi turni utilizzano un TTL di 5 minuti per impostazione predefinita quando ti autentichi con una chiave API o esegui su Amazon Bedrock, Agent Platform di Google Cloud, Microsoft Foundry, o Claude Platform on AWS. Se il tuo carico di lavoro esegue molte sessioni brevi rispetto allo stesso prompt di sistema e contesto con gap più lunghi di 5 minuti tra di essi, la cache scade tra le sessioni e ogni nuova sessione paga il prezzo di input completo. Per richiedere un TTL di 1 ora sulle scritture della cache, impostare la variabile di ambienteENABLE_PROMPT_CACHING_1H. Puoi esportarla nel tuo ambiente shell o container, o passarla attraverso options.env.
L’esempio seguente abilita il TTL di 1 ora per un agente in esecuzione su Amazon Bedrock. Poiché imposta CLAUDE_CODE_USE_BEDROCK, richiede credenziali AWS funzionanti per Amazon Bedrock; senza di esse la query non riesce.
ENABLE_PROMPT_CACHING_1H richiede il TTL di 1 ora su ogni richiesta in entrambi i bucket. Per scegliere un TTL per ogni bucket separatamente, utilizza invece questi controlli. Ognuno accetta 5m o 1h e ha la precedenza su ENABLE_PROMPT_CACHING_1H:
- Conversazione principale: la variabile di ambiente
CLAUDE_CODE_PROMPT_CACHE_TTL, o l’impostazionepromptCacheTtl - Tutto il resto: la variabile di ambiente
CLAUDE_CODE_SUBAGENT_PROMPT_CACHE_TTL, o l’impostazionesubagentPromptCacheTtl
promptCacheTtl a 1h mantiene la cache di 1 ora sulla conversazione principale mentre stai attingendo ai crediti di utilizzo. Per l’ordine di precedenza completo, vedi choose the TTL yourself.
Documentazione correlata
- Riferimento TypeScript SDK - Documentazione API completa
- Panoramica SDK - Introduzione all’SDK
- Autorizzazioni SDK - Gestione delle autorizzazioni degli strumenti