¡ADVERTENCIA! La actualización requiere mucho espacio libre en disco (2x el tamaño de la base de datos).
Acabamos de implementar cambios para actualizar nuestra imagen Docker a PostgreSQL 18. Cualquier administrador de sitio que reconstruya Discourse desde la línea de comandos será actualizado de PostgreSQL 15 a PostgreSQL 18. Ten en cuenta que si te abstuviste de actualizar cuando la actualización de PostgreSQL 15 ocurrió a finales de 2025, puedes saltarte esa actualización e ir directamente a PostgreSQL 18.
Si habías pospuesto la actualización anteriormente, cambia la plantilla de PostgreSQL en app.yml de templates/postgres.13.template.yml a templates/postgres.template.yml.
Como con cualquier actualización, se recomienda encarecidamente hacer una copia de seguridad antes de hacer nada.
Cambios de localización
Anteriormente, hemos visto que se producía corrupción de índices cuando se actualizaba glibc, como durante las actualizaciones del sistema operativo. Desde PostgreSQL 17, hay un nuevo proveedor de localización integrado que está desacoplado de la glibc del sistema operativo y, por lo tanto, es estable entre versiones. Como parte de esta actualización, nos estamos moviendo a este proveedor integrado utilizando la localización C.UTF-8. Esta localización utiliza el orden de puntos de código y la recomendamos por las razones de estabilidad mencionadas anteriormente.
Para lograr el cambio de localización, primero debemos crear el nuevo clúster de BD utilizando el proveedor de localización integrado y luego volcar y restaurar la BD en este clúster. Por esta razón, los requisitos de espacio en disco son mayores que en actualizaciones anteriores donde realizábamos actualizaciones in situ.
Actualización
Guía de instalación oficial (contenedor único)
En tu próxima reconstrucción, verás este mensaje al final:
-------------------------------------------------------------------------------------
ACTUALIZACIÓN DE POSTGRES COMPLETADA
La base de datos antigua 15 se almacena en /shared/postgres_data_old
Para completar la actualización, reconstruye nuevamente usando:
./launcher rebuild app
-------------------------------------------------------------------------------------
¡Eso significa que todo salió bien en la actualización! Solo necesitas emitir una nueva reconstrucción para que tu sitio vuelva a estar en funcionamiento.
Instalación con contenedor de datos
Si estás ejecutando una configuración con un contenedor de datos dedicado basado en la muestra proporcionada en nuestro repositorio discourse_docker, debes asegurarte de que PostgreSQL se detiene de manera segura y limpia.
Hoy en día, tenemos trabajos en segundo plano ejecutando consultas que abarcan varios minutos, por lo que detener el contenedor web ayudará a que el contenedor de datos se detenga de forma segura.
./launcher stop web_only
./launcher stop data
./launcher rebuild data
./launcher rebuild data
./launcher rebuild web_only
Antes de emitir la primera reconstrucción al contenedor de datos, puedes seguir el registro de PostgreSQL para ver si se detuvo correctamente.
Ejecutar un tail -f shared/standalone/log/var-log/postgres/current debería darte el siguiente registro si fue limpio:
2025-01-24 09:19:06.437 UTC [37] LOG: received smart shutdown request
2025-01-24 09:19:06.444 UTC [37] LOG: background worker "logical replication launcher" (PID 54) exited with exit code 1
2025-01-24 09:19:06.446 UTC [49] LOG: shutting down
2025-01-24 09:19:06.468 UTC [37] LOG: database system is shut down
Posponer la actualización
Si necesitas posponer la actualización durante tu próxima reconstrucción, puedes intercambiar la plantilla de PostgreSQL en tu archivo app.yml cambiando "templates/postgres.template.yml" por "templates/postgres.15.template.yml".
Esto no se recomienda, ya que algunos administradores de sitios olvidarán revertir el cambio posteriormente.
Tareas opcionales posteriores a la actualización
Optimizar las estadísticas de PostgreSQL
Después de la actualización, el nuevo PostgreSQL no tendrá estadísticas de tablas a mano. Puedes generarlas usando:
docker exec -u postgres app \
/usr/lib/postgresql/18/bin/vacuumdb -d discourse --analyze-in-stages
Limpiar datos antiguos
Para una instalación estándar, puedes eliminar los datos antiguos en formato PG15 con el siguiente comando:
cd /var/discourse
./launcher cleanup
Si tienes un contenedor de datos separado, deberás eliminar la copia de seguridad de esta manera:
rm -fr /var/discourse/shared/data/postgres_data_old/
FAQ
El clúster de origen no se detuvo correctamente
Si obtienes un error de actualización con el mensaje anterior, puedes intentar un enfoque más simple para devolverlo a un estado mejor.
Reinicia el contenedor antiguo con ./launcher start app. Espera unos minutos hasta que esté de nuevo en funcionamiento.
Ahora deténlo nuevamente con ./launcher stop app. Después de eso, sigue los registros para ver si fue una detención limpia:
tail -f shared/standalone/log/var-log/postgres/current
2025-01-24 09:19:06.437 UTC [37] LOG: received smart shutdown request
2025-01-24 09:19:06.444 UTC [37] LOG: background worker "logical replication launcher" (PID 54) exited with exit code 1
2025-01-24 09:19:06.446 UTC [49] LOG: shutting down
2025-01-24 09:19:06.468 UTC [37] LOG: database system is shut down
Si los registros no indican que la base de datos se ha detenido, puedes iniciar el contenedor antiguo nuevamente, entrar con ./launcher enter app, ejecutar estos comandos y seguir los registros nuevamente una vez terminado.
export SVWAIT=300
sv stop nginx
sv stop unicorn
sv stop postgres
exit
Si los registros se ven como arriba, ahora puedes intentar actualizar nuevamente usando ./launcher rebuild app.
Los valores de lc_collate para la base de datos “postgres” no coinciden
Este error ocurre si estás utilizando localizaciones no predeterminadas para tu base de datos. Se informó que necesitas 3 variables para que tenga éxito. Asegúrate de que la sección env: de tu archivo app.yml tenga las 3 líneas:
LC_ALL: en_US.UTF-8
LANG: en_US.UTF-8
LANGUAGE: en_US.UTF-8
Cambiando en_US.UTF-8 por tu localización.
Cada reconstrucción vuelve a hacer la actualización, es decir, bucle de actualización
Cuando esto ocurre, tus registros de actualización contendrán
mv: cannot move '/shared/postgres_data' to '/shared/postgres_data_old/postgres_data': Directory not empty
mv: cannot move '/shared/postgres_data_new' to '/shared/postgres_data/postgres_data_new': Directory not empty
Esto significa que aún hay archivos de la última actualización flotando alrededor. Muévelos a otro lugar antes de continuar.
Salté la actualización de PostgreSQL 15, ¿qué debo hacer ahora?
Puedes seguir las instrucciones estándar en la parte superior de esta guía y actualizarán desde tu versión a 18 sin problemas.