Ho visto questa scena ripetersi in almeno una dozzina di centri direzionali tra Milano e Roma: un team di sviluppatori senior che fissa un monitor alle tre del mattino, cercando di capire perché il database è piantato mentre i costi del cloud schizzano alle stelle. Il colpevole è quasi sempre lo stesso. Hanno configurato il monitoraggio pensando che bastasse attivare un interruttore nel portale, ma ora si ritrovano sommersi da gigabyte di telemetria inutile che non spiega il motivo per cui una procedura memorizzata sta rallentando l'intero ecosistema. In questo caos, tentare un approccio App Insight Azure Find SP Execution senza una strategia di campionamento precisa e senza conoscere le dipendenze sottostanti è il modo più veloce per bruciare il budget annuale in un solo trimestre. Non è solo un problema di performance tecniche; è un buco nero finanziario che nasce dall'idea sbagliata che "più dati abbiamo, meglio è".
Il disastro del monitoraggio a tappeto con App Insight Azure Find SP Execution
L'errore più comune che ho incontrato nelle consulenze è la cieca fiducia nella configurazione predefinita. Molti tecnici credono che abilitando la raccolta automatica delle dipendenze SQL, Azure catturi magicamente ogni dettaglio utile. Non funziona così. Quando provi a eseguire un processo di App Insight Azure Find SP Execution su un'istanza SQL carica, il sistema inizia a generare una quantità di log spaventosa. Ogni singola chiamata, anche quella da pochi millisecondi, viene registrata, impacchettata e spedita via rete.
Cosa succede nella realtà? La banda passante viene saturata, i tempi di risposta delle applicazioni aumentano a causa dell'overhead di tracciamento e la fattura di fine mese presenta voci per l'ingestion dei dati che superano il costo dei server stessi. Ho lavorato con un'azienda di logistica che pagava 4.000 euro al mese solo per i log di una singola applicazione perché non avevano filtrato le chiamate alle procedure memorizzate più frequenti e insignificanti. La soluzione non è spegnere il monitoraggio, ma passare a un modello basato sull'eccezione e sul valore. Devi configurare i filtri tramite codice (TelemetryProcessors) per scartare tutto ciò che rientra nei parametri di normalità. Se una procedura memorizzata risponde costantemente in 50ms, non ti serve vederla nel portale diecimila volte all'ora. Ti serve vederla solo quando schizza a 500ms o quando fallisce.
Credere che il portale mostri la verità assoluta sulle procedure memorizzate
Un altro sbaglio che vedo fare spesso riguarda l'interpretazione dei grafici di durata. Il portale di monitoraggio ti mostra che una procedura memorizzata ha impiegato 10 secondi, e tu corri a ottimizzare il codice SQL. Passi tre giorni a riscrivere indici e join, ma la durata non cala. Perché? Perché non stai guardando il tempo di rete o il tempo di attesa nel pool di connessioni.
Il problema del tempo nascosto
Spesso il ritardo non è nel database, ma nel modo in cui l'applicazione gestisce la connessione. Se il tuo pool è saturo, la telemetria registrerà una durata elevata perché il cronometro parte quando l'app richiede l'esecuzione, non quando il SQL Server la riceve effettivamente. Ho visto team distruggere piani di esecuzione perfettamente validi solo perché non sapevano leggere la differenza tra duration e network latency all'interno delle proprietà della dipendenza.
La trappola dei parametri mancanti
Per impostazione predefinita, per motivi di sicurezza e privacy (GDPR docet), i parametri di input delle procedure memorizzate non vengono registrati. Cercare di diagnosticare un problema senza sapere quali valori hanno scatenato il rallentamento è come cercare un ago in un pagliaio al buio. Devi implementare manualmente l'arricchimento della telemetria, catturando i parametri solo per le chiamate che superano una certa soglia di tempo, assicurandoti però di offuscare i dati sensibili. Se non lo fai, avrai solo una lista di nomi di procedure lente senza alcuna possibilità di riprodurre il bug localmente.
Ignorare la correlazione tra i livelli dell'architettura
Molti professionisti trattano l'analisi dell'esecuzione come un silos isolato. Guardano la sezione "Performance" e filtrano per "Dependency", isolando la procedura incriminata. Questo è l'errore che ti fa perdere ore dietro a falsi positivi. Un'esecuzione lenta di una procedura spesso è solo l'effetto domino di un problema che nasce altrove, magari in un microservizio che sta effettuando troppe chiamate simultanee (il classico problema N+1).
Se non utilizzi correttamente l'Operation Id per legare la richiesta HTTP iniziale a tutte le chiamate SQL figlie, non capirai mai il contesto. Ho assistito a situazioni in cui una procedura memorizzata sembrava lentissima, ma analizzando l'intera transazione è emerso che il problema era un blocco (lock) causato da un'altra operazione asincrona che nessuno stava monitorando. Senza correlazione, stai solo guardando dei fotogrammi sparsi di un film, sperando di indovinare la trama. La potenza dello strumento risiede nella capacità di ricostruire l'intera catena di eventi, dal click dell'utente sul browser fino all'ultimo byte scritto su disco dal database.
Configurazione errata del campionamento e perdita di dati vitali
Il campionamento è un'arma a doppio taglio. Se lo imposti troppo aggressivo sul lato server (Adaptive Sampling), rischi di perdere proprio quei rari picchi di latenza che stavi cercando di catturare. Se non lo imposti affatto, i costi ti manderanno in bancarotta. La maggior parte delle persone lascia l'Adaptive Sampling attivo e pensa di essere a posto. Poi, quando succede un disastro in produzione, aprono i log e scoprono che i dati di quel minuto specifico sono stati scartati perché il sistema ha deciso che c'era troppo traffico.
La strategia corretta, che ho applicato con successo in sistemi ad alto traffico, consiste nell'usare il campionamento a quota fissa per i dati di successo e il campionamento allo 100% per gli errori e le dipendenze lente. Devi scrivere un modulo personalizzato che dice al sistema: "Se questa operazione ha impiegato più di 2 secondi o ha restituito un errore, non osare scartarla". In questo modo mantieni il controllo dei costi senza sacrificare la visibilità nei momenti critici. Ricorda che un log mancante durante un crash è molto più costoso di qualche euro risparmiato nell'archiviazione dei dati.
Confronto tra un approccio ingenuo e uno professionale
Vediamo come cambia la gestione di un problema reale tra chi usa gli strumenti superficialmente e chi sa dove mettere le mani. Immaginiamo un sistema di e-commerce durante il Black Friday dove il checkout diventa improvvisamente lento.
L'approccio sbagliato si basa sull'aprire il portale, vedere un picco di latenza generale e iniziare a riavviare i servizi sperando in un miglioramento. Il tecnico guarda la tabella delle dipendenze, vede che sp_UpdateInventory impiega 5 secondi di media e conclude che il database è sotto carico. Chiede un upgrade dell'istanza SQL (costo immediato raddoppiato) ma la latenza rimane. Non ha dati sui parametri, non sa quali utenti sono impattati e non vede che il problema è un deadlock causato da un processo di reportistica partito per errore nello stesso momento.
L'approccio corretto invece parte da una telemetria arricchita. Il professionista filtra per la procedura specifica e nota immediatamente, grazie alle proprietà personalizzate aggiunte, che il rallentamento avviene solo per i magazzini situati in una specifica regione. Controlla la correlazione e vede che ogni chiamata a sp_UpdateInventory è preceduta da una chiamata esterna verso un fornitore di spedizioni che sta rispondendo con un timeout di 5 secondi. Il database non c'entra nulla; è l'applicazione che tiene aperta la transazione SQL mentre aspetta una risposta lenta dal web service esterno. Risultato: il problema viene risolto cambiando un timeout nel codice dell'app in 10 minuti, senza spendere un centesimo in hardware inutile.
Analisi superficiale dei dati di App Insight Azure Find SP Execution
Quando si arriva al punto di dover effettivamente fare un debug profondo, molti si fermano alla superficie dei grafici a torta. Il vero valore è nascosto nel linguaggio KQL (Kusto Query Language). Se non sai scrivere una query per incrociare la tabella dependencies con la tabella requests, non stai davvero facendo un'analisi seria.
Ho visto persone passare ore a cliccare filtri nell'interfaccia grafica, quando una query KQL di dieci righe avrebbe isolato il problema in trenta secondi. Devi imparare a estrarre i percentili (P50, P95, P99). La media è bugiarda; se hai nove chiamate da 10ms e una da 10 secondi, la media ti dirà che tutto va bene (circa 1 secondo), ma il tuo utente decimo avrà un'esperienza terribile. Solo analizzando il novantanovesimo percentile capirai quanto è grave il problema di performance. Inoltre, devi monitorare il tasso di fallimento delle dipendenze rispetto al volume totale. Un aumento dell'1% nei fallimenti di una procedura memorizzata potrebbe sembrare trascurabile, ma se quella procedura gestisce i pagamenti, hai appena perso decine di vendite.
Gestione dei costi e ritenzione dei dati senza senso
L'ultimo errore fatale riguarda la conservazione dei dati. Azure ti permette di conservare i log per anni, ma ti fa pagare per ogni giorno extra. Molte aziende tengono tutto per 90 o 180 giorni "per sicurezza", senza rendersi conto che per il debug delle performance delle procedure memorizzate, i dati più vecchi di 14 giorni sono quasi sempre inutili. Le performance del database cambiano con il cambiare del volume dei dati e del codice; guardare come girava una query tre mesi fa non ti aiuta a risolvere il problema di oggi.
Configura una politica di ritenzione breve (30 giorni sono solitamente più che sufficienti) e, se proprio devi conservare i dati per scopi legali o di audit, esportali su uno storage account molto più economico tramite un Continuous Export o un Logic App. Non lasciare che i log di monitoraggio diventino la voce di spesa più alta della tua infrastruttura cloud. Ho visto progetti fallire o essere pesantemente ridimensionati solo perché nessuno aveva controllato i costi di archiviazione di Log Analytics per sei mesi.
- Controlla i limiti di ingestion giornalieri per evitare sorprese in fattura.
- Implementa avvisi (alerts) basati su metriche, non su log, perché costano meno e sono più veloci.
- Rivedi periodicamente quali proprietà personalizzate stai inviando; dati inutili occupano spazio e rendono le query più lente.
- Assicurati che il team di sviluppo sappia effettivamente leggere i dati prodotti, altrimenti stai solo collezionando rumore digitale.
Controllo della realtà
Smettiamola di raccontarci che il monitoraggio cloud sia un processo "imposta e dimentica". La verità è che avere successo con l'analisi delle prestazioni richiede una manutenzione costante e una comprensione profonda di come i dati fluiscono tra i sistemi. Se pensi che basti guardare i grafici colorati del portale per gestire un'infrastruttura critica, sei destinato a fallire non appena si presenterà un problema non banale.
Non esiste una configurazione magica che funzioni per tutti. Dovrai sporcarti le mani con il codice, scrivere query KQL complesse e, soprattutto, dovrai avere il coraggio di scartare il 90% dei dati che raccogli per concentrarti su quel 10% che conta davvero. La tecnologia non risolverà i tuoi problemi di architettura; può solo evidenziarli, spesso in modo molto costoso. Il successo qui si misura in quanto velocemente riesci a ignorare il rumore per trovare il segnale, e questo richiede competenza tecnica reale, non solo la capacità di navigare in una dashboard di Azure. Se non sei disposto a investire tempo nel capire come la tua applicazione interroga il database a livello granulare, allora stai solo aspettando il prossimo crash per scoprire quanto poco sai del tuo sistema.