CMD
CMD
指令有三种形式:
CMD ["executable","param1","param2"]
(exec 形式,这个是推荐的形式)CMD ["param1","param2"]
(在ENTRYPOINT作为默认参数)CMD command param1 param2
(shell 形式)
在Dockerfile
中只能有一个 CMD
指令。如果你列出超过一个CMD
,那么只有最后一个 CMD
会生效。
CMD
的主要目的是为了提供运行容器的默认方法。这些默认方法可以包含一个可执行脚本,或者它们可以省略这个可执行脚本,在这种情况你还必须指定一个ENTRYPOINT
指令。
注意:如果
CMD
被用来提供作为ENTRYPOINT
指令的默认参数,CMD
和ENTRYPOINT
两个指令都要使用 JSON 数组格式来指定。
注意:
exec
被解析为 JSON 数组,意味着你必须使用双引号(")包围单词而不是单引号(’)。
注意:不像shell形式,exec形式不启用命令shell。这个意味着正常的 shell 处理过程是不会发生的。例如
CMD [ "echo", "$HOME" ]
是不会把$HOME变量替换。如果你想 shell 处理那么可以使用 shell形式或者直接执行一个shell,例如:CMD [ "sh", "-c", "echo $HOME" ]
。当使用 exec的形式和直接执行shell,与shell形式的情况 一样,这个是shell做环变量的扩展而不是docker。
当使用了shell或者exec的格式,CMD
指令会设置命令在镜像运行时执行。
如果你使用了CMD
的shell形式,那么<command>
将会在/bin/sh -c
运行。
FROM ubuntu
CMD echo "This is a test." | wc -
如果你想运行你的<command>
而不用shell那么你一定要把命令用JSON数组开表示和在执行脚本中使用全路径。CMD
推荐使用数组形式的格式。任何附加参数必须单独表示为数组中的字符串:
FROM ubuntu
CMD ["/usr/bin/wc","--help"]
如果你想你的容器每次运行一样的可执行脚本,那么你应该考虑组合使用ENTRYPOINT
和CMD
。参考ENTRYPOINT.
如果用户指定参数到docker run
,那么将会覆盖CMD
默认指定的参数。
注意:不要混淆
RUN
和CMD
。RUN
实际上运行一个命令和提交结果;CMD
在构建的过程作不是执行任何东西,但指定了镜像预设的命令(启动容器时运行的命令)。