Lo siento, rompí tu recovery.conf

te rompo la recuperación En PostgreSQL, desde tiempos muy antiguos, ya la versión 8.0 que se lanzó en 2005, se utilizó un archivo de configuración recovery.conf especial para restaurar a un punto específico en el tiempo. Posteriormente, el mismo archivo comenzó a usarse para el modo de espera y la replicación de transmisión.

Sin embargo, desde la próxima versión de PostgreSQL 12, recovery.conf ya no funcionará: lo rompí.
Pero por que?

Recovery.conf tenía una característica: se leía solo al comienzo del DBMS. Y si la recuperación en un punto en el tiempo, que se necesita menos de una vez al año, aún puede conciliarse, entonces la necesidad de reiniciar toda la base de datos para cambiar la dirección del servidor de replicación ascendente es algo deprimente. Vi varias formas de perversiones para eludir esta limitación, como el uso de enrutamiento L3, esquemas de replicación en cascada (de modo que no todas las réplicas, pero al menos solo una parte de ellas, respectivamente) e incluso (incluso si no lo he visto en producción) walbouncer .

Después del próximo reinicio programado de las réplicas, solo por la necesidad de cambiar los parámetros de replicación, decidí retomarlo, pero ¿qué costaría enseñarle a PostgreSQL a volver a leer primary_conninfo en SIGHUP? Todo salió mal. En principio, debe cambiar solo una variable en el proceso de inicio y, a partir de ahí, solicitar un reinicio de WalReceiver, y eso es todo, la replicación continuará con la nueva dirección correctamente. Queda por implementar esto correctamente. Unas semanas más tarde terminé el parche con la implementación de relectura recovery.conf en la señal SIGHUP, mientras que ese parche no rompió el comportamiento de la base de datos existente.

Luego, teniendo el coraje, lo envió a la lista de correo de desarrolladores de PostgreSQL. Lo que Michael Paquier respondió bastante rápido:
Antes de hacer que algunos de ellos sean recargables, cambiemos primero a GUC y no reinventemos el manejo de los parámetros SIGHUP como lo hace su parche.
Vaya, resultó que le hice una pregunta incorrecta al motor de búsqueda. La pregunta no era acerca de volver a leer recovery.conf, sino acerca de la conversión de parámetros desde un recovery.conf separado a la infraestructura GUC (gran configuración unificada) utilizada para todos los demás parámetros DBMS. Es decir, definitivamente no, no necesitamos ese parche, no queremos esto. Primero transfiramos todas estas configuraciones desde recovery.conf a nuestra infraestructura de configuraciones estándar.

En esta triste noticia, me quemé y pensé: "¡Pero transfirámonos!". Leí las discusiones archivadas sobre la consulta de búsqueda correcta, abrí la última discusión encontrada sobre la transferencia de configuraciones (el enlace fue proporcionado amablemente por Michael Paquier en su respuesta, por lo cual le agradezco por separado, así como por la respuesta rápida). En ese momento, en mayo de 2018, el parche fue abandonado por más de un año. Entonces, aquí comenzamos. ¿O es más correcto decir "continuar"? Según el plan de entretenimiento:

  1. lea y enumere los cambios a la última versión publicada del parche
  2. analizar los cambios en el parche y transferir lo necesario a la versión actual de la base de código
  3. arregle todas las referencias a recovery.conf y sus parámetros en la documentación
  4. pruebas de reparación
  5. enviar un nuevo parche a la lista de correo
  6. obtener cualquier comentario
  7. corregir algo de acuerdo con los deseos y volver al párrafo 5
  8. recibir una negativa a aceptar el parche nuevamente (en un año y medio)

¿Suena como un plan de acción? Bueno, aquí vamos!

Cuánto tiempo, brevemente, llegué al punto cinco y el 21 de junio de 2018 publiqué una nueva versión del parche en un nuevo hilo de discusión . Luego 3 meses en el silencio opresivo del silencio escalofriante de los peces Baskerville. A finales de septiembre, Peter Eisentraut, uno de los desarrolladores principales con derecho a comprometerse, de repente mostró interés en el parche. Después de varias iteraciones de correcciones, mientras me alejaba tranquilamente durante unos días para dar un paseo, ver Budapest y ver los lugares de interés, llega una carta desalentadora de Peter Eisentraut:
Revisé el parche e hice un montón de pequeños refinamientos. También he actualizado la documentación más ampliamente. El parche adjunto es comprometible para mí.
Es decir, Peter Eisentraut corrigió algunas pequeñas cosas más a su discreción, actualizó la documentación, grabó toda la sección recovery-config.sgml y cree que de esta forma el parche ya puede ser aceptado. Ah, y pensé que sucedería solo para postgresql 13, incluso si es tan afortunado que el parche generalmente alcance un estado de preparación para el compromiso.

Y unos días después, es decir, el 25 de noviembre de este 2018, Peter Eisentraut realmente acepta este parche :
La configuración de recovery.conf ahora se establece en postgresql.conf (u otras fuentes de GUC). Actualmente, todas las configuraciones afectadas son PGC_POSTMASTER; Esto podría ser refinado en el futuro caso por caso.
La recuperación ahora se inicia mediante un archivo recovery.signal. El modo de espera se inicia mediante un archivo standby.signal. La configuración standby_mode se ha ido. Si se encuentra un archivo recovery.conf, se emite un error.
Se ha cambiado el nombre de la configuración de archivo_activador para promover_archivo_activador como parte del movimiento.
El capítulo de documentación "Configuración de recuperación" se ha integrado en "Configuración del servidor".
pg_basebackup -R ahora agrega configuraciones a postgresql.auto.conf y crea un archivo standby.signal.
Autor: Fujii Masao <masao (dot) fujii (at) gmail (dot) com>
Autor: Simon Riggs <simon (at) 2ndquadrant (dot) com>
Autor: Abhijit Menon-Sen <ams (at) 2ndquadrant (dot) com>
Autor: Sergei Kornilov <sk (at) zsrv (dot) org>
Han pasado dos semanas y este compromiso no se ha revertido. Asombroso Y parece que ni siquiera lo harán. Es asombroso. No se sabe si la comunidad decidirá cambiar el comportamiento en alguna dirección nuevamente, especialmente dado que aún queda un poco de tiempo antes de que la función congele el lanzamiento de postgresql 12 en abril. Pero parece que no tendremos más recovery.conf.

Entonces, ¿qué ha cambiado?


En primer lugar, el DBMS se negará a iniciarse si encuentra un archivo recovery.conf; esto se hizo específicamente para que el usuario, utilizando una de las muchas instrucciones antiguas, no se sorprenda por qué la base de datos ignora la configuración en este archivo.

La antigua configuración standby_mode ha desaparecido. Ahora, así como el hecho mismo de la existencia de recovery.conf para habilitar el modo de recuperación, se reemplaza por dos archivos (de cualquier contenido, generalmente vacío):

  • $ PGDATA / recovery.signal - sucesor ideológico standby_mode = off, la restauración del archivo se realizará al punto especificado en las configuraciones;
  • $ PGDATA / standby.signal - respectivamente, standby_mode = on. Veremos este archivo en todas las réplicas.

Si el proceso de inicio de la base de datos encontró ambos archivos, consideramos que estamos en modo de espera.

Si, para mayor claridad, para reducir los cambios de parámetros en una placa:
antigua recovery.conf
PostgreSQL 12+ postgresql.conf
primary_conninfo
primary_conninfo
nombre_slot_primaria
nombre_slot_primaria
archivo_activador
promover_archivo_activador
recovery_min_apply_delay
recovery_min_apply_delay
objetivo_recuperación
objetivo_recuperación
recovery_target_name
recovery_target_name
recovery_target_time
recovery_target_time
recovery_target_xid
recovery_target_xid
recovery_target_lsn
recovery_target_lsn
recovery_target_inclusive
recovery_target_inclusive
recovery_target_timeline
recovery_target_timeline
recovery_target_action
recovery_target_action
restaurar_comando
restaurar_comando
archive_cleanup_command
archive_cleanup_command
recovery_end_command
recovery_end_command

Puedes ver que un poco menos que nada ha cambiado. En este momento (con la única excepción del prefijo promover_ para archivo_activador_activador), todos los parámetros nuevos se nombran como los anteriores y toman los mismos valores posibles. Aunque, de hecho, todavía hay un cambio con respecto a la configuración del objetivo de recuperación. No sé si alguien usó esto antes, pero fue un comportamiento documentado y fue posible especificar varios recovery_target, recovery_target_lsn, recovery_target_name, recovery_target_time o recovery_target_xid al mismo tiempo. Por ejemplo

recovery_target_lsn = '1/1D9FEA00' recovery_target_xid = '5238954' 

La última línea de recovery.conf se usó realmente para la recuperación. Esto ya no es posible, el objetivo de recuperación debe indicarse por un máximo de uno. Sin embargo, debido a la lógica de la infraestructura de GUC, aún puede especificar el parámetro del mismo nombre varias veces:

 recovery_target_lsn = '1/1D9FEA00' recovery_target_lsn = '1/16AC7D0' 

Esto es aceptable, se restablecerá el valor de configuración especificado en último lugar.

Y, en general, esto es todo lo que hay que decir sobre los cambios visibles desde fuera de PostgreSQL. pg_basebackup -R (--write-recovery-conf) permaneció en su lugar y hace lo que se pretende, solo que ahora agregará parámetros a postgresql.auto.conf en lugar de recovery.conf y creará un archivo standby.signal

Desafortunadamente, cuando digo que estos son todos los cambios que están visibles actualmente, esto es exactamente lo que quiero decir. Todos los parámetros nuevos todavía se configuran como PGC_POSTMASTER, es decir, solo se pueden cambiar cuando se inicia PostgreSQL. Como ya se mencionó, este fue un requisito por parte de la comunidad de desarrolladores: primero, transfiera todas las configuraciones, y solo luego vea si se pueden cambiar en la base de datos en ejecución. Así que ahora PostgreSQL se encuentra en una etapa maravillosa de desarrollo, cuando el comportamiento anterior ya se ha roto y aún no se han introducido cambios para mejorar.

Ya publiqué un parche que permitirá cambiar primary_conninfo y primary_slot_name sobre la marcha. Veamos que pasa.

Lo siento, rompí tu recovery.conf

UPD 7 de abril de 2019


En el último día antes de la función de congelación de la versión 12, puede resumir. Cambiar la configuración de replicación no se incluyó en la versión. Por supuesto, esta también es una historia curiosa. Érase una vez, el parche Simon Riggs que tomé como base ya contenía ediciones para reiniciar walreceiver al cambiar la configuración de conexión. Los seleccioné en un parche separado que complementa la documentación y las pruebas. Y después de 6 actualizaciones de parches y un par de meses de discusión, surge el hecho obvio de que si reinicia walreceiver, la base de datos intentará cambiar a la restauración de archivos desde restore_command. Un comportamiento bastante simple de la máquina de estados, que se desencadena al apagar el receptor de red por cualquier motivo. Pero esto resulta ser "algo que no queremos". Bueno, antes era imposible decir? Ok, lo rehice de alguna manera, pero el calendario ya tenía el último commitfest para la versión 12 y nadie miró aquí. En general, esto no es algo rápido, lo hacen los parches en PostgreSQL. Pero tengo todo el derecho de incluirme en la lista de personas, ¡gracias a quienes se incluyó REINDEX CONCURRENTEMENTE sin terminar más épico sin terminar en la versión 12!

Vale la pena mencionar al final que una serie de configuraciones tienen la oportunidad de cambiar sobre la marcha: archive_cleanup_command, promote_trigger_file, recovery_end_command, recovery_min_apply_delay

Source: https://habr.com/ru/post/es432918/


All Articles