成功等待脚本后如何启动 docker 容器
Posted
技术标签:
【中文标题】成功等待脚本后如何启动 docker 容器【英文标题】:How to start docker container after succesfull wait-for-it script 【发布时间】:2017-02-13 03:09:10 【问题描述】:在启动其他应用程序之前,我正在使用等待它的脚本来检查数据库是否已启动。
#!/bin/bash
set -e
host="$1"
shift
cmd="$@"
until psql -h "$host" -U "postgres" -c '\l'; do
>&2 echo "Postgres is unavailable - sleeping"
sleep 1
done
>&2 echo "Postgres is up - executing command"
exec $cmd
我找到了这个脚本here。
现在我的应用程序容器停止运行mysql is up - executing command
。
所以脚本是成功的(db 正在运行),但我不清楚如何执行我的应用程序的 dockerfile 中的真正 CMD(在脚本之后)。
这是我的 dockerfile 的结尾:
COPY docker-entrypoint.sh /entrypoint.sh
COPY ./wait-for-it.sh wait-for-it.sh
ENTRYPOINT ["/entrypoint.sh"]
EXPOSE 2368
CMD ["npm", "start"]
【问题讨论】:
您可以删除ENTRYPOINT
并将两者都放入CMD
:CMD /entrypoint.sh && npm start
。
您好,我按照您说的做了,但是在 psql 检查成功后,似乎仍然无法在 CMD 上执行命令。所以图像是构建的,我的 docker-compose 执行等待它的脚本,它是成功的,所以我的容器可以启动但是它出错了。什么都没有发生
我认为等待它的脚本需要参数。试试/entrypoint.sh localhost npm start
。抱歉,我现在无法测试,因为我没有 Linux 机器。
【参考方案1】:
让我们先搞清楚几件事。当您在 Dockerfile 中同时使用 ENTRYPOINT
和 CMD
时,CMD
值将作为参数传递给 ENTRYPOINT
。因此,您当前在文件中的内容转换为
/entrypoint.sh npm start
这在您启动容器时执行。在不知道 entrypoint.sh
发生了什么的情况下,很难说这会产生什么影响。
码头工人
您可以进行以下更改,请尝试一下:
从Dockerfile
中删除ENTRYPOINT
。
将CMD
更改为以下内容:
CMD /wait-for-it.sh localhost && /entrypoint.sh npm start
这样做时,请调整以下内容:
wait-for-it.sh
的路径 - 请调整到您在 Dockerfile 中复制脚本文件的位置。我建议你将它复制到与entrypoint.sh
相同的文件夹中。
wait-for-it.sh
脚本文件的 localhost
参数,请替换为您的数据库主机。
上面的内容是运行wait-for-it.sh
脚本,然后,一旦数据库启动,它就会运行您在ENTRYPOINT
和CMD
中的上一个命令。它应该与您目前拥有的相当。
作为替代方案,您也可以从您的 entrypoint.sh
脚本调用 wait-for-it.sh
脚本并仅运行附加步骤(一旦等待脚本成功,npm start
)。由你决定...
Docker 编写
如果您使用 Docker-Compose 启动容器,您可以使用 docker-compose.yaml
文件中的 command
属性覆盖容器启动时执行的命令,例如
command: >
bash -c "
/wait-for-it.sh localhost
&& /entrypoint.sh npm start
"
请注意使用
bash -c
使用您选择的 shell(在本例中为 Bash)启动多个命令
引号,您需要它们才能有多行。
使用这种方法,您基本上可以将多个命令串联起来以依次运行,使用&&
运算符将它们组合起来。
等待脚本
顺便说一句:我将这个wait-for-it script 用于类似的目的,并以与上述相同的方式获得良好的结果。它比您的等待脚本版本更强大,并且几乎支持任何主机/端口组合。我用它来等待 MySQL - 你的问题不清楚是关于 MySQL 还是 PostgreSQL。
【讨论】:
感谢您的回复。我正在使用 mysql,但脚本是从 docker 文档中复制的,但适用于 mysql 并且运行良好。我也尝试使用 docker-compose 启动它,所以我还需要编辑 dockerfile 吗? 我已经用关于 Docker-Compose 的部分更新了答案以上是关于成功等待脚本后如何启动 docker 容器的主要内容,如果未能解决你的问题,请参考以下文章