Vuoi sapere perché una query PostgreSQL è lenta? Allora EXPLAIN ANALYZE è un ottimo punto di partenza. Ma i piani di query possono dipendere da altre attività del server, possono richiedere del tempo per l'esecuzione e possono cambiare nel tempo, quindi se vuoi vedere i piani di esecuzione effettivi delle tue query più lente, auto_explain è lo strumento di cui hai bisogno. In questo post, esamineremo cosa fa, come configurarlo e come utilizzare quei log per velocizzare le tue query.
Cos'è auto_explain?
auto_explain è un'estensione PostgreSQL che consente di registrare i piani di query per query più lente di una soglia (configurabile). Ciò è incredibilmente utile per il debug di query lente, in particolare quelle che solo a volte sono problematiche. È uno dei moduli di contribuzione, quindi può essere installato e configurato facilmente su PostgreSQL normale ed è così utile che lo abbiamo attivato per impostazione predefinita su ScaleGrid.
Grazie infinite a Takahiro Itagaki, l'autore principale dietro la prima versione di auto_explain (commit, thread), Dean Rasheed, su cui si basava la patch iniziale e il suggerimento, e i molti collaboratori e revisori da allora.
Quali parametri auto_explain devo usare?
Di seguito discuteremo i parametri più importanti, ma per favore consulta la tabella qui sotto, o la documentazione ufficiale, per maggiori informazioni sulla gamma completa di cose che puoi monitorare.
Il parametro più importante per auto_explain è log_min_duration
. Per impostazione predefinita, è impostato su -1
, il che significa che non verrà registrato nulla, quindi se vogliamo alcuni registri dobbiamo cambiarlo! L'unità predefinita è ms, quindi un'impostazione di 100
registrerà i piani di query per tutte le query che superano i 100 ms. Questo è ciò che abbiamo scelto come predefinito in ScaleGrid, ma può essere configurato in Admin -> Config. Se, per qualche motivo, desideri registrare il piano di query per ogni query, puoi impostarlo su 0
– ma attenzione, ciò può avere gravi implicazioni sulle prestazioni.
Dato che le query sono già in esecuzione sul server, probabilmente vorrai anche abilitare auto_explain.log_analyze
. Questo rende l'output equivalente all'esecuzione di EXPLAIN ANALYZE
. Per impostazione predefinita, significa anche che vengono tracciati i tempi per operazione. Ciò comporta un sovraccarico aggiuntivo, che può essere ridotto al minimo disattivando auto_explain.log_timing
(attivo per impostazione predefinita con log_analyze
). Naturalmente, tuttavia, i tempi per operazione sono molto utili durante il debug di query lente! I nostri test interni hanno mostrato costi generali accettabili per questo, quindi è attivo per impostazione predefinita in ScaleGrid, ma come sempre testa il tuo carico di lavoro per vedere se il sovraccarico è accettabile nel tuo caso. Al momento le informazioni disponibili pubblicamente su questo argomento sono limitate, ma un recente post del team di pgMustard ha mostrato che, almeno su un piccolo carico di lavoro transazionale, l'overhead può arrivare fino al 2%. Come hanno notato, questo potrebbe essere ridotto con auto_explain.sample_rate
parametro, al costo di tracciare solo un sottoinsieme delle tue query.
L'ultimo parametro di cui parleremo un po' in dettaglio è auto_explain.log_format
. L'output predefinito è TESTO, che è probabilmente quello con cui hai più familiarità dall'utilizzo di EXPLAIN
.
Ecco un semplice esempio di come può apparire l'output di auto_explain in formato TEXT:
2021-09-10 15:32:04.606 BST [22770] LOG: duration: 3184.383 ms plan: Query Text: select * from table1 order by column1; Sort (cost=12875.92..13125.92 rows=100000 width=37) (actual time=2703.799..3055.401 rows=100000 loops=1) Sort Key: column1 Sort Method: external merge Disk: 4696kB Buffers: shared hit=837, temp read=587 written=589 -> Seq Scan on table (cost=0.00..1834.01 rows=100000 width=37) (actual time=0.033..27.795 rows=100000 loops=1) Buffers: shared hit=834
Puoi vedere qui che ottieni la durata della query all'inizio, che potresti essere abituato a vedere alla fine dei piani di query di solito. Vedrai anche il testo della query, inclusi eventuali parametri.
I popolari strumenti di visualizzazione describe.depesz e describe.dalibo accettano entrambi piani di query in formato TEXT, ma supportano entrambi anche il formato JSON. Se alcuni membri del tuo team preferiscono utilizzare strumenti come PEV e pgMustard, che supportano solo il formato JSON, potresti voler impostarlo come formato. Per i clienti su ScaleGrid abbiamo optato per il formato JSON, in parte perché volevamo analizzarlo più facilmente per la nostra funzione di analisi delle query lente.
Ecco un elenco completo dei parametri auto_explain e le loro impostazioni predefinite:
Parametro | Impostazioni predefinite di PostgreSQL | Impostazioni predefinite ScaleGrid |
---|---|---|
auto_explain.log_min_duration | -1 | 100 |
auto_explain.log_analyze | Off | Attivo |
auto_explain.log_timing | Attivo (con log_analyze) | Attivo |
auto_explain.log_buffers | Off | Attivo |
auto_explain.log_verbose | Off | Attivo |
auto_explain.log_triggers | Off | Off |
auto_explain.log_nested_statements | Off | Off |
auto_explain.log_settings (v12) | Off | Off |
auto_explain.log_wal (v13) | Off | Off |
auto_explain.log_format | TESTO | JSON |
auto_explain.log_level | LOG | LOG |
auto_explain.sample_rate | 1 | 1 |
Installazione di auto_explain
Su ScaleGrid, auto_explain è attivo per impostazione predefinita, con una soglia di 100 ms. Puoi configurarlo in Admin -> Config.
Su vanilla PostgreSQL, puoi installare auto_explain semplicemente aggiungendolo a una delle session_preload_libraries
o shared_preload_libraries
. Il primo ha i vantaggi di a) non richiedere un riavvio (ma verrà caricato solo nelle nuove sessioni) e b) renderlo possibile solo per alcuni utenti (impostando questo parametro con ALTER ROLE SET
).
In quanto tale, una configurazione di base per auto_explain potrebbe assomigliare a questa:
session_preload_libraries = auto_explain auto_explain.log_min_duration = 100 auto_explain.log_analyze = true auto_explain.log_buffers = true auto_explain.log_format = JSON
Se stai utilizzando un provider di hosting diverso, vale la pena verificare se supportano auto_explain. Ad esempio, RDS Postgres lo fa, ma a differenza di ScaleGrid, è disattivato per impostazione predefinita, quindi dovrai modificare la configurazione per farlo funzionare.
Caricamento di auto_explain in una singola sessione
Se non vuoi che auto_explain venga eseguito automaticamente nelle sessioni, come superutente hai anche la possibilità di caricarlo in una singola sessione:
LOAD 'auto_explain';
Questo può essere incredibilmente utile per sessioni di debug una tantum, ma naturalmente non è necessario se sei già in grado di farlo funzionare.
auto_explain limitazioni e trucchi
Ne abbiamo già menzionati alcuni di sfuggita, ma sembra un momento sensato per ricordare a noi stessi alcuni degli svantaggi e dei limiti di auto_explain.
In primo luogo, specialmente quando si tiene traccia dei tempi per operazione, può esserci un sovraccarico misurabile nell'uso di auto_explain. Può essere basso, anche con i tempi misurati, ma come sempre vale la pena fare i tuoi test.
In secondo luogo, i tempi di auto_explain sono esclusivi del tempo di pianificazione della query. Il tempo di pianificazione è spesso minimo per le query lente, ma in casi eccezionali può essere responsabile della maggior parte del problema. Pertanto, tieni presente che questi casi potrebbero non essere visualizzati nei tuoi registri o, se lo fanno, una discrepanza con ciò che stai vedendo nella latenza totale potrebbe avere a che fare con il tempo di pianificazione. Un manuale EXPLAIN ANALYZE
ti aiuterà rapidamente a individuarlo.
Come utilizzare l'output di spiegazione per velocizzare le query
Una volta che hai l'output di spiegazione per le tue query più lente, ora puoi iniziare a cercare di velocizzarle!
Dovrai estrarre i piani di query dai registri, per i quali puoi utilizzare pgBadger se non stai utilizzando un servizio gestito che lo fa per te.
La revisione dei piani EXPLAIN è un argomento enorme di per sé. La documentazione di PostgreSQL include una buona ma breve introduzione all'uso di EXPLAIN e l'articolo di Thoughbot sulla lettura di EXPLAIN ANALYZE è un buon passo successivo. Se preferisci un discorso di un'ora, EXPLAIN Explained da Josh Berkus è stato eccellente. Per ulteriori informazioni, Depesz ha una serie di post intitolati Spiegare l'inspiegabile e il team di pgMustard ha un Glossario EXPLAIN abbastanza completo.
Se hai bisogno dell'aiuto degli esperti di PostgreSQL per gestire i tuoi database e velocizzare le tue query lente, prova ScaleGrid. Forniamo supporto gratuito 24 ore su 24, 7 giorni su 7 a livello aziendale che può guidarti attraverso queste lente query e aiutarti a ottimizzarle tutte. La nostra prova gratuita di 30 giorni ti offre tutto il tempo per provare le nostre numerose funzionalità per PostgreSQL e gli altri database supportati.
Ci auguriamo che questo ti dia tutto ciò di cui hai bisogno per iniziare con auto_explain e iniziare ad accelerare qualsiasi query lenta che hai. Se c'è qualcos'altro che vorresti sapere, contattaci.