Quattro estensioni, quattro meccanismi diversi

Prima dei tradeoff serve una distinzione che la parola «built-in» nasconde: i tool già pronti sono di due specie. I server tool girano sull’infrastruttura di Anthropic — la panoramica sul tool use cita web_search, web_fetch, code_execution e tool_search — e non richiedono handler nella tua applicazione: nella risposta trovi il blocco server_tool_use, con id che inizia per srvtoolu_, e appaiato per tool_use_id il suo risultato. I client tool con schema Anthropic (bash, text editor, memory, computer use, browser use) hanno lo schema pubblicato e il modello addestrato su di esso, ma l’esecuzione resta tua: la risposta arriva con stop_reason pari a tool_use e devi rispedire un tool_result, come per un tool tuo.

La conseguenza pratica è che «integrato» non vuol dire «già gestito». Se ti serve la ricerca web non ricostruirla: è un server tool, paghi token più tariffa d’uso e non scrivi codice. Se ti serve una shell, il tool bash ti regala schema e addestramento del modello, ma sandbox, permessi e timeout restano tuoi. Un caso ibrido da conoscere: se Claude chiama un server tool insieme a un tuo tool nello stesso gruppo parallelo, il server tool viene eseguito solo quando gli rimandi i tool_result.

Tool custom: pochi, larghi, descritti bene

Un tool tuo è name, description, input_schema, più opzionali come input_examples, strict e defer_loading. La leva vera è la descrizione, e la documentazione è netta: «This is by far the most important factor in tool performance», con l’indicazione di almeno tre o quattro frasi per tool, incluse quelle su quando NON usarlo.

Il modo tipico di sbagliare è la mappatura uno a uno degli endpoint REST. «A common error we’ve observed is tools that merely wrap existing software functionality or API endpoints», scrive Writing tools for agents, e l’esempio è esplicito: invece di list_users, list_events e create_event, un solo schedule_event che trova la disponibilità e crea l’evento. Consolida le operazioni affini, dai un prefisso di servizio ai nomi (github_list_prs, slack_send_message) e restituisci solo informazione ad alto segnale, con paginazione o troncamento sulle risposte grosse. Ogni definizione occupa contesto: oltre la ventina di tool la documentazione consiglia il tool search, che tiene gli schemi fuori dal contesto finché Claude non li chiede, al prezzo di un turno in più.

Skill: procedura, non nuova capacità

Una Skill è una cartella con un SKILL.md e un frontmatter YAML che richiede name e description. Il meccanismo è la progressive disclosure su tre livelli: i metadati stanno sempre in contesto (circa 100 token per Skill), il corpo entra solo quando la descrizione combacia con la richiesta, i file allegati costano zero finché non vengono letti e di uno script entra in contesto solo l’output. È il motivo per cui «until a Skill is triggered, only its name and description occupy context» e puoi installarne molte senza pagare pegno.

Qui si annida l’errore concettuale: una Skill non apre una porta verso un sistema esterno, descrive come si fa una cosa e si appoggia all’ambiente di esecuzione che già hai. Sull’API richiede il code execution tool, con lo skill_id nel parametro container, e quel container non ha accesso di rete né installazione di pacchetti a runtime: una Skill che deve chiamare la tua API interna lì non funziona. In Claude Code vive in ~/.claude/skills/ o .claude/skills/ e ha la rete della macchina. Le Skill non si sincronizzano fra superfici: quella caricata su claude.ai va caricata di nuovo sull’API.

MCP: una integrazione, molti client

MCP è il protocollo aperto per collegare Claude a tool, database e API di terzi. Dalla Messages API si usa il connector: definisci il server in mcp_servers e nel parametro tools metti un mcp_toolset che lo referenzia. I limiti dichiarati contano nella scelta: sono supportate solo le tool call del protocollo, e «Local STDIO servers cannot be connected directly» — serve un server esposto su HTTPS. Il connector è in beta, non è ZDR-eligible, e il token OAuth lo ottieni e lo rinnovi tu, passandolo come authorization_token.

Il filtro dei tool è la parte che si dimentica: un server con quaranta tool li scarica tutti nel tuo contesto. Usa default_config con enabled a false e abilita solo quelli che servono, oppure disabilita quelli distruttivi.

{
  "type": "mcp_toolset",
  "mcp_server_name": "google-calendar-mcp",
  "default_config": { "enabled": false },
  "configs": { "search_events": { "enabled": true } }
}

In Claude Code lo stesso protocollo arriva anche in locale via stdio, con scope local, project (il file .mcp.json versionato) o user, e i tool compaiono come mcp__server__tool. Vale in entrambi i casi l’avvertenza: «Verify you trust each server before connecting it».

La regola di scelta

Anthropic lo esegue già?             -> server tool, non riscriverlo
Serve solo alla tua applicazione?    -> custom tool nel parametro tools
Serve a più client diversi?          -> server MCP, poi connector o Claude Code
Claude può farlo ma sbaglia il come? -> Skill

Le due domande che risolvono i casi ambigui: chi esegue il codice e chi paga il contesto. Un MCP usato per iniettare istruzioni è una Skill travestita e ti costa un round trip di rete; una Skill usata per raggiungere un sistema esterno è un tool mancante. E vale per tutte e quattro la disciplina che la documentazione impone alle Skill — «Use Skills only from trusted sources» — perché istruzioni e codice di terzi girano con i permessi del tuo agente.