skip to Main Content

Is there a way to initialize/start/keep running a PostgreSQL DB directly from a Dockerfile? I have the following Dockerfile.

# syntax = docker/dockerfile:1.4.0
FROM redhat/ubi8:latest

# Install a custom modified version of PostgreSQL 11
RUN dnf install myprecious-postgresql

# Prepare for PostgreSQL
ARG psqldb=/opt/myprecious/pg/var/lib/pgsql/11
ENV PGDATA=${psqldb}/data
RUN install -d -m 0755 /var/lock/subsys
RUN install -d -m 0755 -o postgres -g postgres ${psqldb}
RUN /etc/init.d/postgresql-${psqlversion} stop
RUN /etc/init.d/postgresql-${psqlversion} initdb

RUN /etc/init.d/postgresql-${psqlversion} start

USER postgres
RUN <<EOF cat >> /tmp/init.sql
CREATE USER hello WITH PASSWORD 'world';
CREATE DATABASE helloworld OWNER hello;
c helloworld
UPDATE pg_language SET lanpltrusted=true WHERE lanname='c';
GRANT ALL ON LANGUAGE c TO hello;
EOF

RUN until /opt/myprecious/pg/bin/pg_isready; do sleep 1; done;
RUN psql -f init.sql

But it looks like the postgresql never started (or stayed up).
enter image description here

Questions:

  • Is there a way to keep PostgreSQL up in between steps?
  • I don’t want to run PostgreSQL as a separate container, I want to just run this whole thing in a box, is it possible?
  • I don’t necessarily need to "keep it running", I could do it at the entry point, but I’d like to initialize DB to some state, is that possible?

2

Answers


  1. Chosen as BEST ANSWER

    Found a way to run PostgreSQL operations in between steps. Basically I just need to restart the db and wait for it to come up before running anything on it.

    Copy the following code into a script that will be run during a step:

    psqlversion=11
    pg_initd=/etc/init.d/postgresql-$psqlversion
    
    # We need to start postgresql again before modifying the PostgreSQL DB
    # since every RUN command in Dockerfile is like a snapshot
    $pg_initd start
    until /opt/carillon/pg/bin/pg_isready; do sleep 1; done;
    

    Anything after the above snippet, PostgreSQL will be available.


  2. Is there a way to keep PostgreSQL up in between steps?

    => nope. the idea of steps in Dockerfile is to prepare image

    you need something like init.sql

    Dockerfile
    
    FROM library/postgres
    COPY init.sql /docker-entrypoint-initdb.d/
    

    In init.sql you can put logic to run on empty db if you run the container in first time, on next container startup if db already initialized, than run of init.sql will be skipped

    See more details here
    How to create User/Database in script for Docker Postgres

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search