PostgreSQL
 sql >> Database >  >> RDS >> PostgreSQL

Compromessi nelle distribuzioni Hot Standby

La nuova funzionalità Hot Standby nel prossimo PostgreSQL 9.0 consente di eseguire query su nodi in standby che in precedenza non facevano altro che eseguire un processo di ripristino. Due aspettative comuni che ho sentito dagli utenti che anticipano questa funzionalità sono che consentirà la distribuzione di query brevi su entrambi i nodi o l'esecuzione di report lunghi sullo standby senza utilizzare risorse sul master. Questi sono entrambi possibili in questo momento, ma a meno che tu non comprenda i compromessi coinvolti nel funzionamento di Hot Standby, qui possono esserci alcuni comportamenti imprevisti.

Query standard di lunga durata

Uno dei problemi tradizionali in un database che utilizza MVCC, come PostgreSQL, è che una query di lunga durata deve mantenere aperta una risorsa, denominata snapshot nell'attuale implementazione di Postgres, per impedire al database di rimuovere i dati necessari per la query operare. Ad esempio, solo perché un altro client ha eliminato una riga e ha eseguito il commit, se una query già in esecuzione necessita di quella riga per essere completata, non è ancora possibile cancellare i blocchi del disco fisico relativi a quella riga. Devi attendere che non siano ancora presenti query aperte che prevedono che quella riga sia visibile.

Limitazioni Hot Standby

Se hai una query di lunga durata che desideri venga eseguita da Hot Standby, ci sono un paio di tipi di problemi che possono verificarsi quando il processo di ripristino sta applicando gli aggiornamenti. Questi sono descritti in dettaglio nella documentazione Hot Standby. Alcuni di questi aspetti negativi causeranno l'annullamento delle query in esecuzione in standby per motivi che potrebbero non essere intuitivamente ovvi:

  • Arriva un aggiornamento HOT o un aggiornamento relativo a VACUUM per eliminare qualcosa che la query prevede di essere visibile
  • Viene visualizzata un'eliminazione dell'albero B
  • Si è verificato un problema di blocco tra la query che stai eseguendo e quali blocchi sono necessari per l'elaborazione dell'aggiornamento.

La situazione del blocco è difficile da affrontare, ma non è molto probabile che accada in pratica per così tanto tempo se stai solo eseguendo query di sola lettura in standby, perché quelle saranno isolate tramite MVCC. Gli altri due non sono difficili da incontrare. La cosa fondamentale da capire è che qualsiasi UPDATE o DELETE sul master possono comportare l'interruzione di qualsiasi query in standby; non importa se le modifiche riguardano anche ciò che sta facendo la query.

Buono, veloce, economico:scegline due

In sostanza, ci sono tre cose che le persone potrebbero voler dare la priorità:

  1. Evita la limitazione del master:consenti agli xids e alle istantanee associate di avanzare illimitatamente sul master, in modo che VACUUM e una pulizia simile non siano trattenuti da ciò che sta facendo lo standby
  2. Query illimitate:esegui query in standby per qualsiasi periodo di tempo arbitrario
  3. Ripristino corrente:mantieni aggiornato il processo di ripristino in standby con ciò che sta accadendo sul master, consentendo un rapido failover per HA

In qualsiasi situazione con Hot Standby, è letteralmente impossibile averli tutti e tre contemporaneamente. Puoi solo scegliere il tuo compromesso. I parametri sintonizzabili disponibili ti consentono già di ottimizzare un paio di modi:

  • La disattivazione di tutte queste impostazioni di ritardo/rinvio ottimizza per il ripristino sempre attuale, ma scoprirai che è più probabile che le query vengano annullate di quanto potresti aspettarti.
  • max_standby_delay ottimizza per query più lunghe, a scapito di mantenere aggiornato il ripristino. Ciò ritarda l'applicazione degli aggiornamenti allo standby una volta visualizzato uno che causerà un problema (HOT, VACUUM, eliminazione B-tree, ecc.).
  • vacuum_defer_cleanup_age e alcuni hack di snapshot possono introdurre alcune limitazioni principali per migliorare gli altri due problemi, ma con un'interfaccia utente debole per farlo. vacuum_defer_cleanup_age è in unità di ID transazione. Devi avere un'idea della quantità media di xid churn sul tuo sistema per unità di tempo per trasformare il modo in cui le persone pensano a questo problema ("rinvia di almeno 1 ora in modo che i miei rapporti vengano eseguiti") in un'impostazione per questo valore. Il tasso di consumo di xid non è una cosa comune o addirittura ragionevole da misurare/prevedere. In alternativa, è possibile aprire uno snapshot sul primario prima di avviare una query di lunga durata in standby. dblink è suggerito nella documentazione di Hot Standby come un modo per farlo. Teoricamente un demone in standby potrebbe essere scritto in user-land, vivendo sul primary, per aggirare anche questo problema (Simon ha un progetto di base per uno). Fondamentalmente, avvii una serie di processi che acquisiscono ciascuno uno snapshot e quindi dormono per un periodo prima di rilasciarlo. Distanziando per quanto tempo ciascuno di loro ha dormito per te, è possibile garantire che gli snapshot xid non avanzino mai troppo rapidamente sul master. Dovrebbe già sembrare ovvio quanto possa essere un terribile hack.

Potenziali miglioramenti

L'unico di questi su cui puoi davvero fare qualcosa in modo pulito è rafforzare e migliorare l'interfaccia utente per il master limiting. Ciò trasforma questo nel problema tradizionale già presente nel database:una query di lunga durata mantiene aperta un'istantanea (o almeno limita l'anticipo degli ID transazione relativi alla visibilità) sul master, impedendo al master di rimuovere le cose necessarie per quella query completare. In alternativa potresti pensare a questo come a un autotuning vacuum_defer_cleanup_age.
La domanda è come rendere il primario rispettare le esigenze di query di lunga durata in standby . Ciò potrebbe essere possibile se più informazioni sui requisiti di visibilità della transazione dello standby fossero condivise con il master. Fare questo tipo di scambio sarebbe davvero qualcosa di più appropriato da condividere con la nuova implementazione della replica in streaming. Il modo in cui viene fornito un semplice server Hot Standby non fornisce alcun feedback verso il master adatto allo scambio di questi dati, oltre ad approcci come il già menzionato hack dblink.
Con PostgreSQL 9.0 che ha appena raggiunto una quarta versione alfa, potrebbe è ancora tempo di vedere alcuni miglioramenti in quest'area ancora prima del rilascio 9.0. Sarebbe bello vedere Hot Standby e Streaming Replication davvero integrati insieme in un modo che realizza cose che nessuno dei due è completamente in grado di fare da solo prima che la codifica su questa versione si blocchi completamente.