I know that it is a typical issue, however I need a community help to resolve it. When I run docker-compose I get Connection refused: Is the server running on host "db" (172.21.0.2) and accepting web_1 TCP/IP connections on port 5432? Web portion of the docker-compose fails, but db runs. I can connect to the db using localhost:5432. It is not a wait issue, because tiangolo/uvicorn-gunicorn:python3.8-alpine3.10 implemented a wait mechanism – dockerize. Does anyone know where the issue is? Or perhaps could anyone just point me the right direction?
So my Dockerfile is
FROM tiangolo/uvicorn-gunicorn:python3.8-alpine3.10
# copy requirements file
COPY ./requirements.txt /usr/src/app/requirements.txt
# install dependencies
RUN set -eux
&& apk add --no-cache --virtual .build-deps build-base
libressl-dev libffi-dev gcc musl-dev python3-dev
postgresql-dev openssl
&& pip install --upgrade pip setuptools wheel
&& pip install -r /usr/src/app/requirements.txt
&& rm -rf /root/.cache/pip
# copy project
COPY . /app
My docker-compose is:
version: '3.7'
services:
db:
image: postgres:13-alpine
volumes:
- postgres_data:/var/lib/postgresql/data/
ports:
- 5432:5432
environment:
- POSTGRES_USER=postgres
- POSTGRES_PASSWORD=postgres
- POSTGRES_DB=api
web:
build: ./src
ports:
- 80:80
depends_on:
- db
environment:
- DATABASE_URL=postgresql://postgres:postgres@db/api
volumes:
postgres_data:
I added a wait using dockerize, however the web portion fails:
Attaching to gunicorn_db_1, gunicorn_web_1
db_1 | The files belonging to this database system will be owned by user "postgres".
db_1 | This user must also own the server process.
db_1 |
db_1 | The database cluster will be initialized with locale "en_US.utf8".
db_1 | The default database encoding has accordingly been set to "UTF8".
db_1 | The default text search configuration will be set to "english".
db_1 |
db_1 | Data page checksums are disabled.
db_1 |
db_1 | fixing permissions on existing directory /var/lib/postgresql/data ... ok
db_1 | creating subdirectories ... ok
db_1 | selecting dynamic shared memory implementation ... posix
db_1 | selecting default max_connections ... 100
db_1 | selecting default shared_buffers ... 128MB
web_1 | 2020/08/30 15:33:51 Waiting for: tcp://db:5432
web_1 | 2020/08/30 15:33:51 Problem with dial: dial tcp 172.21.0.2:5432: connect: connection refused. Sleeping 30s
db_1 | selecting default time zone ... Etc/UTC
db_1 | creating configuration files ... ok
db_1 | running bootstrap script ... ok
db_1 | performing post-bootstrap initialization ... ok
db_1 | syncing data to disk ... initdb: warning: enabling "trust" authentication for local connections
db_1 | You can change this by editing pg_hba.conf or using the option -A, or
db_1 | --auth-local and --auth-host, the next time you run initdb.
db_1 | ok
db_1 |
db_1 |
db_1 | Success. You can now start the database server using:
db_1 |
db_1 | pg_ctl -D /var/lib/postgresql/data -l logfile start
db_1 |
db_1 | waiting for server to start....2020-08-30 15:33:53.037 UTC [45] LOG: starting PostgreSQL 13beta3 (Debian 13~beta3-1.pgdg100+1) on x86_64-pc-linux-gnu, compiled by gcc (Debian 8.3.0-6) 8.3.0, 64-bit
db_1 | 2020-08-30 15:33:53.044 UTC [45] LOG: listening on Unix socket "/var/run/postgresql/.s.PGSQL.5432"
db_1 | 2020-08-30 15:33:53.059 UTC [46] LOG: database system was shut down at 2020-08-30 15:33:52 UTC
db_1 | 2020-08-30 15:33:53.066 UTC [45] LOG: database system is ready to accept connections
db_1 | done
db_1 | server started
db_1 | CREATE DATABASE
db_1 |
db_1 |
db_1 | /usr/local/bin/docker-entrypoint.sh: ignoring /docker-entrypoint-initdb.d/*
db_1 |
db_1 | 2020-08-30 15:33:53.399 UTC [45] LOG: received fast shutdown request
db_1 | waiting for server to shut down....2020-08-30 15:33:53.404 UTC [45] LOG: aborting any active transactions
db_1 | 2020-08-30 15:33:53.407 UTC [45] LOG: background worker "logical replication launcher" (PID 52) exited with exit code 1
db_1 | 2020-08-30 15:33:53.409 UTC [47] LOG: shutting down
db_1 | 2020-08-30 15:33:53.438 UTC [45] LOG: database system is shut down
db_1 | done
db_1 | server stopped
db_1 |
db_1 | PostgreSQL init process complete; ready for start up.
db_1 |
db_1 | 2020-08-30 15:33:53.530 UTC [1] LOG: starting PostgreSQL 13beta3 (Debian 13~beta3-1.pgdg100+1) on x86_64-pc-linux-gnu, compiled by gcc (Debian 8.3.0-6) 8.3.0, 64-bit
db_1 | 2020-08-30 15:33:53.531 UTC [1] LOG: listening on IPv4 address "0.0.0.0", port 5432
db_1 | 2020-08-30 15:33:53.531 UTC [1] LOG: listening on IPv6 address "::", port 5432
db_1 | 2020-08-30 15:33:53.539 UTC [1] LOG: listening on Unix socket "/var/run/postgresql/.s.PGSQL.5432"
db_1 | 2020-08-30 15:33:53.549 UTC [63] LOG: database system was shut down at 2020-08-30 15:33:53 UTC
db_1 | 2020-08-30 15:33:53.559 UTC [1] LOG: database system is ready to accept connections
web_1 | 2020/08/30 15:34:21 Connected to tcp://db:5432
gunicorn_web_1 exited with code 0
2
Answers
In first look your both files seemed good to me, actually adding a depends on should fix this but, according to documentation that doesn’t works that way. it express dependency between containers but that does not mean that a container will wait to other to be ready.
For older versions of Compose we were able to add a health check like this
But since it’s not supported anymore, best option to add a manual wait/sleep to that service.
There is a widely used bash script (wait for it) that you can use to test and wait on the availability of a TCP host and port. It’s also recommended solution from the Compose Documentation. You can copy wait for it into your files and starting using it right away.
Also you might want to check this out: Wait for it usage with docker
Just change the Version of your Docker-Compose to version: "3.5"
and that solved the problem