bash 成功等待脚本后如何启动docker容器
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/39860969/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to start docker container after succesfull wait-for-it script
提问by DenCowboy
I'm using a wait-for-it script to check if the database is up before I'm launching my other app.
在启动其他应用程序之前,我正在使用等待脚本来检查数据库是否已启动。
#!/bin/bash
set -e
host=""
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
I found this script here.
Now my app-container stops running with MySQL is up - executing command
.
So the script was successful (db is running) but it's not clear for me how to execute the real CMD (after the script) which is in my dockerfile of my app.
我在这里找到了这个脚本。现在我的应用程序容器停止运行MySQL is up - executing command
。所以脚本是成功的(db 正在运行),但我不清楚如何执行我的应用程序的 dockerfile 中的真正 CMD(在脚本之后)。
This is the end of my dockerfile:
这是我的 dockerfile 的结尾:
COPY docker-entrypoint.sh /entrypoint.sh
COPY ./wait-for-it.sh wait-for-it.sh
ENTRYPOINT ["/entrypoint.sh"]
EXPOSE 2368
CMD ["npm", "start"]
回答by nwinkler
Let's clear up a couple of things first. When you use both ENTRYPOINT
and CMD
in a Dockerfile, the CMD
value is passed to the ENTRYPOINT
as a parameter. So what you currently have in the file translates to
让我们先澄清几件事。当您在 Dockerfile 中同时使用ENTRYPOINT
和CMD
时,该CMD
值将ENTRYPOINT
作为参数传递给。所以你目前在文件中的内容转换为
/entrypoint.sh npm start
This is executed when you start the container. Without knowing what's happening in entrypoint.sh
, it's hard to tell what impact this has.
这是在您启动容器时执行的。在不知道 中发生了什么的情况下entrypoint.sh
,很难说这有什么影响。
Docker
码头工人
You could make the following changes, please give this a try:
您可以进行以下更改,请尝试一下:
- Remove the
ENTRYPOINT
from theDockerfile
. Change
CMD
to the following:CMD /wait-for-it.sh localhost && /entrypoint.sh npm start
- 取出
ENTRYPOINT
从Dockerfile
。 更改
CMD
为以下内容:CMD /wait-for-it.sh localhost && /entrypoint.sh npm start
When doing that, please adjust the following:
这样做时,请调整以下内容:
- The path for
wait-for-it.sh
- please adjust to wherever you're copying the script file in the Dockerfile. I suggest you copy it to the same folder asentrypoint.sh
. - The
localhost
argument for thewait-for-it.sh
script file, please replace with your database host.
- 路径
wait-for-it.sh
- 请调整到您在 Dockerfile 中复制脚本文件的任何位置。我建议您将其复制到与entrypoint.sh
. - 脚本文件的
localhost
参数wait-for-it.sh
,请替换为您的数据库主机。
What the above does, is run the wait-for-it.sh
script and then, once the database is up, it runs the previous command that you had in ENTRYPOINT
and CMD
. It should be comparable to what you currently have.
上面所做的是运行wait-for-it.sh
脚本,然后,一旦数据库启动,它就会运行您在ENTRYPOINT
和 中的上一个命令CMD
。它应该与您目前拥有的相当。
As an alternative, you could also call the wait-for-it.sh
script from your entrypoint.sh
script and only run the additional steps (npm start
once the wait script has succeeded). Up to you...
作为替代方案,您也可以wait-for-it.sh
从entrypoint.sh
脚本中调用脚本并仅运行附加步骤(npm start
等待脚本成功后)。由你决定...
Docker-Compose
Docker-Compose
If you are using Docker-Compose for starting up your containers, you can overwrite the command that is executed when the container starts using the command
attribute in your docker-compose.yaml
file, e.g.
如果您使用 Docker-Compose 来启动容器,则可以使用文件中的command
属性覆盖容器启动时执行的命令docker-compose.yaml
,例如
command: >
bash -c "
/wait-for-it.sh localhost
&& /entrypoint.sh npm start
"
Please note the use of
请注意使用
bash -c
for starting multiple commands using your shell of choice (Bash in this case)- the quotes, you'll need them for having multiple lines.
bash -c
使用您选择的 shell 启动多个命令(在本例中为 Bash)- 引号,您将需要它们来拥有多行。
Using this method, you can basically chain multiple commands to run after each other, combining them using the &&
operator.
使用这种方法,您基本上可以将多个命令串联在一起,然后使用&&
运算符将它们组合起来。
Wait-for-it Script
等待脚本
BTW: I use this wait-for-it script?for a similar purpose with good results in the same manner as described above. It's slightly more robust than you version of the wait script, and supports pretty much any host/port combination. I use it to wait for MySQL - your question is not clear whether it's about MySQL or PostgreSQL.
顺便说一句:我使用这个等待脚本?用于类似的目的,并以与上述相同的方式获得良好的结果。它比您的等待脚本版本稍微更健壮,并且几乎支持任何主机/端口组合。我用它来等待 MySQL - 你的问题不清楚是关于 MySQL 还是 PostgreSQL。