From c8bb48b3ef27bc76269f129d973b3e316b159ea0 Mon Sep 17 00:00:00 2001 From: Daniel Berteaud Date: Wed, 24 Apr 2024 23:51:51 +0200 Subject: [PATCH] Add support for major upgrades --- example/.variables.yml.swp | Bin 0 -> 16157 bytes example/images/pg-upgrade/Dockerfile | 27 ------- .../root/usr/local/bin/pg-major-upgrade | 56 ------------- .../images/postgres-major-upgrade/Dockerfile | 15 ++-- .../root/usr/local/bin/pg-upgrade.sh | 21 +++-- ...ge.nomad.hcl => postgres-manage.nomad.hcl} | 0 ...es.nomad.hcl => postgres-server.nomad.hcl} | 14 ++-- example/postgres-upgrade.nomad.hcl | 74 ++++++++++++++++++ images/pg-upgrade/Dockerfile | 27 ------- .../root/usr/local/bin/pg-major-upgrade | 56 ------------- images/postgres-major-upgrade/Dockerfile | 19 +++-- .../root/usr/local/bin/pg-upgrade.sh | 21 +++-- manage.nomad.hcl => postgres-manage.nomad.hcl | 0 ...res.nomad.hcl => postgres-server.nomad.hcl | 14 ++-- postgres-upgrade.nomad.hcl | 51 ++++++++++++ templates/patroni.yml.tpl | 11 ++- variables.yml | 23 +++++- 17 files changed, 220 insertions(+), 209 deletions(-) create mode 100644 example/.variables.yml.swp delete mode 100644 example/images/pg-upgrade/Dockerfile delete mode 100644 example/images/pg-upgrade/root/usr/local/bin/pg-major-upgrade rename example/{manage.nomad.hcl => postgres-manage.nomad.hcl} (100%) rename example/{postgres.nomad.hcl => postgres-server.nomad.hcl} (98%) create mode 100644 example/postgres-upgrade.nomad.hcl delete mode 100644 images/pg-upgrade/Dockerfile delete mode 100644 images/pg-upgrade/root/usr/local/bin/pg-major-upgrade rename manage.nomad.hcl => postgres-manage.nomad.hcl (100%) rename postgres.nomad.hcl => postgres-server.nomad.hcl (96%) create mode 100644 postgres-upgrade.nomad.hcl diff --git a/example/.variables.yml.swp b/example/.variables.yml.swp new file mode 100644 index 0000000000000000000000000000000000000000..1ee16ef278ac0690b6ee3f5cf9598adc6d92a740 GIT binary patch literal 16157 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 - -ARG PG_FROM= \ - PG_TO= - -ENV LANG=fr_FR.utf8 \ - TZ=Europe/Paris - -COPY --from=walg /usr/local/bin/wal-g /usr/local/bin/wal-g - -RUN set -eux &&\ - apk --no-cache upgrade &&\ - for VER in 12 13 14 15; do \ - apk --no-cache add postgresql${PG_VERSION} \ - postgresql${PG_VERSION}-client \ - postgresql${PG_VERSION}-contrib \ - done - apk --no-cache add icu-data-full \ - tzdata &&\ - mkdir -p /run/postgresql &&\ - chown -R postgres:postgres /run/postgresql - -COPY root/ / - -USER postgres -CMD ["pg-major-upgrade"] diff --git a/example/images/pg-upgrade/root/usr/local/bin/pg-major-upgrade b/example/images/pg-upgrade/root/usr/local/bin/pg-major-upgrade deleted file mode 100644 index ec232bb..0000000 --- a/example/images/pg-upgrade/root/usr/local/bin/pg-major-upgrade +++ /dev/null @@ -1,56 +0,0 @@ -#!/bin/sh - -set -euo pipefail - -if [ -z "${PG_FROM}" ]; then - echo "You must set PG_FROM env var to the source version" - exit 1 -elif [ -z "${PG_TO}" ]; then - echo "You must set PG_TO env var to the destination version" - exit 1 -elif [ ! -d "${PG_BASE_DATA}/${PG_FROM}" ]; then - echo "Source data dir ${PG_BASE_DATA}/${PG_FROM} must already exist" - exit 1 -fi - -if [ -z "${DO_PG_UPGRADE}" -o "${DO_PG_UPGRADE}" != "1" ]; then - echo "Not running the upgrade. Please set DO_PG_UPGRADE=1" -fi - -cd ${PG_BASE_DATA} - -echo "Creating new data dir for version ${PG_TO}" -mkdir -p ${PG_BASE_DATA}/${PG_TO} -chmod 700 ${PG_BASE_DATA}/${PG_TO} - -echo "Commenting SSL directives (SSL cert not available, nor needed in the upgrade context)" -cp ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf.old -sed -i -r 's/^(ssl.*)/#\1/g' ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf - -echo "Replacing pg_hba with a custom one" -cp ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf.old -cat <<_EOF > ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf -local all postgres peer -_EOF - -echo "Initializing new PG cluster" -/usr/libexec/postgresql${PG_TO}/bin/initdb --pgdata=${PG_BASE_DATA}/${PG_TO} --auth-host=scram-sha-256 --auth-local=peer --icu-locale=${LANG} --data-checksums --encoding=UTF8 --locale-provider=icu - -echo "Upgrading PG data from ${PG_BASE_DATA}/${PG_FROM} to ${PG_BASE_DATA}/${PG_TO}" -/usr/libexec/postgresql${PG_TO}/bin/pg_upgrade \ - --clone \ - --old-datadir ${PG_BASE_DATA}/${PG_FROM} \ - --new-datadir ${PG_BASE_DATA}/${PG_TO} \ - --old-bindir /usr/libexec/postgresql${PG_FROM}/bin \ - --new-bindir /usr/libexec/postgresql${PG_TO}/bin - -echo "Keep old patroni.dynamic.json config" -if [ -e "${PG_BASE_DATA}/${PG_FROM}/patroni.dynamic.json" ]; then - cp ${PG_BASE_DATA}/${PG_FROM}/patroni.dynamic.json ${PG_BASE_DATA}/${PG_TO}/ -fi - -echo "Restoring configuration" -cp -f ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf.old ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf -cp -f ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf.old ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf -cp -f ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf ${PG_BASE_DATA}/${PG_TO}/pg_hba.conf -cp -f ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf ${PG_BASE_DATA}/${PG_TO}/postgresql.conf diff --git a/example/images/postgres-major-upgrade/Dockerfile b/example/images/postgres-major-upgrade/Dockerfile index 0ce9fbf..59d8fb7 100644 --- a/example/images/postgres-major-upgrade/Dockerfile +++ b/example/images/postgres-major-upgrade/Dockerfile @@ -1,16 +1,21 @@ FROM danielberteaud/alma:9.24.4-1 MAINTAINER Daniel Berteaud -ENV PG_BASE_DATA=/data/db/ +ENV PG_BASE_DATA=/data/db/ \ + PG_INITDB_OPTS="--data-checksum --encoding UTF-8" -RUN set -eux \ - dnf update -y &&\ +RUN set -eux &&\ rpm -i https://download.postgresql.org/pub/repos/yum/reporpms/EL-9-x86_64/pgdg-redhat-repo-latest.noarch.rpm &&\ dnf module -y disable postgresql &&\ - dnf install -y --setopt=install_weak_deps=0 glibc-langpack-fr glibc-langpack-en &&\ - for VER in 11 12 13 14 15 16; do dnf install -y postgresql${VER} postgresql${VER}-server postgresql${VER}-contrib; done &&\ + dnf -y install glibc-langpack-fr glibc-langpack-en &&\ + dnf install -y postgresql15 postgresql15-server postgresql15-contrib; \ + dnf install -y postgresql16 postgresql16-server postgresql16-contrib; \ dnf clean all &&\ rm -rf /var/cache/yum/* /var/log/yum/* /var/lib/yum/history* +COPY --from=danielberteaud/postgres:15.24.4-1 /usr/pgsql-15/share/extension/vectors* /usr/pgsql-15/share/extension/ +COPY --from=danielberteaud/postgres:15.24.4-1 /usr/pgsql-15/lib/vectors.so /usr/pgsql-15/lib/vectors.so +COPY --from=danielberteaud/postgres:16.24.4-1 /usr/pgsql-16/share/extension/vectors* /usr/pgsql-16/share/extension/ +COPY --from=danielberteaud/postgres:16.24.4-1 /usr/pgsql-16/lib/vectors.so /usr/pgsql-16/lib/vectors.so COPY root/ / diff --git a/example/images/postgres-major-upgrade/root/usr/local/bin/pg-upgrade.sh b/example/images/postgres-major-upgrade/root/usr/local/bin/pg-upgrade.sh index 84946c0..e0fe536 100755 --- a/example/images/postgres-major-upgrade/root/usr/local/bin/pg-upgrade.sh +++ b/example/images/postgres-major-upgrade/root/usr/local/bin/pg-upgrade.sh @@ -1,6 +1,8 @@ #!/bin/sh -set -euxo pipefail +set -euo pipefail + +mkdir -p /data/db if [ -z "${PG_FROM}" ]; then echo "You must set PG_FROM env var to the source version" @@ -13,8 +15,8 @@ elif [ ! -d "${PG_BASE_DATA}/${PG_FROM}" ]; then exit 1 fi -if [ -z "${DO_PG_UPGRADE}" -o "${DO_PG_UPGRADE}" != "1" ]; then - echo "Not running the upgrade. Please set DO_PG_UPGRADE=1" +if [ -z "${DO_PG_UPGRADE}" -o "${DO_PG_UPGRADE}" != "true" ]; then + echo "Not running the upgrade. Please set DO_PG_UPGRADE=true" fi cd "${PG_BASE_DATA}" @@ -27,6 +29,15 @@ echo "Commenting SSL directives (SSL cert not available, nor needed in the upgra cp "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf" "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf.old" sed -i -r 's/^(ssl.*)/#\1/g' "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf" +echo "Commenting Socket directive" +sed -i -r 's/^(unix_socket_directories.*)/#\1/g' "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf" + +#echo "Commenting shared_preload_libraries directive" +#sed -i -r 's/^(shared_preload_libraries.*)/#\1/g' "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf" + +echo "Commenting log_XXX directives" +sed -i -r 's/^(log_.*)/#\1/g' "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf" + echo "Replacing pg_hba with a custom one" cp "${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf" "${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf.old" cat <<_EOF > "${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf" @@ -34,11 +45,11 @@ local all postgres peer _EOF echo "Initializing new PG cluster" -/usr/pgsql-${PG_TO}/bin/initdb --pgdata=${PG_BASE_DATA}/${PG_TO} --data-checksums --encoding UTF-8 +/usr/pgsql-${PG_TO}/bin/initdb --pgdata=${PG_BASE_DATA}/${PG_TO} ${PG_INITDB_OPTS} echo "Upgrading PG data from ${PG_BASE_DATA}/${PG_FROM} to ${PG_BASE_DATA}/${PG_TO}" /usr/pgsql-${PG_TO}/bin/pg_upgrade \ - --clone \ + ${PG_UPGRADE_OPTS} \ --old-datadir "${PG_BASE_DATA}/${PG_FROM}" \ --new-datadir "${PG_BASE_DATA}/${PG_TO}" \ --old-bindir /usr/pgsql-${PG_FROM}/bin \ diff --git a/example/manage.nomad.hcl b/example/postgres-manage.nomad.hcl similarity index 100% rename from example/manage.nomad.hcl rename to example/postgres-manage.nomad.hcl diff --git a/example/postgres.nomad.hcl b/example/postgres-server.nomad.hcl similarity index 98% rename from example/postgres.nomad.hcl rename to example/postgres-server.nomad.hcl index 3b7bd22..0f0d1b3 100644 --- a/example/postgres.nomad.hcl +++ b/example/postgres-server.nomad.hcl @@ -1,4 +1,4 @@ -job "postgres" { +job "postgres-server" { datacenters = ["dc1"] @@ -93,8 +93,8 @@ job "postgres" { port = "patroni" path = "/health" protocol = "https" - interval = "20s" - timeout = "10s" + interval = "30s" + timeout = "5s" # Patroni REST API is using a cert from a private CA tls_skip_verify = true } @@ -105,15 +105,15 @@ job "postgres" { type = "script" command = "/local/update_tags.sh" task = "postgres" - interval = "20s" - timeout = "10s" + interval = "30s" + timeout = "5s" } check { name = "ready" type = "script" interval = "30s" - timeout = "10s" + timeout = "5s" task = "postgres" command = "pg_isready" } @@ -332,8 +332,6 @@ bootstrap: initdb: - data-checksum - encoding: UTF-8 - #- locale-provider: icu - #- icu-locale: fr_FR.utf8 post_bootstrap: /local/create_users.sh diff --git a/example/postgres-upgrade.nomad.hcl b/example/postgres-upgrade.nomad.hcl new file mode 100644 index 0000000..0a69062 --- /dev/null +++ b/example/postgres-upgrade.nomad.hcl @@ -0,0 +1,74 @@ +job "postgres-upgrade" { + + datacenters = ["dc1"] + region = "global" + priority = 80 + + type = "batch" + + meta { + # Force job to be different for each execution + run_uuid = "${uuidv4()}" + } + # Postgres upgrader not explicitely enabled + # Add a constraint to ensure it can't run + constraint { + attribute = "${attr.kernel.name}" + value = "nonexistant" + } + + group "upgrade" { + + + volume "backup" { + source = "postgres-backup" + type = "csi" + access_mode = "multi-node-multi-writer" + attachment_mode = "file-system" + } + + volume "data" { + source = "postgres-data" + type = "csi" + access_mode = "single-node-writer" + attachment_mode = "file-system" + per_alloc = true + } + + + network { + mode = "bridge" + } + + task "upgrade" { + driver = "docker" + + config { + image = "danielberteaud/postgres-major-upgrade:latest" + force_pull = true + readonly_rootfs = true + + } + + env { + PG_FROM = "" + PG_TO = "" + PG_INITDB_OPTS = "--data-checksum --encoding UTF-8 " + PG_UPGRADE_OPTS = "--new-options=-c --new-options=shared_preload_libraries=vectors.so --clone " + DO_PG_UPGRADE = "false" + } + + volume_mount { + volume = "data" + destination = "/data" + } + + + resources { + cpu = 1000 + memory = 1024 + } + + } + } +} diff --git a/images/pg-upgrade/Dockerfile b/images/pg-upgrade/Dockerfile deleted file mode 100644 index 6eefec7..0000000 --- a/images/pg-upgrade/Dockerfile +++ /dev/null @@ -1,27 +0,0 @@ -FROM [[ .docker.repo ]][[ .docker.base_images.alpine.image ]] -MAINTAINER [[ .docker.maintainer ]] - -ARG PG_FROM= \ - PG_TO= - -ENV LANG=[[ .locale.lang ]] \ - TZ=[[ .locale.tz ]] - -COPY --from=walg /usr/local/bin/wal-g /usr/local/bin/wal-g - -RUN set -eux &&\ - apk --no-cache upgrade &&\ - for VER in 12 13 14 15; do \ - apk --no-cache add postgresql${PG_VERSION} \ - postgresql${PG_VERSION}-client \ - postgresql${PG_VERSION}-contrib \ - done - apk --no-cache add icu-data-full \ - tzdata &&\ - mkdir -p /run/postgresql &&\ - chown -R postgres:postgres /run/postgresql - -COPY root/ / - -USER postgres -CMD ["pg-major-upgrade"] diff --git a/images/pg-upgrade/root/usr/local/bin/pg-major-upgrade b/images/pg-upgrade/root/usr/local/bin/pg-major-upgrade deleted file mode 100644 index ec232bb..0000000 --- a/images/pg-upgrade/root/usr/local/bin/pg-major-upgrade +++ /dev/null @@ -1,56 +0,0 @@ -#!/bin/sh - -set -euo pipefail - -if [ -z "${PG_FROM}" ]; then - echo "You must set PG_FROM env var to the source version" - exit 1 -elif [ -z "${PG_TO}" ]; then - echo "You must set PG_TO env var to the destination version" - exit 1 -elif [ ! -d "${PG_BASE_DATA}/${PG_FROM}" ]; then - echo "Source data dir ${PG_BASE_DATA}/${PG_FROM} must already exist" - exit 1 -fi - -if [ -z "${DO_PG_UPGRADE}" -o "${DO_PG_UPGRADE}" != "1" ]; then - echo "Not running the upgrade. Please set DO_PG_UPGRADE=1" -fi - -cd ${PG_BASE_DATA} - -echo "Creating new data dir for version ${PG_TO}" -mkdir -p ${PG_BASE_DATA}/${PG_TO} -chmod 700 ${PG_BASE_DATA}/${PG_TO} - -echo "Commenting SSL directives (SSL cert not available, nor needed in the upgrade context)" -cp ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf.old -sed -i -r 's/^(ssl.*)/#\1/g' ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf - -echo "Replacing pg_hba with a custom one" -cp ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf.old -cat <<_EOF > ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf -local all postgres peer -_EOF - -echo "Initializing new PG cluster" -/usr/libexec/postgresql${PG_TO}/bin/initdb --pgdata=${PG_BASE_DATA}/${PG_TO} --auth-host=scram-sha-256 --auth-local=peer --icu-locale=${LANG} --data-checksums --encoding=UTF8 --locale-provider=icu - -echo "Upgrading PG data from ${PG_BASE_DATA}/${PG_FROM} to ${PG_BASE_DATA}/${PG_TO}" -/usr/libexec/postgresql${PG_TO}/bin/pg_upgrade \ - --clone \ - --old-datadir ${PG_BASE_DATA}/${PG_FROM} \ - --new-datadir ${PG_BASE_DATA}/${PG_TO} \ - --old-bindir /usr/libexec/postgresql${PG_FROM}/bin \ - --new-bindir /usr/libexec/postgresql${PG_TO}/bin - -echo "Keep old patroni.dynamic.json config" -if [ -e "${PG_BASE_DATA}/${PG_FROM}/patroni.dynamic.json" ]; then - cp ${PG_BASE_DATA}/${PG_FROM}/patroni.dynamic.json ${PG_BASE_DATA}/${PG_TO}/ -fi - -echo "Restoring configuration" -cp -f ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf.old ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf -cp -f ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf.old ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf -cp -f ${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf ${PG_BASE_DATA}/${PG_TO}/pg_hba.conf -cp -f ${PG_BASE_DATA}/${PG_FROM}/postgresql.conf ${PG_BASE_DATA}/${PG_TO}/postgresql.conf diff --git a/images/postgres-major-upgrade/Dockerfile b/images/postgres-major-upgrade/Dockerfile index 3b8566b..61c7753 100644 --- a/images/postgres-major-upgrade/Dockerfile +++ b/images/postgres-major-upgrade/Dockerfile @@ -1,17 +1,26 @@ FROM [[ .docker.repo ]][[ .docker.base_images.alma9.image ]] MAINTAINER [[ .docker.maintainer ]] -ENV PG_BASE_DATA=/data/db/ +ENV PG_BASE_DATA=/data/db/ \ + PG_INITDB_OPTS="--data-checksum --encoding UTF-8" -RUN set -eux \ - dnf update -y &&\ +[[- $pg_ver := coll.Slice "15" "16" ]] + +RUN set -eux &&\ rpm -i https://download.postgresql.org/pub/repos/yum/reporpms/EL-9-x86_64/pgdg-redhat-repo-latest.noarch.rpm &&\ dnf module -y disable postgresql &&\ - dnf install -y --setopt=install_weak_deps=0 glibc-langpack-fr glibc-langpack-en &&\ - for VER in 11 12 13 14 15 16; do dnf install -y postgresql${VER} postgresql${VER}-server postgresql${VER}-contrib; done &&\ + dnf -y install glibc-langpack-fr glibc-langpack-en &&\ +[[- range $ver := $pg_ver ]] + dnf install -y postgresql[[ $ver ]] postgresql[[ $ver ]]-server postgresql[[ $ver ]]-contrib; \ +[[- end ]] dnf clean all &&\ rm -rf /var/cache/yum/* /var/log/yum/* /var/lib/yum/history* +[[- range $ver := $pg_ver ]] +COPY --from=[[ $.docker.repo ]][[ (index $.docker.base_images (printf "postgres%s" $ver)).image ]] /usr/pgsql-[[ $ver ]]/share/extension/vectors* /usr/pgsql-[[ $ver ]]/share/extension/ +COPY --from=[[ $.docker.repo ]][[ (index $.docker.base_images (printf "postgres%s" $ver)).image ]] /usr/pgsql-[[ $ver ]]/lib/vectors.so /usr/pgsql-[[ $ver ]]/lib/vectors.so +[[- end ]] + COPY root/ / USER postgres diff --git a/images/postgres-major-upgrade/root/usr/local/bin/pg-upgrade.sh b/images/postgres-major-upgrade/root/usr/local/bin/pg-upgrade.sh index 84946c0..e0fe536 100755 --- a/images/postgres-major-upgrade/root/usr/local/bin/pg-upgrade.sh +++ b/images/postgres-major-upgrade/root/usr/local/bin/pg-upgrade.sh @@ -1,6 +1,8 @@ #!/bin/sh -set -euxo pipefail +set -euo pipefail + +mkdir -p /data/db if [ -z "${PG_FROM}" ]; then echo "You must set PG_FROM env var to the source version" @@ -13,8 +15,8 @@ elif [ ! -d "${PG_BASE_DATA}/${PG_FROM}" ]; then exit 1 fi -if [ -z "${DO_PG_UPGRADE}" -o "${DO_PG_UPGRADE}" != "1" ]; then - echo "Not running the upgrade. Please set DO_PG_UPGRADE=1" +if [ -z "${DO_PG_UPGRADE}" -o "${DO_PG_UPGRADE}" != "true" ]; then + echo "Not running the upgrade. Please set DO_PG_UPGRADE=true" fi cd "${PG_BASE_DATA}" @@ -27,6 +29,15 @@ echo "Commenting SSL directives (SSL cert not available, nor needed in the upgra cp "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf" "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf.old" sed -i -r 's/^(ssl.*)/#\1/g' "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf" +echo "Commenting Socket directive" +sed -i -r 's/^(unix_socket_directories.*)/#\1/g' "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf" + +#echo "Commenting shared_preload_libraries directive" +#sed -i -r 's/^(shared_preload_libraries.*)/#\1/g' "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf" + +echo "Commenting log_XXX directives" +sed -i -r 's/^(log_.*)/#\1/g' "${PG_BASE_DATA}/${PG_FROM}/postgresql.conf" + echo "Replacing pg_hba with a custom one" cp "${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf" "${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf.old" cat <<_EOF > "${PG_BASE_DATA}/${PG_FROM}/pg_hba.conf" @@ -34,11 +45,11 @@ local all postgres peer _EOF echo "Initializing new PG cluster" -/usr/pgsql-${PG_TO}/bin/initdb --pgdata=${PG_BASE_DATA}/${PG_TO} --data-checksums --encoding UTF-8 +/usr/pgsql-${PG_TO}/bin/initdb --pgdata=${PG_BASE_DATA}/${PG_TO} ${PG_INITDB_OPTS} echo "Upgrading PG data from ${PG_BASE_DATA}/${PG_FROM} to ${PG_BASE_DATA}/${PG_TO}" /usr/pgsql-${PG_TO}/bin/pg_upgrade \ - --clone \ + ${PG_UPGRADE_OPTS} \ --old-datadir "${PG_BASE_DATA}/${PG_FROM}" \ --new-datadir "${PG_BASE_DATA}/${PG_TO}" \ --old-bindir /usr/pgsql-${PG_FROM}/bin \ diff --git a/manage.nomad.hcl b/postgres-manage.nomad.hcl similarity index 100% rename from manage.nomad.hcl rename to postgres-manage.nomad.hcl diff --git a/postgres.nomad.hcl b/postgres-server.nomad.hcl similarity index 96% rename from postgres.nomad.hcl rename to postgres-server.nomad.hcl index c8334e4..46866e9 100644 --- a/postgres.nomad.hcl +++ b/postgres-server.nomad.hcl @@ -1,4 +1,4 @@ -job "[[ .instance ]]" { +job "[[ .instance ]]-server" { [[- $c := merge .pg . ]] @@ -53,8 +53,8 @@ job "[[ .instance ]]" { port = "patroni" path = "/health" protocol = "https" - interval = "20s" - timeout = "10s" + interval = "[[ $c.consul.check.interval ]]" + timeout = "[[ $c.consul.check.timeout ]]" # Patroni REST API is using a cert from a private CA tls_skip_verify = true } @@ -65,15 +65,15 @@ job "[[ .instance ]]" { type = "script" command = "/local/update_tags.sh" task = "postgres" - interval = "20s" - timeout = "10s" + interval = "[[ $c.consul.check.interval ]]" + timeout = "[[ $c.consul.check.timeout ]]" } check { name = "ready" type = "script" - interval = "30s" - timeout = "10s" + interval = "[[ $c.consul.check.interval ]]" + timeout = "[[ $c.consul.check.timeout ]]" task = "postgres" command = "pg_isready" } diff --git a/postgres-upgrade.nomad.hcl b/postgres-upgrade.nomad.hcl new file mode 100644 index 0000000..bef9b37 --- /dev/null +++ b/postgres-upgrade.nomad.hcl @@ -0,0 +1,51 @@ +job "[[ .instance ]]-upgrade" { +[[- $c := merge .pg . ]] +[[ template "common/job_start" $c ]] + type = "batch" + + meta { + # Force job to be different for each execution + run_uuid = "${uuidv4()}" + } + +[[- if (not $c.upgrade.enabled) ]] + # Postgres upgrader not explicitely enabled + # Add a constraint to ensure it can't run + constraint { + attribute = "${attr.kernel.name}" + value = "nonexistant" + } +[[- end ]] + + group "upgrade" { +[[- $c := merge $c.upgrade $c ]] +[[ template "common/volumes" $c ]] + + network { + mode = "bridge" + } + + task "upgrade" { + driver = "[[ $c.nomad.driver ]]" + + config { +[[ template "common/image" $c ]] + } + + env { + PG_FROM = "[[ $c.from ]]" + PG_TO = "[[ $c.to ]]" + PG_INITDB_OPTS = "[[ range $idx, $opt := .pg.server.initdb ]]--[[ $opt | regexp.Replace ":(\\s+)" "$1" ]] [[ end ]]" + PG_UPGRADE_OPTS = "[[ range $idx, $opt := $c.options ]]--[[ $opt | regexp.Replace ":(\\s+)" "$1" | regexp.Replace "\"" "\\\"" ]] [[ end ]]" + DO_PG_UPGRADE = "[[ $c.enabled | ternary "true" "false" ]]" + } + + volume_mount { + volume = "data" + destination = "/data" + } + +[[ template "common/resources" $c ]] + } + } +} diff --git a/templates/patroni.yml.tpl b/templates/patroni.yml.tpl index 40ef54b..8666737 100644 --- a/templates/patroni.yml.tpl +++ b/templates/patroni.yml.tpl @@ -16,10 +16,9 @@ bootstrap: [[- end ]] initdb: - - data-checksum - - encoding: UTF-8 - #- locale-provider: icu - #- icu-locale: [[ .locale.lang ]] +[[- range $idx, $opt := .initdb ]] + - [[ $opt ]] +[[- end ]] post_bootstrap: /local/create_users.sh @@ -43,8 +42,8 @@ postgresql: on_start: /local/update_tags.sh connect_address: {{ env "NOMAD_HOST_ADDR_postgres" }} - bin_dir: /usr/pgsql-15/bin - data_dir: /data/db/15 + bin_dir: /usr/pgsql-[[ .pg.server.pg_version ]]/bin + data_dir: /data/db/[[ .pg.server.pg_version ]] listen: 0.0.0.0:{{ env "NOMAD_ALLOC_PORT_postgres" }} use_pg_rewind: True #remove_data_directory_on_rewind_failure: True diff --git a/variables.yml b/variables.yml index cd210b7..c980665 100644 --- a/variables.yml +++ b/variables.yml @@ -83,6 +83,10 @@ pg: # How many nodes should use synchronous replication. No effect unless count > 1 synchronous_node_count: 0 + # Options to pass to initdb when initializing the cluster + initdb: + - "data-checksum" + - "encoding: UTF-8" # Postgres parameters # The following memory related settings can be expressed as a percentage, and wil be computed based on the memory allocation of the container # shared_buffers effective_cache_size maintenance_work_mem wal_buffers work_mem @@ -365,14 +369,29 @@ pg: # Settings for major upgrades upgrade: - image: danielberteaud/pg-major-upgrade:latest + # Set to true to run the upgrade + enabled: false + + # Docker image to use + image: '[[ .docker.repo ]]postgres-major-upgrade:latest' + + # Custom env var to set in the container env: {} + # Options to pass to pg_upgrade + options: + - new-options=-c + - new-options=shared_preload_libraries=vectors.so + - clone + + # Major postgres versions, eg + # from: 15 + # to: 16 from: "" to: "" - do_upgrade: false + # Resource allocation resources: cpu: '[[ .pg.server.resources.cpu ]]' memory: '[[ .pg.server.resources.memory ]]'