编写 Dockerfile 最佳实践
admin
2023-04-07 05:41:14
0次

官方仓库虽然有数十万计的免费镜像,但大多数无法直接满足公司业务需求,这就需要我们自己去定制镜像了。

Docker通过Dockerfile自动构建镜像,Dockerfile是一个包含用于组建镜像的文本文件,由一条一条的指令组成。

这里,给你提供4点编写建议,可帮助你编写高效易用的Dockerfile。

1. 减少镜像层

一次RUN指令形成新的一层,尽量Shell命令都写在一行,减少镜像层。
例如:

FROM centos:7
MAINTAINER www.ctnrs.com
RUN yum install epel-release -y 
RUN yum install -y gcc gcc-c++ make -y
RUN wget http://docs.php.net/distributions/php-5.6.36.tar.gz
RUN tar zxf php-5.6.36.tar.gz
RUN cd php-5.6.36
RUN ./configure --prefix=/usr/local/php 
RUN make -j 4 
RUN make install
EXPOSE 9000
CMD ["php-fpm"]

应该写成:

FROM centos:7
MAINTAINER www.ctnrs.com
RUN yum install epel-release -y && \
    yum install -y gcc gcc-c++ make

RUN wget http://docs.php.net/distributions/php-5.6.36.tar.gz && \
    tar zxf php-5.6.36.tar.gz && \
    cd php-5.6.36 && \
    ./configure --prefix=/usr/local/php && \
    make -j 4 && make install
EXPOSE 9000
CMD ["php-fpm"]

结果:12层 -> 6层

2. 优化镜像大小:清理无用数据

一次RUN形成新的一层,如果没有在同一层删除,无论文件是否最后删除,都会带到下一层,所以要在每一层清理对应的残留数据,减小镜像大小。

FROM centos:7
MAINTAINER www.ctnrs.com
RUN yum install epel-release -y && \
    yum install -y gcc gcc-c++ make gd-devel libxml2-devel \
    libcurl-devel libjpeg-devel libpng-devel openssl-devel \
    libmcrypt-devel libxslt-devel libtidy-devel autoconf \
    iproute net-tools telnet wget curl && \
    yum clean all && \
    rm -rf /var/cache/yum/*

RUN wget http://docs.php.net/distributions/php-5.6.36.tar.gz && \
    tar zxf php-5.6.36.tar.gz && \
    cd php-5.6.36 && \
    ./configure --prefix=/usr/local/php \
    make -j 4 && make install && \
    cd / && rm -rf php*

至少能节省几十M,甚至几百M。

3. 减少网络传输时间

最好在内部有一个存放软件包的地方,类似于上述的PHP官方下载地址:http://docs.php.net/distributions/php-5.6.36.tar.gz ,如果用到maven构建这样的操作,同时也更改为私有maven仓库,减少网络传输时间,提高镜像构建速度。

4. 多阶段进行镜像构建

如果运行一个项目,根据咱们上面的做法,是直接把代码拷贝到基础镜像里,如果是一个需要预先代码编译的项目呢?例如JAVA语言,如何代码编译、部署在一起完成呢!

上面做法需要事先在一个Dockerfile构建一个基础镜像,包括项目运行时环境及依赖库,再写一个Dockerfile将项目拷贝到运行环境中,有点略显复杂了。

像JAVA这类语言如果代码编译是在Dockerfile里操作,还需要把源代码构建进去,但实际运行时只需要构建出的包,这种把源代码放进去有一定安全风险,并且也增加了镜像体积。
为了解决上述问题,Docker 17.05开始支持多阶段构建(multi-stage builds),可以简化Dockerfile,减少镜像大小。

例如,构建JAVA项目镜像:

# git clone https://github.com/lizhenliang/tomcat-java-demo
# cd tomcat-java-demo
# vi Dockerfile
FROM maven AS build
ADD ./pom.xml pom.xml
ADD ./src src/
RUN mvn clean package

FROM lizhenliang/tomcat
RUN rm -rf /usr/local/tomcat/webapps/ROOT
COPY --from=build target/*.war /usr/local/tomcat/webapps/ROOT.war

# docker build -t demo:v1 .
# docker container run -d -v demo:v1

首先,第一个FROM 后边多了个 AS 关键字,可以给这个阶段起个名字。
然后,第二部分FROM用的我们上面构建的Tomcat镜像,COPY关键字增加了—from参数,用于拷贝某个阶段的文件到当前阶段。这样一个Dockerfile就都搞定了。

小结:镜像小有很多好处,例如快速部署、快速回滚。减少服务中断时间,同时镜像仓库占用磁盘空间也少了。

编写 Dockerfile 最佳实践

相关内容

热门资讯

空调连续工作多久需要停机休息 空调连续工作的时间取决于多个因素,包括空调的型号、功率、使用环境和维护情况等。一般来说,空调可以连续...
空调哪个符号是除湿的 空调除湿功能通常用一个水滴形状的符号表示。不同品牌和型号的空调遥控器可能会有所差异,但一般来说,除湿...
格力空调多长时间加一次氟利昂 1、一般情况下,空调对氟利昂的使用量是非常小的,所以在空调使用了四年左右的时候再考虑加也没问题。2、...
空调用多长时间需要加氟一次 一般情况下是五年。当出现以下这几种情况时,空调才需要加氟。1、空调的室内机和室外机各有两个接口,当接...
格调生活·C标思享荟:卡萨帝在... 9月12日的郑州龙湖金融岛,夜风轻拂,灯光璀璨。“C标时刻共传奇——卡萨帝思享荟暨20周年品牌盛典郑...
品牌价值破千亿、高端份额持续领... 9月12日,“C标时刻共传奇——卡萨帝思享荟暨20周年品牌盛典郑州站”在郑州龙湖金融岛举办。2026...
空调主板坏了修800还是换新的 空调主板坏了是修还是换新,需要考虑多个因素,以下是一些建议:1. 维修成本:如果维修费用较低,比如 ...
空调开多久需要休息多长时间 问题:空调开多久需要休息多长时间回答:1、在使用空调的过程中,一般空调开7~8个小时左右需要休息2~...
中央空调多长时间清洗一次 1、一般空调开机前清洗一次即可,空调开机中间时段再清洗一次,空调关机时清洗一次,这样比较合理。2、空...
中央空调氟利昂多久加一次 看空调制热和制冷程度,很多人的观点认为氟利昂必须一年放一次,其实这个观点是错误的,理解上面有点偏差,...