我们在打包多个镜像的时候,通常都是通过将所有的命令写到Dockerfile
文件中。
但是这样可能会出现一个问题就是,在打包的过程中,我们可能会下载一些网络资源到构建的过程中。
又或者是,我们可能要将源文件复制到镜像中进行构建。这样就被别人可以看到我们的源码了。
为了解决这些问题。我们可以使用多阶段构建来解决
下面以减少镜像大小为基础来介绍多阶段构建。
需求
使用php
官网的基础镜像,在基础镜像的基础上安装一个swoole
扩展。
完成需求
- 找到
php
官方的Docker1
docker pull php:7.2.34-cli-alpine3.12
- 创建
Dockerfile
文件。添加swoole
扩展
参考swoole
官网。https://wiki.swoole.com/#/environment
创建Dockerfile
文件
1
2
3
4
5
6
7
8
9
10
11
FROM php:7.2.34-cli-alpine3.12
RUN apk add autoconf \
&& apk add build-base \
&& wget https://github.com/swoole/swoole-src/archive/refs/tags/v4.8.6.tar.gz \
&& tar xzvf v4.8.6.tar.gz \
&& cd swoole-src-4.8.6/ \
&& phpize \
&& ./configure \
&& make && make install \
&& docker-php-ext-enable swoole
- 运行命令。进行构建
1
2
3
4
5
6
# 运行命令构建镜像
docker build -t swoole_test:0.1 .
# 查看镜像
docker image ls | grep swoole_test
#镜像大小 555MB
通过结果我们看到。直接使用Dockerfile
进行打包的大小为555MB
。已经非常大了。
要知道,我们的基础镜像才几十MB
多阶段构建
将Dockerfile文件改为
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
FROM php:7.2.34-cli-alpine3.12
RUN apk add autoconf \
&& apk add build-base \
&& wget https://github.com/swoole/swoole-src/archive/refs/tags/v4.8.6.tar.gz \
&& tar xzvf v4.8.6.tar.gz \
&& cd swoole-src-4.8.6/ \
&& phpize \
&& ./configure \
&& make && make install \
&& docker-php-ext-enable swoole
# -------------
FROM php:7.2.34-cli-alpine3.12
COPY --from=0 /usr/local/lib/php/extensions/no-debug-non-zts-20170718/swoole.so /usr/local/lib/php/extensions/no-debug-non-zts-20170718/swoole.so
COPY --from=0 /usr/local/include/php/ext/swoole /usr/local/include/php/ext/swoole
RUN apk add build-base && docker-php-ext-enable swoole
原理就是,先通过一个Dockerfile
进行打包。等需要的扩展全部安装好了之后。
重新使用一个Dockerfile
。将生成好的文件复制过来即可。这样就完成了打包的过程。
运行命令进行打包
1
2
3
4
5
6
docker build -t swoole_test:0.2 .
# 查看镜像信息
docker image ls | grep swoole_test
#镜像大小330MB
我们可以看到。这个镜像就小了很多了。
其实还可以做到更小。
例如,官方的swoole.alpine镜像才30M左右。
可参考swoole
官方的构建镜像。更加小。但是好像并没有采用多阶段构建
https://github.com/swoole/docker-swoole
参考文档
- https://yeasy.gitbook.io/docker_practice/image/multistage-builds
- https://wiki.swoole.com/#/environment