Docker镜像优化打包速度思考

 更新时间:2023年05月08日 10:24:27   作者:在下uptown  
本文主要介绍了Docker镜像优化打包速度思考,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧

前言

image.png

当下主流的业务架构大部分会选择用容器进行部署,并结合一些容器编排技术k8s技术。由于公司业务调整,jenkins打包的工作交付到我这边来负责。

结果组长上来就给我一个当头一棒,打包速度太慢,尽量优化下。我寻思过年也没忘记给拜年啊,不行把送出去的特产要回来吧,没啥用啊,净给整这一出。

说归说闹归闹,别拿绩效开玩笑,毕竟这年终还没发呢,该忍还得忍。君让臣死,臣不得不死,硬着头皮上吧

压缩镜像大小

优化第一步,瘦身,docker images查看了下基础服务的镜像大小,好家伙没有小于300M的,一个普通的小服务都要300多,显然在镜像体积上可以做做文章。

在Docker官方的建议中有一个点,使用更小的基础镜像。而在小的基础镜像中全网的一致答案都是alpine了。

alpine是一个非常特别的Linux版本,大小才5M左右,最早适用于嵌入式系统,但随着容器的流行,这个才5M大小的Linux在Docker中流行起来了,因为太小了,非常节省空间。

这里就对比下同样属于Linux镜像centeros与alpine的大小

REPOSITORY TAG IMAGE ID CREATED SIZE
alpine 3.16.2 9c6f07244728 7 days ago 5.54MB
centeros latest df5de72bdb3b 2 weeks ago 77.8MB

解决完基础镜像再来研究下第三方包是不是有可优化的点,仔细分析Dockerfile发现在构建过程中去拉代码打包的,那么构建过程中就会存在大量运行时不需要的包。这部分清掉基本上就可以瘦身成功了。

构建过程中,通过apk安装软件包时,可以指定虚拟包.build-deps,这样git之类的工具归属到虚拟包下,由于仅是构建阶段用到的命令,如执行npm installpip install,当把项目构建完以后,通过apk del .build-deps清理掉所有临时命令即可。

这样就可以保证构建出的镜像最小了。

利用缓存加速打包速度

docker本身是有缓存机制的,也就是每次build的时候会检查Dockerfile是否发生了变更,这里要注意是Dockerfile发生了变更,并不是代码发生变更。

得到这个结论的时候其实我是很迷惑的,照这么来说的话,Dockefile基本不会变,每次走缓存为什么jenkins打包速度这么慢呢。

后来在build命令里发现了端倪,有人在docker build时加了--no-cache参数,因为代码是在镜像构建时拉取的,每次走了缓存那么代码就不会拉取了,每次都会走缓存。所以为了避免代码不对运维在命令里加了--no-cache

那怎么办呢,因为Dockefile执行从上到下依次执行。把代码放到最低端,通过定义随机数或时间戳的方式使拉代码的命令缓存失效而不影响上面的第三方包的安装。

42ce9b8428f6effa08aa41798c5e798.jpg

岂不美哉。

Multi-stage Build

Docker 提供了 Multi-stage Build(多阶段构建),可以实现镜像瘦身。

我们将镜像构建分成两个阶段:

在 ”build“ 阶段依然采用 JDK 作为基础镜像,并利用 Maven 进行应用构建; 在最终发布的镜像中,我们会采用 JRE 版本作为基础镜像,并从”build“ 镜像中直接拷贝出生成的 jar 文件。这意味着在最终发布的镜像中,只包含运行时所需必要内容,不包含任何编译时依赖,大大减少了镜像体积。

FROM adoptopenjdk/openjdk8 AS build
RUN sed -i 's/archive.ubuntu.com/mirrors.aliyun.com/' /etc/apt/sources.list
RUN apt-get update
RUN apt-get install -y \
git \
maven
WORKDIR /tmp
RUN git clone https://github.com/spring-projects/spring-petclinic.git
WORKDIR /tmp/spring-petclinic
RUN mvn install
FROM adoptopenjdk/openjdk8:jre8u222-b10-alpine-jre
COPY --from=build /tmp/spring-petclinic/target/spring-petclinic-2.1.0.BUILD-SNAPSHOT.jar spring-petclinic-2.1.0.BUILD-SNAPSHOT.jar
CMD ["java","-jar","spring-petclinic-2.1.0.BUILD-SNAPSHOT.jar"]

Java打包测试

springboot背景下,在默认的maven打包插件加入分层打包配置

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <configuration>
                    <layers>
                        <enabled>true</enabled>
                    </layers>
                </configuration>
            </plugin>
        </plugins>
    </build>

再次进行打包分析操作mvn clean package,现在我们可以用下面命令来看分层打包编译的jar包结构 java -Djarmode=layertools -jar target/dockers-demo-0.0.1-SNAPSHOT.jar list

图片

可以看到layertools识别出jar包内将依赖打包到不同文件夹中,接下来我们改造下原有的dockerfile。

如果不分层打包的话,一次全量包会特别大。如果只更改部分代码的话。

FROM openjdk:8 as builder
RUN mvn clean package -DskipTests
# 声明端口并没有真正运行在这个端口
EXPOSE 8080
ADD ./target/*.jar ./app.jar
RUN java -Djarmode=layertools -jar app.jar extract
FROM openjdk:8-jre
MAINTAINER ttzommed@foxmail.com
WORKDIR application
# 复制第三方依赖、SpringBoot内部配置、快照依赖
COPY --from=builder application/dependencies/ ./
COPY --from=builder application/spring-boot-loader/ ./
COPY --from=builder application/snapshot-dependencies/ ./
COPY --from=builder application/application/ ./
EXPOSE 8080
ENTRYPOINT ["java", "org.springframework.boot.loader.JarLauncher"]

依靠docker的分层特征,分次加入文件即可达到分层加速打包的效果

到此这篇关于Docker镜像优化打包速度思考的文章就介绍到这了,更多相关Docker镜像打包优化内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • 快速安装Docker详细步骤教程

    快速安装Docker详细步骤教程

    这篇文章主要为大家详细的介绍了快速安装Docker的详细步骤教程,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2022-03-03
  • Docker动态给容器Container暴露端口操作

    Docker动态给容器Container暴露端口操作

    这篇文章主要介绍了Docker动态给容器Container暴露端口操作,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2020-11-11
  • docker网络双向连接详解

    docker网络双向连接详解

    在本篇文章里小编给大家分享的是一篇关于docker网络双向连接知识点详解内容,有兴趣朋友们可以参考学习下。
    2020-01-01
  • docker常用命令操作方法

    docker常用命令操作方法

    最近几天都在研究docker,今天给大家分享docker一些常用的命令,需要的朋友可以参考下
    2017-11-11
  • 解析Docker 下拉取oracle 11g镜像配置的问题

    解析Docker 下拉取oracle 11g镜像配置的问题

    这篇文章主要介绍了Docker 下拉取oracle 11g镜像配置的问题,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2021-09-09
  • Docker 基础网络配置详解

    Docker 基础网络配置详解

    这篇文章主要介绍了Docker 基础网络配置详解,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2018-09-09
  • Docker安装MS SQL Server并使用Navicat远程连接的操作方法

    Docker安装MS SQL Server并使用Navicat远程连接的操作方法

    SQL Server支持广泛的应用程序开发接口(API),包括T-SQL、ADO.NET、ODBC、OLE DB等,并支持多种操作系统,包括Windows、Linux和Docker等,这篇文章主要介绍了Docker安装MS SQL Server并使用Navicat远程连接,需要的朋友可以参考下
    2023-06-06
  • Spring Cloud中使用jib进行docker部署的步骤详解

    Spring Cloud中使用jib进行docker部署的步骤详解

    这篇文章主要介绍了Spring Cloud中使用jib进行docker部署的步骤详解,本文通过图文并茂的形式给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2020-09-09
  • 通过docker容器搭建lamp架构的流程

    通过docker容器搭建lamp架构的流程

    这篇文章主要介绍了dcoker容器搭建lamp架构,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2021-12-12
  • 使用Docker搭建MySQL主从数据库的方法步骤

    使用Docker搭建MySQL主从数据库的方法步骤

    本文主要介绍了使用Docker搭建MySQL主从数据库的方法步骤,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2023-01-01

最新评论