8、Docker镜像瘦身

Docker镜像瘦身

一、 常见docker镜像瘦身方法

在 Docker 镜像瘦身方面,有多种工具和技术可以帮助你显著减小镜像体积,提升构建和部署效率。以下是常用的工具和方法:


1. 基础优化方法

① 多阶段构建(Multi-stage Builds)
  • 原理 :在 Dockerfile 中使用多个 FROM 阶段,仅保留最终需要的文件。

  • 示例

    dockerfile 复制代码
    # 第一阶段:编译环境
    FROM golang:1.21 AS builder
    WORKDIR /app
    COPY . .
    RUN go build -o myapp .
    
    # 第二阶段:运行环境(仅复制二进制文件)
    FROM alpine:latest
    COPY --from=builder /app/myapp /usr/local/bin/
    CMD ["myapp"]
  • 效果:避免将编译工具链打包到最终镜像中。

② 选择最小化基础镜像
  • 优先使用 alpinedistrolessscratch 镜像:

    dockerfile 复制代码
    FROM alpine:3.19  # 仅 5MB 左右
    # 或 Google 的 distroless(无 shell 和包管理器)
    FROM gcr.io/distroless/static-debian12
③ 合并 RUN 命令
  • 减少镜像层数,清理临时文件:

    dockerfile 复制代码
    RUN apt-get update && \
        apt-get install -y curl && \
        rm -rf /var/lib/apt/lists/*

2. 专用瘦身工具

① Dive
  • 功能:交互式分析镜像每层内容,找出冗余文件。

  • 安装

    bash 复制代码
    brew install dive  # macOS
    sudo apt-get install dive  # Debian/Ubuntu
  • 使用

    bash 复制代码
    dive build -t my-image:latest .
② Docker Slim
  • 原理:动态分析容器运行时的文件依赖,删除未使用的文件。

  • 安装

    bash 复制代码
    curl -sL https://downloads.dockerslim.com/releases/1.40.0/dist_linux.tar.gz | tar -xz
  • 使用

    bash 复制代码
    docker-slim build --target my-image:latest
  • 效果:可减少 50%~90% 体积。

③ Skopeo + Buildah
  • 场景 :替代 docker build,支持更灵活的镜像构建和压缩。

    bash 复制代码
    buildah bud --layers=false -t my-image .  # 禁用缓存层
    skopeo copy docker://my-image oci://my-image-optimized
④ Whaler
  • 功能:逆向分析已有镜像的构建过程,找出优化点。

    bash 复制代码
    docker run -v /var/run/docker.sock:/var/run/docker.sock pegleg/whaler -s my-image

3. 高级技巧

① 删除非必要文件
  • 手动清理缓存、文档、测试文件:

    dockerfile 复制代码
    RUN find /usr -name "*.doc" -delete && \
        rm -rf /var/cache/apk/*
② 使用 UPX 压缩二进制文件
  • 对 Go、C++ 等静态编译的程序进一步压缩:

    dockerfile 复制代码
    RUN upx --best --lzma /usr/local/bin/myapp
③ 分块构建(适用于微服务)
  • 将静态文件(如前端资源)分离到独立镜像,通过 CDN 分发。

4. 效果对比

工具/方法 适用场景 体积减少幅度
多阶段构建 编译型语言(Go/Rust) 50%~90%
Alpine 基础镜像 所有场景 60%~80%
Docker Slim 已存在的镜像 30%~90%
Dive 分析 诊断冗余文件 依赖手动清理

5. 自动化集成

  • CI/CD 流水线:在构建阶段加入瘦身步骤(例如 GitLab CI):

    yaml 复制代码
    build:
      stage: build
      script:
        - docker build -t my-image .
        - docker-slim build --target my-image

通过组合使用这些工具和方法,可以轻松将几百 MB 的镜像压缩到几十 MB。建议从 多阶段构建最小化基础镜像 开始,再通过 DiveDocker Slim 进一步优化。

二、 docker-slim命令

docker-slim 是一个用于优化 Docker 镜像的工具,它通过静态分析和动态分析(运行容器)来瘦身镜像,去除不必要的文件和依赖。以下是 docker-slim 的常用命令和使用方式:


1. 安装 Docker Slim(必须使用最新版本)

在开始前,确保已安装 docker-slim

bash 复制代码
https://github.com/slimtoolkit/slim/releases/tag/1.40.11
export PATH=$PATH:/slimPath
##永久生效
ln -s 
vim /etc/profile

2. 基本命令

(1)镜像分析

分析镜像但不生成优化后的镜像:

bash 复制代码
docker-slim xray --target IMAGE_NAME:TAG
(2)镜像瘦身

对镜像进行瘦身(生成优化后的镜像):

bash 复制代码
docker-slim build --target IMAGE_NAME:TAG
  • 默认会生成一个名为 <原镜像名>.slim 的新镜像。
  • 例如:原镜像是 nginx:alpine,瘦身后生成 nginx.slim:latest

3. 常用参数

参数 说明
--target 指定要优化的镜像(必需)
--http-probe 启用 HTTP 探针(默认启用,检测容器暴露的端口和服务)
--http-probe-cmd 自定义 HTTP 探针的请求(例如测试 API 端点)
--show-clogs 显示容器运行时的日志
--expose 指定容器暴露的端口(如果未自动检测到)
--env 传递环境变量给容器(例如 --env VAR=value
--entrypoint 覆盖容器的默认入口点
--cmd 覆盖容器的默认命令
--pull 拉取目标镜像(如果本地不存在)
--dockerfile 指定 Dockerfile 路径(用于补充分析)
--publish-exposed-ports 显式发布端口
--network 执行网络模式

4. 高级用法

(1)自定义输出镜像名称
bash 复制代码
docker-slim build --target nginx:alpine --tag nginx:custom-slim
(2)禁用 HTTP 探针
bash 复制代码
docker-slim build --target nginx:alpine --http-probe=false
(3)保留指定文件/目录

通过 --include-path 保留必要的文件:

bash 复制代码
docker-slim build --target myapp --include-path /app/configs

默认会生成瘦身报告,报告会保存在 执行命令时的当前目录下:slim.report.json文件中。


5. 示例

示例 1:瘦身一个 Python Flask 应用
bash 复制代码
docker-slim build \
  --target my-flask-app:latest \
  --http-probe-cmd /api/health \
  --show-clogs
示例 2:分析但不优化镜像
bash 复制代码
docker-slim xray --target redis:alpine

6. 注意事项

  1. 动态分析docker-slim 会临时运行容器,因此确保目标镜像的默认命令/入口点能够正常启动服务。
  2. 兼容性 :某些镜像(如基于 scratch 的极简镜像)可能不兼容。
  3. 调试 :如果瘦身后镜像无法运行,检查日志(--show-clogs)或使用 docker-slim debug 调试。

7. 更多帮助

查看完整文档:

bash 复制代码
docker-slim --help
docker-slim build --help

官方文档:https://docker-slim.io/

通过 docker-slim,你可以显著减少镜像大小(通常缩减 50%-90%),同时保持核心功能。

二、docker-squash

docker-squash 是一个用于优化 Docker 镜像的工具,它可以将 Docker 镜像中的多个层(layers)合并为一个或多个层,从而减少镜像的体积。Docker 镜像由多个层组成,每一层都代表文件系统的一部分更改。虽然这种分层结构有助于提高镜像的构建效率和共享性,但过多的层可能会导致镜像体积变大,影响镜像的传输和存储效率。

docker-squash 通过将多个层合并为一个层,可以有效地减少镜像的体积,同时保留镜像的功能。这对于优化生产环境中的 Docker 镜像非常有用。

安装 docker-squash

docker-squash 是一个 Python 工具,可以通过 pip 安装:

bash 复制代码
pip install docker-squash

使用 docker-squash

以下是 docker-squash 的基本用法:

  1. 拉取镜像

    首先,拉取需要优化的 Docker 镜像:

    bash 复制代码
    docker pull your-image:tag
  2. 使用 docker-squash 合并层

    运行 docker-squash 命令来合并镜像的层:

    bash 复制代码
    docker-squash -t your-image:squashed your-image:tag

    其中:

    • -t your-image:squashed:指定优化后的镜像名称和标签。
    • your-image:tag:需要优化的原始镜像。
  3. 验证优化后的镜像

    优化完成后,可以查看镜像的体积是否减小:

    bash 复制代码
    docker images
  4. 推送优化后的镜像

    如果需要,可以将优化后的镜像推送到 Docker Registry:

    bash 复制代码
    docker push your-image:squashed

注意事项

  • docker-squash 会删除镜像的历史记录,因此优化后的镜像将无法查看每一层的构建历史。
  • 使用 docker-squash 时,建议在开发和测试环境中进行充分验证,确保优化后的镜像功能正常。

替代方案

Docker 从 17.05 版本开始引入了多阶段构建(multi-stage builds),这是一种更优雅的优化镜像体积的方式。通过多阶段构建,可以在构建过程中丢弃不必要的层,从而减少最终镜像的体积。建议优先使用多阶段构建来优化镜像。

总结

docker-squash 是一个实用的工具,可以帮助减少 Docker 镜像的体积,但在使用时需要注意其局限性。结合多阶段构建等 Docker 原生功能,可以更好地优化镜像的体积和性能。

相关推荐
抠脚学代码2 小时前
Linux开发-->驱动开发-->字符设备驱动框架(2)
linux·运维·驱动开发
何中应2 小时前
Promehteus如何指定数据路径
运维·prometheus·监控
热爱Liunx的丘丘人2 小时前
Ansible的Playbook案例一
linux·运维·服务器·ansible
Minla2 小时前
kubectl常用命令别名设置(linux|windows)
linux·运维·服务器·k8s
学习论之费曼学习法2 小时前
用 Agent 自动化数据处理:从 2 小时到 15 分钟的效率革命
运维·自动化
cyber_两只龙宝2 小时前
【Oracle】Oracle之SQL的聚合函数和分组
linux·运维·数据库·sql·云原生·oracle
做运维的阿瑞2 小时前
Linux 系统启动过程解析
linux·运维·服务器
菜菜小狗的学习笔记2 小时前
八股(六)操作系统
linux·运维·服务器
zhou757712172 小时前
linux搭建 Hermes Agent(爱马仕)
linux·运维·服务器