Image 如何从图像生成Dockerfile?
是否可以从图像生成Dockerfile?我想知道有两个原因:Image 如何从图像生成Dockerfile?,image,repository,docker,Image,Repository,Docker,是否可以从图像生成Dockerfile?我想知道有两个原因: 我可以从存储库下载图像,但想看看生成它们的配方 我喜欢保存快照的想法,但一旦我完成了,最好有一个结构化的格式来检查所做的工作 在这一点上是不可能的(除非图像的作者明确地包含Dockerfile) 然而,它绝对是有用的!有两件事将有助于获得此功能 受信任的构建(详细信息请参见 生成过程生成的后续映像中更详细的元数据。从长远来看,元数据应指示生成映像的生成命令,这意味着可以从一系列映像重建Dockerfile 要了解docker映像是如何
在这一点上是不可能的(除非图像的作者明确地包含Dockerfile) 然而,它绝对是有用的!有两件事将有助于获得此功能
要了解docker映像是如何构建的,请使用
docker历史记录——无trunc
命令
您可以从映像生成docker文件,但它不会包含您想要完全了解映像生成方式的所有内容。合理地说,您可以提取docker文件的MAINTAINER、ENV、EXPOSE、VOLUME、WORKDIR、ENTRYPOINT、CMD和ONBUILD部分
以下脚本应适用于您:
#!/bin/bash
docker history --no-trunc "$1" | \
sed -n -e 's,.*/bin/sh -c #(nop) \(MAINTAINER .*[^ ]\) *0 B,\1,p' | \
head -1
docker inspect --format='{{range $e := .Config.Env}}
ENV {{$e}}
{{end}}{{range $e,$v := .Config.ExposedPorts}}
EXPOSE {{$e}}
{{end}}{{range $e,$v := .Config.Volumes}}
VOLUME {{$e}}
{{end}}{{with .Config.User}}USER {{.}}{{end}}
{{with .Config.WorkingDir}}WORKDIR {{.}}{{end}}
{{with .Config.Entrypoint}}ENTRYPOINT {{json .}}{{end}}
{{with .Config.Cmd}}CMD {{json .}}{{end}}
{{with .Config.OnBuild}}ONBUILD {{json .}}{{end}}' "$1"
我将此用作脚本的一部分,以将正在运行的容器重建为图像:
如果希望能够重新打包图像,Dockerfile主要很有用
需要记住的是,docker映像实际上可以是真实或虚拟机的tar备份。我用这种方式制作了几个docker映像。甚至构建历史记录显示,我导入一个巨大的tar文件作为创建映像的第一步
如何从图像生成或反转Dockerfile
你可以
alias dfimage="docker run -v /var/run/docker.sock:/var/run/docker.sock --rm alpine/dfimage"
dfimage -sV=1.36 nginx:latest
它将自动拉取目标docker映像并导出Dockerfile
。参数-sV=1.36
并不总是必需的
参考:
现在,如果选择特定标记,hub.docker.com将直接使用细节命令显示图像层
奖金
如果您想知道每个层中更改了哪些文件
alias dive="docker run -ti --rm -v /var/run/docker.sock:/var/run/docker.sock wagoodman/dive"
dive nginx:latest
在左侧,您可以看到每个层的命令,在右侧(使用tab跳转),黄线是在该层中更改某些文件的文件夹
(使用空格折叠目录)
旧答案
下面是旧的答案,它不再起作用了
$ docker pull centurylink/dockerfile-from-image
$ alias dfimage="docker run -v /var/run/docker.sock:/var/run/docker.sock --rm centurylink/dockerfile-from-image"
$ dfimage --help
Usage: dockerfile-from-image.rb [options] <image_id>
-f, --full-tree Generate Dockerfile for all parent layers
-h, --help Show this message
$docker从图像中提取centurylink/dockerfile
$alias dfimage=“docker run-v/var/run/docker.sock:/var/run/docker.sock--rm centurylink/dockerfile from image”
$dImage--帮助
用法:dockerfile-from-image.rb[选项]
-f、 --完整树为所有父层生成Dockerfile
-h、 --帮助显示此消息
我不知何故完全忽略了公认答案中的实际命令,因此,在这里,在它自己的一段中,我再次看到了它,看看有多少人像我一样
$ docker history --no-trunc <IMAGE_ID>
$docker历史记录--无trunc
bash解决方案:
docker history --no-trunc $argv | tac | tr -s ' ' | cut -d " " -f 5- | sed 's,^/bin/sh -c #(nop) ,,g' | sed 's,^/bin/sh -c,RUN,g' | sed 's, && ,\n & ,g' | sed 's,\s*[0-9]*[\.]*[0-9]*\s*[kMG]*B\s*$,,g' | head -n -1
逐步解释:
tac : reverse the file
tr -s ' ' trim multiple whitespaces into 1
cut -d " " -f 5- remove the first fields (until X months/years ago)
sed 's,^/bin/sh -c #(nop) ,,g' remove /bin/sh calls for ENV,LABEL...
sed 's,^/bin/sh -c,RUN,g' remove /bin/sh calls for RUN
sed 's, && ,\n & ,g' pretty print multi command lines following Docker best practices
sed 's,\s*[0-9]*[\.]*[0-9]*\s*[kMG]*B\s*$,,g' remove layer size information
head -n -1 remove last line ("SIZE COMMENT" in this case)
例如:
~ dih ubuntu:18.04
ADD file:28c0771e44ff530dba3f237024acc38e8ec9293d60f0e44c8c78536c12f13a0b in /
RUN set -xe
&& echo '#!/bin/sh' > /usr/sbin/policy-rc.d
&& echo 'exit 101' >> /usr/sbin/policy-rc.d
&& chmod +x /usr/sbin/policy-rc.d
&& dpkg-divert --local --rename --add /sbin/initctl
&& cp -a /usr/sbin/policy-rc.d /sbin/initctl
&& sed -i 's/^exit.*/exit 0/' /sbin/initctl
&& echo 'force-unsafe-io' > /etc/dpkg/dpkg.cfg.d/docker-apt-speedup
&& echo 'DPkg::Post-Invoke { "rm -f /var/cache/apt/archives/*.deb /var/cache/apt/archives/partial/*.deb /var/cache/apt/*.bin || true"; };' > /etc/apt/apt.conf.d/docker-clean
&& echo 'APT::Update::Post-Invoke { "rm -f /var/cache/apt/archives/*.deb /var/cache/apt/archives/partial/*.deb /var/cache/apt/*.bin || true"; };' >> /etc/apt/apt.conf.d/docker-clean
&& echo 'Dir::Cache::pkgcache ""; Dir::Cache::srcpkgcache "";' >> /etc/apt/apt.conf.d/docker-clean
&& echo 'Acquire::Languages "none";' > /etc/apt/apt.conf.d/docker-no-languages
&& echo 'Acquire::GzipIndexes "true"; Acquire::CompressionTypes::Order:: "gz";' > /etc/apt/apt.conf.d/docker-gzip-indexes
&& echo 'Apt::AutoRemove::SuggestsImportant "false";' > /etc/apt/apt.conf.d/docker-autoremove-suggests
RUN rm -rf /var/lib/apt/lists/*
RUN sed -i 's/^#\s*\(deb.*universe\)$/\1/g' /etc/apt/sources.list
RUN mkdir -p /run/systemd
&& echo 'docker' > /run/systemd/container
CMD ["/bin/bash"]
这源于@fallino的答案,通过使用的输出格式选项进行了一些调整和简化。由于macOS和Gnu/Linux具有不同的命令行实用程序,Mac需要不同的版本。如果您只需要其中一个,您可以使用这些行
#!/bin/bash
case "$OSTYPE" in
linux*)
docker history --no-trunc --format "{{.CreatedBy}}" $1 | # extract information from layers
tac | # reverse the file
sed 's,^\(|3.*\)\?/bin/\(ba\)\?sh -c,RUN,' | # change /bin/(ba)?sh calls to RUN
sed 's,^RUN #(nop) *,,' | # remove RUN #(nop) calls for ENV,LABEL...
sed 's, *&& *, \\\n \&\& ,g' # pretty print multi command lines following Docker best practices
;;
darwin*)
docker history --no-trunc --format "{{.CreatedBy}}" $1 | # extract information from layers
tail -r | # reverse the file
sed -E 's,^(\|3.*)?/bin/(ba)?sh -c,RUN,' | # change /bin/(ba)?sh calls to RUN
sed 's,^RUN #(nop) *,,' | # remove RUN #(nop) calls for ENV,LABEL...
sed $'s, *&& *, \\\ \\\n \&\& ,g' # pretty print multi command lines following Docker best practices
;;
*)
echo "unknown OSTYPE: $OSTYPE"
;;
esac
更新2018年12月宝马的答案 chenzj/dImage-如hub.docker.com上所述,从其他图像重新生成Dockerfile。因此,您可以按如下方式使用它:
docker pull chenzj/dfimage
alias dfimage="docker run -v /var/run/docker.sock:/var/run/docker.sock --rm chenzj/dfimage"
dfimage IMAGE_ID > Dockerfile
docker pull chenzj/dImage
别名dfimage=“docker run-v/var/run/docker.sock:/var/run/docker.sock--rm chenzj/dfimage”
dImage\u id
这是Docker的方法,应该标记为选中的答案。@jenson这不完全相同,可以覆盖95%。但不适用于压扁的图像。@BMW您能帮我解决这个问题吗?运行示例中的图像?/usr/lib/ruby/gems/2.2.0/gems/excon-0.45.4/lib/excon/unix\u socket.rb:14:in'connect\u nonblock':C连接被拒绝-connect(2)for/var/run/docker.sock(Errno::econnreference)(Excon::Errors::SocketError)centurylink/dockerfile from image不适用于新版本的docker。这一个适用于我:imagelayers.io似乎已损坏。它找不到任何图像,包括它的演示图像。这让我明白:json:无法将数组解组为类型的Go值。ContainerJSONC您能更详细地描述您的上一条评论吗?所有内容是否都在/只是按照正常?还是有特殊情况?我想这是一个6yo的答案,但我从daemon那里得到了错误响应:找不到页面
,那么为什么我们需要ub.docker.com/r/chenzj/dfimage
?这甚至是一个更新的答案。我猜是因为docker history
以相反的顺序打印Dockerfile行,并删除RUN
指令(您只会得到命令本身,而不是它前面的运行
keyworkd)和其他内容,因此您需要手动编辑它以获得可构建的Dockerfile。其他工具可能会自动为您进行编辑(我没有尝试过,所以我不知道。)@user7610您的命令仅显示从集线器提取的图像的历史记录。我如何在docker图像上看到我的命令?@BarzanHayati您可以将其作为一个新问题提问并链接到此处吗?提问时要非常具体。显示启动图像的命令,然后发出一些您希望稍后看到的命令,例如,然后停止容器(如果你实际上就是这么做的),然后询问如何检索发出的命令。谢谢。@user7610我可以问,但只要我问了,我就必须删除它,因为其他用户对重复的问题会给我加减分。最简单的解决方案。谢谢!这不会在分解多行运行语句时添加反斜杠。我已经在inspi中添加了我自己的答案mac上不提供this.tac的red,因此您可以选择下面的awk:| awk