Creo applicazioni web moderne e strumenti digitali personalizzati per aiutare le attività a crescere attraverso l'innovazione tecnologica. La mia passione è unire informatica ed economia per generare valore reale.
La mia passione per l'informatica è nata tra i banchi dell'Istituto Tecnico Commerciale di Maglie, dove ho scoperto il potere della programmazione e il fascino di creare soluzioni digitali. Fin da subito, ho capito che l'informatica non era solo codice, ma uno strumento straordinario per trasformare idee in realtà.
Durante gli studi superiori in Sistemi Informativi Aziendali, ho iniziato a intrecciare informatica ed economia, comprendendo come la tecnologia possa essere il motore della crescita per qualsiasi attività. Questa visione mi ha accompagnato all'Università degli Studi di Bari, dove ho conseguito la Laurea in Informatica, approfondendo le mie competenze tecniche e la mia passione per lo sviluppo software.
Oggi metto questa esperienza al servizio di imprese, professionisti e startup, creando soluzioni digitali su misura che automatizzano processi, ottimizzano risorse e aprono nuove opportunità di business. Perché la vera innovazione inizia quando la tecnologia incontra le esigenze reali delle persone.
Le Mie Competenze
Analisi Dati & Modelli Previsionali
Trasformo i dati in insights strategici con analisi approfondite e modelli predittivi per decisioni informate
Automazione Processi
Creo strumenti personalizzati che automatizzano operazioni ripetitive e liberano tempo per attività a valore aggiunto
Sistemi Custom
Sviluppo sistemi software su misura, dalle integrazioni tra piattaforme alle dashboard personalizzate
Credo fermamente che l'informatica sia lo strumento più potente per trasformare le idee in realtà e migliorare la vita delle persone.
Democratizzare la Tecnologia
La mia missione è rendere l'informatica accessibile a tutti: dalle piccole imprese locali alle startup innovative, fino ai professionisti che vogliono digitalizzare la propria attività. Ogni realtà merita di sfruttare le potenzialità del digitale.
Unire Informatica ed Economia
Non è solo questione di scrivere codice: è capire come la tecnologia possa generare valore reale. Intrecciando competenze informatiche e visione economica, aiuto le attività a crescere, ottimizzare processi e raggiungere nuovi traguardi di efficienza e redditività.
Creare Soluzioni su Misura
Ogni attività è unica, e così devono esserlo le soluzioni. Sviluppo strumenti personalizzati che rispondono alle esigenze specifiche di ciascun cliente, automatizzando processi ripetitivi e liberando tempo per ciò che conta davvero: far crescere il business.
Trasforma la Tua Attività con la Tecnologia
Che tu gestisca un negozio, uno studio professionale o un'azienda, posso aiutarti a sfruttare le potenzialità dell'informatica per lavorare meglio, più velocemente e in modo più intelligente.
Il mio percorso accademico e le tecnologie che padroneggio
Certificazioni Professionali
8 certificazioni conseguite
Nuovo
Visualizza
Reinvention With Agentic AI Learning Program
Anthropic
Dicembre 2024
Nuovo
Visualizza
Agentic AI Fluency
Anthropic
Dicembre 2024
Nuovo
Visualizza
AI Fluency for Students
Anthropic
Dicembre 2024
Nuovo
Visualizza
AI Fluency: Framework and Foundations
Anthropic
Dicembre 2024
Nuovo
Visualizza
Claude with the Anthropic API
Anthropic
Dicembre 2024
Visualizza
Master SQL
RoadMap.sh
Novembre 2024
Visualizza
Oracle Certified Foundations Associate
Oracle
Ottobre 2024
Visualizza
People Leadership Credential
Connect
Settembre 2024
Linguaggi & Tecnologie
Java
Python
JavaScript
Angular
React
TypeScript
SQL
PHP
CSS/SCSS
Node.js
Docker
Git
💼
12/2024 - Presente
Custom Software Engineering Analyst
Accenture
Bari, Puglia, Italia · Ibrida
Analisi e sviluppo di sistemi informatici attraverso l'utilizzo di Java e Quarkus in Health and Public Sector. Formazione continua su tecnologie moderne per la creazione di soluzioni software personalizzate ed efficienti e sugli agenti.
💼
06/2022 - 12/2024
Analista software e Back End Developer Associate Consultant
Links Management and Technology SpA
Esperienza nell'analisi di sistemi software as-is e flussi ETL utilizzando PowerCenter. Formazione completata su Spring Boot per lo sviluppo di applicazioni backend moderne e scalabili. Sviluppatore Backend specializzato in Spring Boot, con esperienza in progettazione di database, analisi, sviluppo e testing dei task assegnati.
💼
02/2021 - 10/2021
Programmatore software
Adesso.it (prima era WebScience srl)
Esperienza nell'analisi AS-IS e TO-BE, evoluzioni SEO ed evoluzioni website per migliorare le performance e l'engagement degli utenti.
🎓
2018 - 2025
Laurea in Informatica
Università degli Studi di Bari Aldo Moro
Bachelor's degree in Computer Science, focusing on software engineering, algorithms, and modern development practices.
📚
2013 - 2018
Diploma - Sistemi Informativi Aziendali
Istituto Tecnico Commerciale di Maglie
Technical diploma specializing in Business Information Systems, combining IT knowledge with business management.
Contattami
Hai un progetto in mente? Parliamone! Compila il form qui sotto e ti risponderò al più presto.
* Campi obbligatori. I tuoi dati saranno utilizzati solo per rispondere alla tua richiesta.
Hooks: Automazione Event-Driven in Claude Code
Claude Code è uno strumento potente di per se, ma la sua vera forza emerge quando lo si estende
con un sistema di automazione event-driven: gli Hooks. Gli hooks sono comandi shell
che vengono eseguiti automaticamente in risposta a eventi specifici durante il ciclo di vita
di una sessione Claude Code, trasformando un assistente AI reattivo in un
sistema di sviluppo proattivo e personalizzato.
A differenza dei server MCP, che richiedono la creazione di processi separati e comunicazione
tramite protocolli strutturati, gli hooks operano come semplici script shell eseguiti
direttamente dal processo Claude Code. Questo li rende estremamente leggeri, veloci da
implementare e perfetti per automazioni che non necessitano della complessità di un server
dedicato. In questo articolo esploreremo in profondità ogni aspetto degli hooks: dalla
configurazione alla creazione di automazioni complesse, dai casi d'uso reali alle best
practice per un utilizzo efficace.
Cosa Imparerai
Comprendere il sistema di hooks event-driven di Claude Code
Configurare hooks nei file di settings JSON
Padroneggiare tutti e 6 gli eventi hook disponibili
Creare hooks personalizzati per automazioni complesse
Utilizzare hook di community come Britfix, CC Notify e cchooks
Gestire errori, performance e sicurezza negli hooks
Implementare pattern avanzati di comunicazione tra agenti
Applicare best practice per un ecosistema hooks robusto
Panoramica della Serie
#
Articolo
Focus
1
Claude come Partner Tecnico
Setup e primi passi
2
Contesto e Setup del Progetto
CLAUDE.md e configurazione
3
Ideazione e Requisiti
MVP e user personas
4
Architettura Backend e Frontend
Spring Boot e Angular
5
Struttura del Codice
Organizzazione e convenzioni
6
Prompt Engineering Avanzato
Tecniche avanzate
7
Testing e qualità
Strategie e generazione test
8
Documentazione Professionale
README, API, ADR
9
Deploy e DevOps
Docker, CI/CD, monitoring
10
Evoluzione e Manutenzione
Refactoring e scalabilità
11
Integrazione Progetto Reale
Claude Code in produzione
12
CLI Avanzata e Comandi
Padronanza della riga di comando
13
Custom Slash Commands e Skills
Estendere Claude Code
14
Sub-Agenti e Delegazione
Orchestrare agenti specializzati
15
Hooks: Automazione Event-Driven (sei qui)
Automazione basata su eventi
16
Ralph Wiggum: Loop AI Autonomi
Sviluppo autonomo iterativo
17
BMAD Method: Sviluppo Agile AI
Metodologia agile AI-driven
18
Orchestrazione Multi-Agente
Coordinare team di agenti
19
Collaborazione e Coworking AI
Lavorare insieme a Claude
20
Sicurezza e Permessi
Proteggere il workflow
21
Monitoring e Ottimizzazione
Metriche e performance
1. Cosa Sono gli Hooks di Claude Code
Gli hooks di Claude Code sono comandi shell definiti dall'utente che vengono
eseguiti automaticamente in corrispondenza di eventi specifici durante una sessione.
Funzionano in modo analogo ai git hooks o ai lifecycle hooks dei framework di sviluppo:
si agganciano a momenti chiave del flusso di lavoro e permettono di iniettare logica
personalizzata senza modificare il comportamento core dell'agente.
La filosofia alla base degli hooks è semplice ma potente: anziche richiedere a Claude
di eseguire azioni tramite prompt (che l'agente potrebbe interpretare in modo diverso
dal previsto), gli hooks garantiscono un'esecuzione deterministica e affidabile.
Il comando viene eseguito esattamente come definito, ogni volta, senza variazioni
o interpretazioni creative.
Hooks vs MCP Servers: Quando Usare Cosa
Caratteristica
Hooks
MCP Servers
Complessità
Bassa - script shell
Alta - processo separato
Latenza
Minima - esecuzione diretta
Maggiore - comunicazione IPC
Controllo modello
No - l'LLM non decide
Si - l'LLM sceglie quando usarli
Determinismo
Totale - sempre eseguiti
Parziale - dipende dal contesto
Configurazione
JSON in settings.json
Server dedicato con SDK
Casi d'uso
Automazioni, notifiche, validazioni
Strumenti complessi, integrazioni API
Sicurezza
Esecuzione locale controllata
Permessi granulari per tool
Architettura del Sistema Hooks
Il sistema hooks si inserisce nel ciclo di esecuzione di Claude Code come un layer
di intercettazione trasparente. Ogni volta che si verifica un evento supportato,
Claude Code verifica se esistono hooks configurati per quell'evento, prepara il
contesto sotto forma di input JSON tramite stdin, esegue il comando shell specificato
e processa l'output per determinare eventuali modifiche al flusso.
Gli hooks ricevono input strutturato in formato JSON tramite stdin e possono
restituire output JSON tramite stdout per influenzare il comportamento
dell'agente. Questo approccio basato su stream consente la composizione di pipeline
di elaborazione complesse mantenendo un'interfaccia semplice e universale.
Gli hooks vengono configurati nel file .claude/settings.json all'interno
della directory del progetto o nella configurazione globale dell'utente
(~/.claude/settings.json). La struttura di configurazione è un oggetto JSON
che mappa eventi a liste di hook, dove ogni hook specifica il comando da eseguire
e opzionalmente un matcher per filtrare su quali strumenti o condizioni attivare l'hook.
Pattern regex per filtrare l'attivazione. Supporta pipe per OR logico.
command
string
Si
Comando shell da eseguire. Può essere un percorso assoluto o relativo.
timeout
number
No
Timeout in millisecondi. Default: 60000 (60 secondi).
Il campo matcher è particolarmente potente perchè supporta espressioni regolari
complete. Questo significa che si possono creare hook che rispondono solo a specifici
strumenti o combinazioni di strumenti, mantenendo il sistema reattivo e performante.
Esempi di Matcher Avanzati
// Singolo tool
"matcher": "Write"
// Multipli tool con OR
"matcher": "Write|Edit|MultiEdit"
// Pattern regex complesso
"matcher": "^(Bash|Terminal)$"
// Tutti i tool (nessun matcher = wildcard)
// Omettere il campo matcher
// Tool che iniziano con "File"
"matcher": "^File.*"
// Escludere specifici tool (negazione regex)
"matcher": "^(?!Read).*$"
Livelli di Configurazione
Claude Code supporta tre livelli gerarchici di configurazione per gli hooks,
permettendo di definire automazioni a diversi livelli di granularità:
Progetto (.claude/settings.json): Hooks specifici per il repository corrente. Ideali per automazioni legate al progetto come linting, formattazione o notifiche di team.
Utente (~/.claude/settings.json): Hooks globali che si applicano a tutte le sessioni dell'utente. Perfetti per preferenze personali come notifiche desktop o logging.
Enterprise (/etc/claude/settings.json): Hooks a livello di organizzazione. Usati per policy aziendali come audit logging o compliance checks.
Quando esistono hooks a più livelli per lo stesso evento, vengono eseguiti tutti in
ordine di precedenza: prima enterprise, poi utente, infine progetto. Questo garantisce
che le policy aziendali vengano sempre rispettate, indipendentemente dalle configurazioni
locali.
3. I 6 Eventi Hook in Dettaglio
Claude Code espone sei eventi distinti a cui è possibile agganciare hooks. Ogni evento
corrisponde a un momento preciso nel ciclo di vita di una sessione e fornisce un contesto
specifico tramite l'input JSON. Comprendere ogni evento in profondità è fondamentale
per progettare automazioni efficaci e robuste.
3.1 PreToolUse: Intercettare Prima dell'Esecuzione
L'evento PreToolUse si attiva prima che Claude Code esegua
qualsiasi strumento. E' il punto di intercettazione più potente perchè consente di
ispezionare, modificare o bloccare l'esecuzione di uno strumento
prima che produca effetti nel sistema.
Input JSON per PreToolUse
Campo
Tipo
Descrizione
tool_name
string
Nome dello strumento (es. "Write", "Bash", "Edit")
tool_input
object
Parametri passati allo strumento
session_id
string
Identificativo univoco della sessione
L'hook può restituire un JSON di output con tre possibili decisioni:
"decision": "allow" - Permette l'esecuzione dello strumento senza modifiche
"decision": "block" - Blocca completamente l'esecuzione. Richiede un campo reason con la motivazione.
"decision": "modify" - Modifica i parametri dello strumento prima dell'esecuzione. Richiede un campo tool_input con i parametri aggiornati.
#!/bin/bash
# Hook PreToolUse: blocca operazioni su file protetti
INPUT=$(cat)
TOOL_NAME=$(echo "$INPUT" | jq -r '.tool_name')
TOOL_INPUT=$(echo "$INPUT" | jq -r '.tool_input')
# Blocca scrittura su file di configurazione critica
if [ "$TOOL_NAME" = "Write" ] || [ "$TOOL_NAME" = "Edit" ]; then
FILE_PATH=$(echo "$TOOL_INPUT" | jq -r '.file_path // .path // ""')
# Lista file protetti
PROTECTED_FILES=(".env" ".env.production" "secrets.json" "credentials.yaml")
for PROTECTED in "
#123;PROTECTED_FILES[@]}"; do
if [[ "$FILE_PATH" == *"$PROTECTED"* ]]; then
echo "{\"decision\": \"block\", \"reason\": \"File protetto: $PROTECTED. Modifica manuale richiesta.\"}"
exit 0
fi
done
fi
# Blocca comandi Bash distruttivi
if [ "$TOOL_NAME" = "Bash" ]; then
COMMAND=$(echo "$TOOL_INPUT" | jq -r '.command // ""')
# Pattern pericolosi
if echo "$COMMAND" | grep -qE "rm\s+-rf\s+/|DROP\s+TABLE|DELETE\s+FROM.*WHERE\s+1=1|format\s+c:"; then
echo "{\"decision\": \"block\", \"reason\": \"Comando potenzialmente distruttivo bloccato.\"}"
exit 0
fi
fi
# Permettere tutto il resto
echo '{"decision": "allow"}'
auto-format.sh - Modificare parametri prima dell'esecuzione
#!/bin/bash
# Hook PreToolUse: aggiunge automaticamente header ai nuovi file
INPUT=$(cat)
TOOL_NAME=$(echo "$INPUT" | jq -r '.tool_name')
if [ "$TOOL_NAME" = "Write" ]; then
FILE_PATH=$(echo "$INPUT" | jq -r '.tool_input.file_path')
CONTENT=$(echo "$INPUT" | jq -r '.tool_input.content')
# Aggiungi header copyright ai file TypeScript
if [[ "$FILE_PATH" == *.ts ]]; then
HEADER="// Copyright $(date +%Y) - MyCompany\n// Auto-generated header by Claude Code hook\n\n"
MODIFIED_CONTENT="#123;HEADER}#123;CONTENT}"
echo "$INPUT" | jq --arg content "$MODIFIED_CONTENT" \
'{decision: "modify", tool_input: (.tool_input + {content: $content})}'
exit 0
fi
fi
echo '{"decision": "allow"}'
3.2 PostToolUse: Reagire Dopo l'Esecuzione
L'evento PostToolUse si attiva dopo che uno strumento ha completato
la sua esecuzione. E' il punto ideale per logging, validazione dei risultati,
trasformazione dell'output e azioni consequenti basate sul risultato dell'operazione.
A differenza di PreToolUse, PostToolUse non può bloccare o modificare l'operazione
(che e già avvenuta), ma può influenzare il modo in cui Claude interpreta il risultato
e può eseguire azioni collaterali come aggiornare log, inviare notifiche o attivare
pipeline esterne.
Input JSON per PostToolUse
Campo
Tipo
Descrizione
tool_name
string
Nome dello strumento eseguito
tool_input
object
Parametri usati per l'esecuzione
tool_output
string
Risultato dello strumento
session_id
string
Identificativo della sessione
post-tool-logger.py - Logging strutturato delle operazioni
#!/usr/bin/env python3
"""Hook PostToolUse: logga tutte le operazioni di scrittura file."""
import json
import sys
from datetime import datetime
from pathlib import Path
def main():
input_data = json.loads(sys.stdin.read())
tool_name = input_data.get("tool_name", "")
tool_input = input_data.get("tool_input", {})
session_id = input_data.get("session_id", "unknown")
# Logga solo operazioni di modifica file
if tool_name in ("Write", "Edit", "MultiEdit"):
log_entry = {
"timestamp": datetime.now().isoformat(),
"session_id": session_id,
"tool": tool_name,
"file": tool_input.get("file_path", "N/A"),
"operation": "write" if tool_name == "Write" else "edit"
}
log_file = Path(".claude/hooks/activity.log")
log_file.parent.mkdir(parents=True, exist_ok=True)
with open(log_file, "a") as f:
f.write(json.dumps(log_entry) + "\n")
# Logga comandi Bash eseguiti
if tool_name == "Bash":
command = tool_input.get("command", "")
log_entry = {
"timestamp": datetime.now().isoformat(),
"session_id": session_id,
"tool": "Bash",
"command": command[:200], # Tronca per sicurezza
"exit_code": "success"
}
log_file = Path(".claude/hooks/bash-history.log")
log_file.parent.mkdir(parents=True, exist_ok=True)
with open(log_file, "a") as f:
f.write(json.dumps(log_entry) + "\n")
if __name__ == "__main__":
main()
3.3 UserPromptSubmit: Intercettare i Prompt Utente
L'evento UserPromptSubmit si attiva quando l'utente invia un prompt
a Claude Code. Questo hook permette di pre-processare, arricchire o filtrare
i messaggi dell'utente prima che raggiungano il modello. E' particolarmente utile per
aggiungere contesto automatico, applicare template di prompt o implementare filtri
di sicurezza sui messaggi in ingresso.
enrich-prompt.sh - Arricchire i prompt con contesto
L'evento Stop si attiva quando Claude Code termina di generare una
risposta o completa un task. E' il punto ideale per notifiche, cleanup,
generazione di report e qualsiasi azione che debba avvenire al termine
di un'interazione. Questo hook è particolarmente prezioso per task lunghi dove
l'utente potrebbe non essere davanti al terminale.
notify-complete.sh - Notifica desktop al completamento
#!/bin/bash
# Hook Stop: invia notifica desktop quando Claude completa
INPUT=$(cat)
STOP_REASON=$(echo "$INPUT" | jq -r '.stop_reason // "completed"')
# Notifica su Linux (notify-send)
if command -v notify-send &> /dev/null; then
notify-send "Claude Code" "Task completato: $STOP_REASON" \
--icon=dialog-information \
--urgency=normal
fi
# Notifica su macOS (osascript)
if command -v osascript &> /dev/null; then
osascript -e "display notification \"Task completato: $STOP_REASON\" with title \"Claude Code\""
fi
# Suono di completamento
if command -v aplay &> /dev/null; then
aplay /usr/share/sounds/freedesktop/stereo/complete.oga 2>/dev/null &
elif command -v afplay &> /dev/null; then
afplay /System/Library/Sounds/Glass.aiff &
fi
3.5 SessionStart: Inizializzazione della Sessione
L'evento SessionStart si attiva all'inizio di ogni nuova sessione
Claude Code. E' il momento ideale per setup dell'ambiente, caricamento di contesto
aggiuntivo, validazione dei prerequisiti e preparazione delle risorse necessarie
per la sessione di lavoro.
session-init.sh - Setup ambiente alla partenza
#!/bin/bash
# Hook SessionStart: prepara l'ambiente di sviluppo
# Verifica prerequisiti
echo "Verificando ambiente di sviluppo..." >&2
# Controlla che Node.js sia disponibile
if ! command -v node &> /dev/null; then
echo '{"warning": "Node.js non trovato. Alcune funzionalità potrebbero non funzionare."}' >&2
fi
# Controlla che il database di sviluppo sia raggiungibile
if command -v pg_isready &> /dev/null; then
if ! pg_isready -q 2>/dev/null; then
echo '{"warning": "PostgreSQL non raggiungibile. Avviare il database."}' >&2
fi
fi
# Carica variabili d'ambiente dal .env
if [ -f ".env" ]; then
export $(grep -v '^#' .env | xargs) 2>/dev/null
fi
# Registra inizio sessione
echo "{\"session_start\": \"$(date -Iseconds)\", \"cwd\": \"$(pwd)\"}" \
>> .claude/hooks/sessions.log 2>/dev/null
# Pulisci file temporanei di sessioni precedenti
find /tmp -name "claude-hook-*" -mtime +1 -delete 2>/dev/null
3.6 SessionEnd: Cleanup e Report Finale
L'evento SessionEnd si attiva alla chiusura di una sessione Claude Code.
E' il punto perfetto per salvare lo stato, generare report di sessione,
eseguire cleanup e archiviare informazioni utili per sessioni future.
session-report.py - Report automatico di fine sessione
#!/usr/bin/env python3
"""Hook SessionEnd: genera un report della sessione di lavoro."""
import json
import sys
from datetime import datetime
from pathlib import Path
def main():
input_data = json.loads(sys.stdin.read())
session_id = input_data.get("session_id", "unknown")
# Leggi il log delle attivita
log_file = Path(".claude/hooks/activity.log")
activities = []
if log_file.exists():
with open(log_file) as f:
for line in f:
try:
entry = json.loads(line.strip())
if entry.get("session_id") == session_id:
activities.append(entry)
except json.JSONDecodeError:
continue
# Genera report
report = {
"session_id": session_id,
"end_time": datetime.now().isoformat(),
"total_operations": len(activities),
"files_modified": list(set(
a.get("file", "") for a in activities
if a.get("tool") in ("Write", "Edit", "MultiEdit")
)),
"bash_commands": sum(
1 for a in activities if a.get("tool") == "Bash"
)
}
# Salva report
reports_dir = Path(".claude/hooks/reports")
reports_dir.mkdir(parents=True, exist_ok=True)
report_file = reports_dir / f"session-{session_id[:8]}.json"
with open(report_file, "w") as f:
json.dump(report, f, indent=2)
print(f"Report sessione salvato: {report_file}", file=sys.stderr)
if __name__ == "__main__":
main()
Riepilogo Eventi Hook
Evento
Quando si Attiva
Può Bloccare?
Può Modificare?
PreToolUse
Prima dell'esecuzione di un tool
Si
Si (parametri tool)
PostToolUse
Dopo l'esecuzione di un tool
No
No (solo side effects)
UserPromptSubmit
Quando l'utente invia un prompt
Si
Si (testo prompt)
Stop
Quando Claude finisce di generare
No
No
SessionStart
All'inizio di una nuova sessione
No
No
SessionEnd
Alla chiusura della sessione
No
No
4. Hook della Community: Soluzioni Pronte all'Uso
La community di Claude Code ha sviluppato una serie di hook sofisticati che risolvono
esigenze comuni degli sviluppatori. Questi progetti open-source dimostrano la versatilita
del sistema hooks e possono essere utilizzati direttamente o come base per personalizzazioni.
4.1 Britfix: Conversione Automatica Inglese Americano-Britannico
Britfix è un hook PostToolUse che converte automaticamente l'ortografia
inglese americana in ortografia britannica nei file scritti da Claude Code. E' stato
creato per team che lavorano con standard britannici ma utilizzano un modello AI
addestrato prevalentemente su testi americani.
L'hook intercetta ogni operazione di scrittura file, analizza il contenuto per parole
con ortografia americana (come "color", "optimize", "center") e le sostituisce con
le varianti britanniche ("colour", "optimise", "centre"). Il processo è trasparente
e non richiede alcun intervento manuale.
CC Notify è un sistema di notifiche desktop avanzato che va oltre
la semplice notifica di completamento. Supporta notifiche differenziate per tipo
di evento, storico delle notifiche, integrazione con sistemi di messaggistica
(Slack, Discord, Telegram) e configurazione granulare per tipo di attivita.
Una funzionalità particolarmente utile di CC Notify è la capacità di stimare il tempo
rimanente per task lunghi basandosi sullo storico delle sessioni precedenti, permettendo
all'utente di pianificare il proprio tempo in modo più efficace mentre Claude Code
lavora in background.
cchooks è un SDK Python che semplifica drasticamente la creazione
di hook complessi. Invece di scrivere script shell con parsing JSON manuale, cchooks
fornisce decoratori Python tipizzati, gestione automatica dell'input/output e una
libreria di utilita per operazioni comuni.
Hook con cchooks SDK
#!/usr/bin/env python3
"""Hook creato con cchooks SDK."""
from cchooks import hook, PreToolUseInput, HookDecision
@hook("PreToolUse")
def validate_file_size(event: PreToolUseInput) -> HookDecision:
"""Blocca la scrittura di file troppo grandi."""
if event.tool_name == "Write":
content = event.tool_input.get("content", "")
max_lines = 500
if content.count("\n") > max_lines:
return HookDecision.block(
reason=f"File troppo grande: {content.count(chr(10))} righe "
f"(max {max_lines}). Suddividi in file più piccoli."
)
return HookDecision.allow()
@hook("PostToolUse")
def auto_lint(event):
"""Esegue linting automatico dopo ogni modifica file."""
import subprocess
if event.tool_name in ("Write", "Edit"):
file_path = event.tool_input.get("file_path", "")
if file_path.endswith(".ts") or file_path.endswith(".js"):
subprocess.run(
["npx", "eslint", "--fix", file_path],
capture_output=True, timeout=30
)
elif file_path.endswith(".py"):
subprocess.run(
["python3", "-m", "black", file_path],
capture_output=True, timeout=30
)
4.4 Claude Code Hook Comms: Comunicazione Real-Time tra Agenti
Claude Code Hook Comms abilita la comunicazione in tempo reale tra
più istanze di Claude Code che lavorano sullo stesso progetto o su progetti correlati.
Utilizza un sistema di messaggistica basato su file condivisi o socket per coordinare
le attivita di agenti multipli, evitando conflitti e duplicazioni di lavoro.
Questo hook è particolarmente utile in scenari di sviluppo multi-agente dove diversi
Claude Code lavorano su aspetti diversi di un progetto (ad esempio frontend e backend)
e devono sincronizzarsi su modifiche alle interfacce condivise.
Creare hook personalizzati richiede la comprensione del formato di input/output,
la scelta del linguaggio di scripting appropriato e l'attenzione a robustezza ed
efficienza. Questa sezione fornisce un percorso completo dalla creazione alla
messa in produzione di hook professionali.
Step 1: Definire l'Obiettivo
Prima di scrivere codice, è essenziale definire chiaramente cosa deve fare l'hook:
Quale evento? Identificare il momento esatto in cui l'hook deve intervenire
Quale azione? Definire cosa deve fare (bloccare, modificare, loggare, notificare)
Quali condizioni? Specificare quando l'hook deve attivarsi (matcher)
Quale impatto? Valutare le conseguenze dell'hook sul workflow
Il testing degli hook è fondamentale perchè errori nello script possono bloccare
o rallentare l'intera sessione Claude Code. Ecco un approccio strutturato al testing:
Oltre all'uso base, gli hooks possono essere combinati in pattern sofisticati
che risolvono esigenze complesse di automazione. Questa sezione presenta alcuni
dei pattern più utili emersi dall'esperienza della community.
Pattern: Auto-Commit su Checkpoint
Questo pattern crea automaticamente commit Git a intervalli regolari durante
una sessione di sviluppo, garantendo che il lavoro non venga mai perso e
fornendo punti di rollback granulari.
auto-checkpoint.sh - Commit automatici
#!/bin/bash
# Hook PostToolUse: crea checkpoint automatici
INPUT=$(cat)
TOOL_NAME=$(echo "$INPUT" | jq -r '.tool_name')
# Solo per operazioni di modifica file
if [ "$TOOL_NAME" = "Write" ] || [ "$TOOL_NAME" = "Edit" ]; then
FILE_PATH=$(echo "$INPUT" | jq -r '.tool_input.file_path // ""')
# Controlla se ci sono abbastanza modifiche per un checkpoint
CHANGES=$(git diff --stat 2>/dev/null | tail -1)
NUM_FILES=$(git diff --name-only 2>/dev/null | wc -l)
if [ "$NUM_FILES" -ge 3 ]; then
git add -A 2>/dev/null
git commit -m "checkpoint: auto-save dopo $NUM_FILES file modificati" \
--no-verify 2>/dev/null
echo "[CHECKPOINT] Commit automatico: $NUM_FILES file" >&2
fi
fi
Pattern: Quality Gate Pre-Commit
Questo pattern esegue automaticamente controlli di qualità (linting, type checking,
test unitari) prima di permettere operazioni di scrittura, assicurando che ogni
modifica rispetti gli standard del progetto.
quality-gate.sh - Controlli qualità automatici
#!/bin/bash
# Hook PreToolUse: quality gate per file TypeScript
INPUT=$(cat)
TOOL_NAME=$(echo "$INPUT" | jq -r '.tool_name')
if [ "$TOOL_NAME" = "Write" ]; then
FILE_PATH=$(echo "$INPUT" | jq -r '.tool_input.file_path')
CONTENT=$(echo "$INPUT" | jq -r '.tool_input.content')
if [[ "$FILE_PATH" == *.ts ]]; then
# Scrivi il contenuto in un file temporaneo per analisi
TEMP_FILE=$(mktemp /tmp/claude-hook-XXXXXX.ts)
echo "$CONTENT" > "$TEMP_FILE"
# Esegui type checking
ERRORS=$(npx tsc --noEmit --strict "$TEMP_FILE" 2>&1 || true)
rm -f "$TEMP_FILE"
if echo "$ERRORS" | grep -q "error TS"; then
ERROR_COUNT=$(echo "$ERRORS" | grep -c "error TS")
echo "{\"decision\": \"block\", \"reason\": \"Type check fallito: $ERROR_COUNT errori TypeScript trovati. Correggi prima di scrivere.\"}"
exit 0
fi
fi
fi
echo '{"decision": "allow"}'
Pattern: Context Enrichment Pipeline
Questo pattern arricchisce automaticamente ogni prompt dell'utente con informazioni
contestuali rilevanti, come lo stato del repository, i file modificati di recente,
i test falliti e le metriche di progetto.
context-pipeline.sh - Arricchimento contestuale
#!/bin/bash
# Hook UserPromptSubmit: pipeline di arricchimento contesto
INPUT=$(cat)
PROMPT=$(echo "$INPUT" | jq -r '.prompt')
# Raccogli contesto
CONTEXT_PARTS=()
# 1. Stato Git
BRANCH=$(git rev-parse --abbrev-ref HEAD 2>/dev/null)
if [ -n "$BRANCH" ]; then
DIRTY=$(git status --porcelain 2>/dev/null | wc -l)
CONTEXT_PARTS+=("[Branch: $BRANCH, File modificati: $DIRTY]")
fi
# 2. Test falliti recenti
if [ -f "test-results.json" ]; then
FAILED=$(jq '.numFailedTests // 0' test-results.json 2>/dev/null)
if [ "$FAILED" -gt 0 ]; then
CONTEXT_PARTS+=("[WARNING: $FAILED test falliti]")
fi
fi
# 3. TODO in sospeso
TODO_COUNT=$(grep -r "TODO\|FIXME\|HACK" src/ --include="*.ts" 2>/dev/null | wc -l)
if [ "$TODO_COUNT" -gt 0 ]; then
CONTEXT_PARTS+=("[TODO aperti nel codice: $TODO_COUNT]")
fi
# Costruisci contesto aggregato
if [ #123;#CONTEXT_PARTS[@]} -gt 0 ]; then
CONTEXT=$(printf "%s " "#123;CONTEXT_PARTS[@]}")
ENRICHED="$CONTEXT\n\n$PROMPT"
echo "$INPUT" | jq --arg p "$ENRICHED" '{decision: "modify", prompt: $p}'
else
echo '{"decision": "allow"}'
fi
7. Performance, Sicurezza e Best Practice
Gli hooks vengono eseguiti in modo sincrono nel ciclo di vita di Claude Code,
il che significa che hook lenti o malfunzionanti possono degradare significativamente
l'esperienza utente. Seguire le best practice di performance e sicurezza è essenziale
per mantenere un workflow fluido e protetto.
Ottimizzazione delle Performance
Regole d'Oro per Hook Performanti
Regola
Motivazione
Implementazione
Timeout aggressivi
Evitare blocchi della sessione
Impostare timeout a 5-10 secondi per hook critici
Matcher specifici
Ridurre esecuzioni non necessarie
Usare regex precise invece di wildcard
Operazioni async
Non bloccare per I/O lento
Delegare operazioni pesanti a processi background
Cache locale
Evitare ricalcoli costosi
Salvare risultati intermedi in file temporanei
Early exit
Minimizzare tempo di esecuzione
Controllare condizioni di uscita all'inizio dello script
Logging controllato
Evitare I/O disco eccessivo
Usare log rotation e livelli di severita
Sicurezza degli Hooks
Gli hooks eseguono comandi shell con i permessi dell'utente corrente, il che
rappresenta sia un vantaggio (pieno accesso al sistema) che un rischio (esecuzione
non controllata). E' fondamentale applicare principi di sicurezza rigorosi:
Principio del minimo privilegio: Ogni hook dovrebbe avere accesso solo alle risorse strettamente necessarie per il suo funzionamento
Validazione input: Tutti i dati ricevuti tramite stdin devono essere validati e sanitizzati prima dell'uso
Nessun segreto hardcoded: API key, password e token non devono mai essere inclusi direttamente negli script hook
Audit trail: Mantenere un log di tutte le azioni eseguite dagli hooks per tracciabilita
Review periodica: Rivedere regolarmente gli hook configurati per identificare rischi emergenti
Attenzione: Rischi di Sicurezza
Gli hooks di progetto (definiti in .claude/settings.json) vengono eseguiti
automaticamente quando si apre una sessione Claude Code nel repository. Questo significa
che un repository malevolo potrebbe includere hook dannosi. Verificare sempre
i file di configurazione prima di aprire sessioni in repository non fidati.
Gestione Errori
Un hook che fallisce silenziosamente è peggiore di un hook che non esiste. Implementare
una gestione degli errori robusta è fondamentale per la manutenibilità del sistema:
robust-hook.sh - Hook con gestione errori completa
#!/bin/bash
set -euo pipefail
# Trap per gestire errori e cleanup
cleanup() {
local exit_code=$?
if [ $exit_code -ne 0 ]; then
echo "[HOOK ERROR] Exit code: $exit_code" >&2
echo "{\"error\": \"Hook fallito con codice $exit_code\"}" >&2
fi
# Cleanup risorse temporanee
rm -f /tmp/claude-hook-$.tmp 2>/dev/null
}
trap cleanup EXIT
# Timeout per l'intero script
TIMEOUT=10
(
sleep $TIMEOUT
echo "[HOOK TIMEOUT] Script superato $TIMEOUT secondi" >&2
kill $ 2>/dev/null
) &
TIMEOUT_PID=$!
# Logica principale con error handling
INPUT=$(cat) || {
echo '{"decision": "allow"}' # Fallback sicuro
exit 0
}
TOOL_NAME=$(echo "$INPUT" | jq -r '.tool_name // ""' 2>/dev/null) || TOOL_NAME=""
# ... logica del hook ...
# Cancella il timer di timeout
kill $TIMEOUT_PID 2>/dev/null || true
echo '{"decision": "allow"}'
8. Esempio Completo: Ecosistema Hooks per un Progetto Angular
Per concludere, presentiamo un esempio completo di ecosistema hooks configurato
per un progetto Angular con SSR, coprendo tutti e sei gli eventi e dimostrando
come gli hooks collaborano per creare un ambiente di sviluppo robusto e automatizzato.