#!/usr/bin/env bash set -Eeo pipefail file_env() { local var="$1" local fileVar="${var}_FILE" local def="${2:-}" if [ "${!var:-}" ] && [ "${!fileVar:-}" ]; then printf >&2 'error: both %s and %s are set (but are exclusive)\n' "$var" "$fileVar" exit 1 fi local val="$def" if [ "${!var:-}" ]; then val="${!var}" elif [ "${!fileVar:-}" ]; then val="$(< "${!fileVar}")" fi export "$var"="$val" unset "$fileVar" } docker_setup_env() { file_env 'POSTGRES_PASSWORD' file_env 'POSTGRES_REPLICATOR_USERNAME' file_env 'POSTGRES_REPLICATOR_PASSWORD' file_env 'POSTGRES_PGPOOL_USERNAME' file_env 'POSTGRES_PGPOOL_PASSWORD' } docker_temp_server_start() { NOTIFY_SOCKET= \ PGUSER="postgres" \ pg_ctl -D "${PGDATA}" \ -o "-c listen_addresses='' -p 5432" \ -w start } docker_temp_server_stop() { PGUSER="postgres" \ pg_ctl -D "${PGDATA}" -m fast -w stop } pg_setup_conf() { { printf "\n" printf "archive_command = '/bin/true'\n" printf "archive_mode = on\n" printf "hot_standby = on\n" printf "max_replication_slots = 10\n" printf "max_wal_senders = 10\n" printf "wal_compression = on\n" printf "wal_log_hints = on\n" if [[ -n $POSTGRES_MAX_CONNECTIONS ]]; then printf "\nmax_connections = '%s'\n" "$POSTGRES_MAX_CONNECTIONS" fi } >> "$PGDATA/postgresql.conf" } pg_setup_hba_conf() { { printf '\n' printf 'local all all trust\n' if [[ -n $POSTGRES_REPLICATOR_USERNAME ]]; then printf 'local replication %s trust\n' "$POSTGRES_REPLICATOR_USERNAME" printf 'host replication %s 127.0.0.1/32 trust\n' "$POSTGRES_REPLICATOR_USERNAME" printf 'host replication %s %s trust\n' "$POSTGRES_REPLICATOR_USERNAME" "${POSTGRES_NETWORK:-100.64.0.0/10}" fi if [[ -n $POSTGRES_PGPOOL_USERNAME ]]; then printf 'local replication %s trust\n' "$POSTGRES_PGPOOL_USERNAME" printf 'host replication %s 127.0.0.1/32 trust\n' "$POSTGRES_PGPOOL_USERNAME" printf 'host replication %s %s trust\n' "$POSTGRES_PGPOOL_USERNAME" "${POSTGRES_NETWORK:-100.64.0.0/10}" fi printf '\n' printf 'host all all all scram-sha-256\n' } >> "$PGDATA/pg_hba.conf" } if [ "$(id -u)" = '0' ]; then exec gosu postgres "$BASH_SOURCE" fi install --directory --owner postgres --group postgres --mode 700 /var/lib/postgresql/.ssh cp /ssh/* /var/lib/postgresql/.ssh/ chmod 600 /var/lib/postgresql/.ssh/* docker_setup_env if [[ ! -s "$PGDATA/PG_VERSION" ]]; then if [[ -z $POSTGRES_UPSTREAM ]] || [[ -z $POSTGRES_REPLICATOR_USERNAME ]]; then initdb --username=postgres --pwfile=<(printf "%s\n" "${POSTGRES_PASSWORD}") pg_setup_conf pg_setup_hba_conf if [[ -n $POSTGRES_REPLICATOR_USERNAME ]] || [[ -n $POSTGRES_PGPOOL_USERNAME ]]; then export PGPASSWORD="$POSTGRES_PASSWORD" docker_temp_server_start if [[ -n $POSTGRES_REPLICATOR_USERNAME ]]; then psql -c "CREATE USER ${POSTGRES_REPLICATOR_USERNAME} WITH REPLICATION LOGIN ENCRYPTED PASSWORD '${POSTGRES_REPLICATOR_PASSWORD}';" fi if [[ -n $POSTGRES_PGPOOL_USERNAME ]]; then psql -c "CREATE USER ${POSTGRES_PGPOOL_USERNAME} WITH LOGIN ENCRYPTED PASSWORD '${POSTGRES_PGPOOL_PASSWORD}';" psql -c "CREATE EXTENSION pgpool_recovery;" template1 fi docker_temp_server_stop unset PGPASSWORD fi else until pg_basebackup -h "${POSTGRES_UPSTREAM}" -U "${POSTGRES_REPLICATOR_USERNAME}" -D "${PGDATA}" -Fp -Xs -R &> /dev/null do echo "Upstream host not ready. Waiting for 5 minutes..." sleep 300 done fi fi sudo service ssh start postgres