0

I am trying to configure the postgres docker image to run as part of the compose setup and have hit an unexpected problem with it. I suspect it is somehow related to the image itself and some internal details about it as it's extremely minimalistic:

services:
    db_master:
        image: postgres:16.1-bullseye
        user: postgres
        restart: on-failure:3
        hostname: postgres_master
        ports:
            - 0.0.0.0:25432:5432
        environment:
            POSTGRES_PASSWORD: postgres
            POSTGRES_USER: postgres
            POSTGRES_DB: postgres
            PGHOSTADDR: 0.0.0.0
            POSTGRES_NAME: test-postgres
            POSTGRES_ALLOW_EMPTY_PASSWORD: 1
            POSTGRES_HOST_AUTH_METHOD: "trust"
            POSTGRES_INITDB_ARGS: "--log_min_messages=DEBUG1 --archive_mode=on --archive_command='test ! -f /tmp/db_backup/%f && cp %p /tmp/db_backup/%f'"

which produces an error:

db_master_1 | initdb: unrecognized option '--log_min_messages=DEBUG1'

I have also tried to use a list for environment:

    db_backup:
        image: postgres_tm:latest
        user: postgres
        restart: unless-stopped
        hostname: postgres_backup
        ports:
            - 0.0.0.0:35432:5432
        environment:
            - POSTGRES_PASSWORD=postgres
            - POSTGRES_USER=postgres
            - POSTGRES_DB=postgres
            - PGHOSTADDR=0.0.0.0
            - POSTGRES_NAME=backup-postgres
            - POSTGRES_ALLOW_EMPTY_PASSWORD=1
            - POSTGRES_HOST_AUTH_METHOD="trust"
            - POSTGRES_INITDB_ARGS="--log_min_messages=DEBUG1 --archive_mode=on --archive_command='test ! -f /tmp/db_backup/%f && cp %p /tmp/db_backup/%f'"

which gives a slightly different error, suggesting the entire arg is packed into extra quotations and stored as such:

db_backup_1  | initdb: unrecognized option '--log_min_messages=DEBUG1 --archive_mode=on --archive_command='test ! -f /tmp/db_backup/%f && cp %p /tmp/db_backup/%f''
db_backup_1  | initdb: hint: Try "initdb --help" for more information.

I even tried using an .env file, but the outcome is the same every time.

I must say it's very confusing ass I've seen some complains about compose handling of multiargs when they are stored as environmental variable. I tried using a single argument only but it still complained about any type of argument, be it debug or archive_mode=on

my host environment details:

  • docker-compose version 1.25.0, build unknown
  • Docker version 24.0.7, build afdd53b

EDIT

After digging into the docker entrypoint script I can see that the initdb only initialises the database, but does not pass arguments used by postgres itself. I would really prefer to avoid having to bake custom made config file into the image and would prefer more docker-friendly setup that's easy to orchestrate and scale, so suggestions are very welcome and appreciated

1 Answer 1

0

You are missing some crucial information about containerized version of postgresql.

This question touches somewhat similar situation, albeit in kubernetes environment. But the principle is the same:

Postgresql docker image can only support several env parameters, POSTGRES_PASSWORD, POSTGRES_USER ,POSTGRES_DB, POSTGRES_INITDB_ARGS, POSTGRES_INITDB_WALDIR, POSTGRES_HOST_AUTH_METHOD, PGDATA.

So half of the stuff you are trying to pass in will not work as it is.

Normally something like PGOPTIONS would do the trick, but since that is not on the list (will give an error about needing to restart the service), you have in my opinion two options:

  1. Provide the options as arguments to the entrypoint set for the image. Meaning that you use command to append the existing entrypoint in the postgres-image.
services:
    db_master:
        image: postgres:16.1-bullseye
        command: -c log_min_messages=DEBUG1 -c archive_mode=on -c archive_command='test ! -f /tmp/db_backup/%f && cp %p /tmp/db_backup/%f'
        environment:
            POSTGRES_PASSWORD: postgres
            POSTGRES_USER: postgres
            POSTGRES_DB: postgres

or preferably

  1. Provide extra options with a config file instead. See for example this question for details.
services:
    db_master:
        image: postgres:16.1-bullseye
        command: -c log_min_messages=DEBUG1 -c archive_mode=on -c archive_command='test ! -f /tmp/db_backup/%f && cp %p /tmp/db_backup/%f'
        environment:
            POSTGRES_PASSWORD: postgres
            POSTGRES_USER: postgres
            POSTGRES_DB: postgres
        volumes:
           - ./customPostgresql.conf:/etc/postgresql.conf

Sign up to request clarification or add additional context in comments.

2 Comments

is using the config file and mounting it as a volume seen as /correct/ way of doing it in docker setup? I was under the impression that it would be frowned upon, but I have no problems adding config files with as part of my deployment. I'll ultimately want to use Kubernetes, so it will be a good read for me - thank you!
Not at all frowned upon, personally I think it's the correct way to do complex configurations with docker-compose. It scales nicely to whatever deployment you do (local, kubernetes, docker-compose) and it's a nice bonus that you can store the config file to version control if you want.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.