My docker file is not building

vambePRO

7 months ago

Docker file:

Use Postgres 16 as the base image

FROM postgres:16

Install OpenSSL, sudo, and pglogical extension dependencies

RUN apt-get update && apt-get install -y openssl sudo postgresql-16-pglogical

Allow the postgres user to execute certain commands as root without a password

RUN echo "postgres ALL=(root) NOPASSWD: /usr/bin/mkdir, /bin/chown, /usr/bin/openssl" > /etc/sudoers.d/postgres

Add init scripts while setting permissions

COPY --chmod=755 init-ssl.sh /docker-entrypoint-initdb.d/init-ssl.sh
COPY --chmod=755 wrapper.sh /usr/local/bin/wrapper.sh

Create a configuration script to set wal_level to 'logical'

COPY --chmod=755 config-wal.sh /docker-entrypoint-initdb.d/config-wal.sh

Set environment variables to enable pglogical

ENV POSTGRESINITDBARGS="--wal-level=logical"

Ensure pglogical is loaded and enabled

RUN echo "sharedpreloadlibraries = 'pglogical'" >> /usr/share/postgresql/postgresql.conf.sample

Set executable permissions for the wrapper script

RUN chmod +x /usr/local/bin/wrapper.sh

ENTRYPOINT ["wrapper.sh"]
CMD ["postgres", "--port=5432"]

wrapper.sh:

!/bin/bash

exit as soon as any of these commands fail, this prevents starting a database without certificates

set -e

ls -l /usr/local/bin/wrapper.sh

Make sure there is a PGDATA variable available

if [ -z "$PGDATA" ]; then
echo "Missing PGDATA variable"
exit 1
fi

Set up needed variables

SSLDIR="/var/lib/postgresql/data/certs" INITSSLSCRIPT="/docker-entrypoint-initdb.d/init-ssl.sh" POSTGRESCONF_FILE="$PGDATA/postgresql.conf"

Regenerate if the certificate is not a x509v3 certificate

if [ -f "$SSLDIR/server.crt" ] && ! openssl x509 -noout -text -in "$SSLDIR/server.crt" | grep -q "DNS:localhost"; then
echo "Did not find a x509v3 certificate, regenerating certificates…"
bash "$INITSSLSCRIPT"
fi

Regenerate if the certificate has expired or will expire

2592000 seconds = 30 days

if [ -f "$SSLDIR/server.crt" ] && ! openssl x509 -checkend 2592000 -noout -in "$SSLDIR/server.crt"; then
echo "Certificate has or will expire soon, regenerating certificates…"
bash "$INITSSLSCRIPT"
fi

Generate a certificate if the database was initialized but is missing a certificate

Useful when going from the base postgres image to this ssl image

if [ -f "$POSTGRESCONFFILE" ] && [ ! -f "$SSLDIR/server.crt" ]; then echo "Database initialized without certificate, generating certificates…" bash "$INITSSL_SCRIPT"
fi

unset PGHOST to force psql to use Unix socket path

this is specific to Railway and allows

us to use PGHOST after the init

unset PGHOST

unset PGPORT also specific to Railway

since postgres checks for validity of

the value in PGPORT we unset it in case

it ends up being empty

unset PGPORT

Call the entrypoint script with the

appropriate PGHOST & PGPORT and redirect

the output to stdout if LOGTOSTDOUT is true

if [[ "$LOGTOSTDOUT" == "true" ]]; then
/usr/local/bin/docker-entrypoint.sh "$@" 2>&1
else
/usr/local/bin/docker-entrypoint.sh "$@"
fi

View Deploy details

ⓘ Deployment information is only viewable by project members and Railway employees.

Awaiting User Response

2 Replies

vambePRO

7 months ago

init-ssl.sh:

#!/bin/bash

# Log directory and file permissions

ls -ld "$SSL_DIR"

ls -l "$SSL_DIR"

if [ -z "$PGDATA" ]; then

echo "Error: PGDATA is not set."

exit 1

fi

# exit as soon as any of these commands fail, this prevents starting a database without certificates

set -e

# Set up needed variables

SSL_DIR="/var/lib/postgresql/data/certs"

SSL_SERVER_CRT="$SSL_DIR/server.crt"

SSL_SERVER_KEY="$SSL_DIR/server.key"

SSL_SERVER_CSR="$SSL_DIR/server.csr"

SSL_ROOT_KEY="$SSL_DIR/root.key"

SSL_ROOT_CRT="$SSL_DIR/root.crt"

SSL_V3_EXT="$SSL_DIR/v3.ext"

POSTGRES_CONF_FILE="$PGDATA/postgresql.conf"

# Use sudo to create the directory as root

sudo mkdir -p "$SSL_DIR"

# Use sudo to change ownership as root

sudo chown postgres:postgres "$SSL_DIR"

# Generate self-signed 509v3 certificates

# ref: https://www.postgresql.org/docs/16/ssl-tcp.html#SSL-CERTIFICATE-CREATION

openssl req -new -x509 -days "${SSL_CERT_DAYS:-820}" -nodes -text -out "$SSL_ROOT_CRT" -keyout "$SSL_ROOT_KEY" -subj "/CN=root-ca"

chmod og-rwx "$SSL_ROOT_KEY"

openssl req -new -nodes -text -out "$SSL_SERVER_CSR" -keyout "$SSL_SERVER_KEY" -subj "/CN=localhost"

chown postgres:postgres "$SSL_SERVER_KEY"

chmod og-rwx "$SSL_SERVER_KEY"

cat >| "$SSL_V3_EXT" <<EOF

[v3_req]

authorityKeyIdentifier = keyid, issuer

basicConstraints = critical, CA:TRUE

keyUsage = digitalSignature, nonRepudiation, keyEncipherment, dataEncipherment

subjectAltName = DNS:localhost

EOF

openssl x509 -req -in "$SSL_SERVER_CSR" -extfile "$SSL_V3_EXT" -extensions v3_req -text -days "${SSL_CERT_DAYS:-820}" -CA "$SSL_ROOT_CRT" -CAkey "$SSL_ROOT_KEY" -CAcreateserial -out "$SSL_SERVER_CRT"

chown postgres:postgres "$SSL_SERVER_CRT"

# PostgreSQL configuration, enable ssl and set paths to certificate files

cat >> "$POSTGRES_CONF_FILE" <<EOF

ssl = on

ssl_cert_file = '$SSL_SERVER_CRT'

ssl_key_file = '$SSL_SERVER_KEY'

ssl_ca_file = '$SSL_ROOT_CRT'

EOF

Nixpacks.toml:

[build]

builder = "dockerfile"

dockerfile = "Dockerfile.16"

[phases.setup]

aptPkgs = ["openssl", "wget", "postgresql"]

[phases.build]

cmds = ["chmod +x init-ssl.sh", "./init-ssl.sh"]

[start]

cmd = "./wrapper.sh"

[variables]

PGDATA = "/var/lib/postgresql/data"


7 months ago

Please provide a minimal reproducible example, in this case, the public repo that you are trying to deploy.


Status changed to Awaiting User Response railway[bot] 7 months ago


My docker file is not building - Railway Help Station