重用inheritance的图像的CMD或ENTRYPOINT
我怎样才能包括我自己的shell脚本CMD
的容器启动/重新启动/附加,而不删除由inheritance的图像使用的CMD
?
我正在使用这个,它执行我的脚本很好,但似乎覆盖PHP的CMD
:
FROM php COPY start.sh /usr/local/bin CMD ["/usr/local/bin/start.sh"]
我应该做什么不同? 我正在避免复制/粘贴父图像的ENTRYPOINT或CMD的前景,也许这不是一个好方法。
正如评论中所提到的,这里没有内置的解决scheme。 在Dockerfile中,您看不到当前CMD
或ENTRYPOINT
的值。 如果您控制上游基础映像并在其中包含此代码,则允许下游组件进行更改,那么拥有run-parts
解决scheme是非常好的。 但是docker有一个固有的问题会导致这个问题,容器应该只运行一个需要在前台运行的命令。 因此,如果上游映像启动,它将保持运行,而不会让后面的步骤有机会运行,所以您将留有复杂性以确定运行命令的顺序,以确保单个命令最终运行而不退出。
我的个人偏好是一个更简单和硬编码的选项,添加我自己的命令或入口点,并使我的命令的最后一步exec
上游命令。 您仍然需要手动识别要从上游Dockerfile调用的脚本名称。 但是现在在你的start.sh
,你将会拥有:
#!/bin/sh # run various pieces of initialization code here # ... # kick off the upstream command: exec /upstream-entrypoint.sh "$@"
通过使用exec
调用,您可以将pid 1传输到上游入口点,以便正确处理信号。 后面的"$@"
通过任何命令行parameter passing。 你可以使用set
来调整$@
的值,如果你想在你自己的start.sh
脚本中处理和提取一些参数的话。
如果基本映像不是你的,那么你不得不手动调用父命令。
如果你拥有父母的形象,你可以尝试camptocamp
的人在camptocamp
build议。
他们基本上使用通用脚本作为调用目录上run-parts
的入口点。 所做的是按字典顺序在该目录中运行所有脚本。 所以,当你扩展一个图像时,你只需要把你的新脚本放在同一个文件夹中。
但是,这意味着您必须通过添加可能无法控制的脚本前缀来维持秩序。 (想象一下,父图像决定稍后添加一个新的脚本…)。
无论如何,这可以工作。
更新#1
关于这个docker在容器运行之后有一个长期的讨论。 一个build议是将你的docker run或compose命令封装在shell脚本中,然后在其他命令上运行docker exec。
如果您想要使用这种方法,您基本上将父CMD作为运行命令,并在docker运行后将其作为docker exec。