在容器内运行服务时,让我们说命令是mongodb
docker run -d myimage
将立即退出,并返回容器ID.在我的CI脚本中,我在运行mongo容器后立即运行客户端来测试mongodb连接.问题是:客户端无法连接,因为服务尚未启动.除了sleep 10在我的脚本中添加一个大的,我没有看到任何等待容器启动和运行的选项.
Docker有一个wait在这种情况下不起作用的命令,因为容器不存在.这是码头工人的限制吗?谢谢
sup*_*ero 43
找到这个简单的解决方案,一直在寻找更好的东西但没有运气......
until [ "`/usr/bin/docker inspect -f {{.State.Running}} CONTAINERNAME`"=="true" ]; do
    sleep 0.1;
done;
或者如果你想等到容器报告为健康(假设你有健康检查)
until [ "`/usr/bin/docker inspect -f {{.State.Health.Status}} CONTAINERNAME`"=="healthy" ]; do
    sleep 0.1;
done;
Von*_*onC 38
正如在docker 1.12 的类似问题中所评论的那样
HEALTHCHECK根据docker/docker#23218将支持合并到上游- 可以考虑在开始下一个容器之前确定容器是否健康
这是自docker 1.12rc3(2016-07-14)以来可用的
docker-compose正在支持等待特定条件的功能.  
它使用
libcompose(因此我不必重建docker交互)并为此添加了一堆配置命令.在这里查看:https://github.com/dansteen/controlled-compose
您可以在Dockerfile中使用它,如下所示:
HEALTHCHECK --interval=5m --timeout=3s \
  CMD curl -f http://localhost/ || exit 1
官方文档:https://docs.docker.com/engine/reference/builder/#/healthcheck
小智 30
如果您不想公开端口,如果您打算链接容器并且可能正在运行多个实例进行测试,那么我发现这是在一行中执行此操作的好方法:)此示例为基于等待ElasticSearch准备好:
docker inspect --format '{{ .NetworkSettings.IPAddress }}:9200' elasticsearch | xargs wget --retry-connrefused --tries=5 -q --wait=3 --spider
这需要wget可用,这是Ubuntu的标准.它将在尝试之间重试5次,3秒,即使连接被拒绝,也不会下载任何内容.
Mar*_*ood 23
如果您启动的容器化服务不一定能很好地响应curl或wget请求(很可能是很多服务),那么您可以使用nc.
这是来自主机脚本的片段,它启动Postgres容器并在继续之前等待它可用:
POSTGRES_CONTAINER=`docker run -d --name postgres postgres:9.3`
# Wait for the postgres port to be available
until nc -z $(sudo docker inspect --format='{{.NetworkSettings.IPAddress}}' $POSTGRES_CONTAINER) 5432
do
    echo "waiting for postgres container..."
    sleep 0.5
done
编辑 - 此示例不要求您对正在测试的端口进行EXPOSE,因为它访问Docker为容器分配的"私有"IP地址.但是,这仅在docker主机守护程序正在侦听环回(127.xxx)时才有效.如果(例如)您在Mac上运行boot2docker VM,则无法使用此方法,因为您无法从Mac shell路由到容器的"私有"IP地址.
jpe*_*zzo 16
假设您知道MongoDB服务器的主机+端口(或者因为您使用了它-link,或者因为您注入了它们-e),您可以使用它curl来检查MongoDB服务器是否正在运行并接受连接.
以下代码段将尝试每秒连接,直到它成功:
#!/bin/sh
while ! curl http://$DB_PORT_27017_TCP_ADDR:$DB_PORT_27017_TCP_PORT/
do
  echo "$(date) - still trying"
  sleep 1
done
echo "$(date) - connected successfully"
我最终得到了类似的东西:
#!/bin/bash
attempt=0
while [ $attempt -le 59 ]; do
    attempt=$(( $attempt + 1 ))
    echo "Waiting for server to be up (attempt: $attempt)..."
    result=$(docker logs mongo)
    if grep -q 'waiting for connections on port 27017' <<< $result ; then
      echo "Mongodb is up!"
      break
    fi
    sleep 2
done
扔掉我自己的解决方案:
我正在使用docker网络,因此Mark的netcat技巧对我不起作用(无法从主机网络访问),而且Erik的想法对于postgres容器不起作用(即使postgres还没有,容器也被标记为正在运行可以连接到).所以我只是试图通过循环中的短暂容器连接到postgres:
#!/bin/bash
docker network create my-network
docker run -d \
    --name postgres \
    --net my-network \
    -e POSTGRES_USER=myuser \
    postgres
# wait for the database to come up
until docker run --rm --net my-network postgres psql -h postgres -U myuser; do
    echo "Waiting for postgres container..."
    sleep 0.5
done
# do stuff with the database...
如果您想等待打开的端口,可以使用这个简单的脚本:
until </dev/tcp/localhost/32022; do sleep 1; done
等待端口 32022 能够连接。
| 归档时间: | 
 | 
| 查看次数: | 57795 次 | 
| 最近记录: |