docker中的entrypoint和cmd
关于docker中的entrypoint和cmd的疑惑很久了,一直搞不明白两者的区别,参阅两篇文章后逐渐解开疑惑,在此记录
参考:
docker - What is the difference between CMD and ENTRYPOINT in a Dockerfile? - Stack Overflow
ENTRYPOINT
entrypoint
参数我的理解是相当于一个指定一个解释器,就像shell的shebang。一切传入到容器的参数和选项都将由entrypoint
指定的值来处理。
也就是说指定了entrypoint
的值以后,就可以将容器本身当成一个二进制文件或者说可执行文件,在run生成容器实例时使用镜像描述的cmd
或者命令行中覆写的cmd
当作参数传入
如果entrypoint
没有指定,则执行cmd
中的第一个参数
这个参数只能出现一次
CMD
cmd
一般会当作entrypoint
的参数传入。如果entrypoint
没有指定,那么他将直接代替entrypoint
以执行后续命令,而不是作为参数
这个参数可与出现多次,但只有最后一次指定的会生效
小结
也就是说,ENTRYPOINT和CMD使用是相对灵活的。对于需要处理单一任务的容器可以指定ENTRYPOINT和CMD以专注特定任务;而只使用CMD而不使用ENTRYPOINT就可以随时更改容器的使用的主程序以完成不同的任务
ENTRYPOINT+CMD == 可执行文件+默认参数
ENTRYPOINT == 解释器
CMD == 直接执行命令
分析
1-拉取运行实例容器
以这个镜像grycap/cowsay 为例,粗浅分析一下
先run两个容器,后面再对他们的配置文件进行修改:
1 | docker run -i --name 1no_entry_point |
有一只牛在说话,说明成功了
2-修改配置文件
之后再修改它们的配置文件
容器配置文件路径在/var/lib/docker/containers/<容器id>/config.v2.json
这种修改配置方法应该是比较邪道的,网上查了资料都没有对这种方法的描述
打开后发现有一坨东西缩在一行,在vim下用python工具格式化一下。在vim下输入这一小段命令:
:%python3 -m json.tool
(会变成:'<,'>!python3 -m json.tool
)
格式整理好了,但是每次容器启动时停止都会将其转为一行的格式且变更为原来的配置。所以需要保证这时候容器处于停止状态
1no_entry_point
修改Path
Args
Cmd
Entrypoint
为以下值:
1entry_point
修改Path
Args
Cmd
Entrypoint
为以下值:
对于无ENTRYPOINT只有CMD的配置,
Path
为CMD第一个字段,剩下的字段分开塞进Args
对于ENTRIYPOINT和CMD都有的配置,
Path
应该也是ENTRYPOINT的第一个字段,剩下的CMD和ENTRYPOINT字段应该也要塞进Args
里(这里尚未验证)另外,该配置里那段奇怪的编码字段是中文“测试”的UTF-16编码
修改完毕后运行:
1 | ➜ ~ docker start -i 1no_entry_point |
可以看到两个效果是一样的。说到底只是一个把cowsay这个可执行文件放在entrypoint
;一个放在cmd
总结
虽然还不是很懂,但是我认为写了ENTRYPOINT的镜像对于处理一次性文件好像比较有优势。例如这样阅后即焚的容器,处理容器内部/etc/passwd
:
1 | ➜ ~ docker run --rm --entrypoint=/bin/cat alpine:latest /etc/passwd |
- 标题: docker中的entrypoint和cmd
- 作者: 7cmb
- 创建于 : 2024-04-28 16:32:05
- 更新于 : 2024-10-12 23:07:35
- 链接: https://7cmb.com/docker中的entrypoint和cmd/
- 版权声明: 本文章采用 CC BY-NC-SA 4.0 进行许可。