Docker wait for postgresql to be running

2019-02-03 15:31发布

I am using postgresql with django in my project. i've got them in different containers and the problem is that i need to wait for postgres before running django. At this time i am doing it with sleep 5 in command.sh file for django container. I also found that netcat can do the trick but i would prefer way without additional packages. curl and wget can't do this because they do not support postgres protocol. Is there a way to do it?

7条回答
欢心
2楼-- · 2019-02-03 15:45

The simplest solution is a short bash script:

while ! nc -z HOST PORT; do sleep 1; done;
./run-smth-else;
查看更多
孤傲高冷的网名
3楼-- · 2019-02-03 15:47

This will successfully wait for Postgres to start. (Specifically line 6). Just replace npm start with whatever command you'd like to happen after Postgres has started.

services:
  practice_docker: 
    image: dockerhubusername/practice_docker
    ports: 
      - 80:3000
    command: bash -c 'while !</dev/tcp/db/5432; do sleep 1; done; npm start'
    depends_on:
      - db
    environment:
      - DATABASE_URL=postgres://postgres:password@db:5432/practicedocker
      - PORT=3000   
  db:
    image: postgres
    environment:
      - POSTGRES_USER=postgres
      - POSTGRES_PASSWORD=password
      - POSTGRES_DB=practicedocker
查看更多
相关推荐>>
4楼-- · 2019-02-03 15:49

If you have psql you could simply add the following code to you .sh file:

RETRIES=5

until psql -h $PG_HOST -U $PG_USER -d $PG_DATABASE -c "select 1" > /dev/null 2>&1 || [ $RETRIES -eq 0 ]; do
  echo "Waiting for postgres server, $((RETRIES--)) remaining attempts..."
  sleep 1
done
查看更多
劫难
5楼-- · 2019-02-03 15:49

Maybe you could use docker compose to manage your containers.

Here is the documentation.

In its yaml file, you can set the links properties to express dependency between services. Then, the service will startup as you wish.

查看更多
We Are One
6楼-- · 2019-02-03 15:52

Problem with your solution tiziano is that curl is not installed by default and i wanted to avoid installing additional stuff. Anyway i did what bereal said. Here is the script if anyone would need it.

import socket
import time
import os

port = int(os.environ["DB_PORT"]) # 5432

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
while True:
    try:
        s.connect(('myproject-db', port))
        s.close()
        break
    except socket.error as ex:
        time.sleep(0.1)
查看更多
Animai°情兽
7楼-- · 2019-02-03 15:52

wait-for-it small wrapper scripts which you can include in your application’s image to poll a given host and port until it’s accepting TCP connections.

can be cloned in Dockerfile by below command

RUN git clone https://github.com/vishnubob/wait-for-it.git

docker-compose.yml

version: "2"
services:
   web:
     build: .
     ports:
       - "80:8000"
     depends_on:
       - "db"
     command: ["./wait-for-it/wait-for-it.sh", "db:5432", "--", "npm",  "start"]
   db:
     image: postgres
查看更多
登录 后发表回答