Docker Buildx 插件交叉编译镜像

开发环境

windows桌面版本,使用wsl子系统安装,启动windows子系统Ubuntu命令行;查看docker版本;

dxy@DESKTOP-9RDR780:~$ docker --version
Docker version 20.10.7, build f0df350

1、启用启用 buildx 插件

要想使用 buildx,首先要确保 Docker 版本不低于 19.03,同时还要通过设置环境变量 DOCKER_CLI_EXPERIMENTAL 来启用。可以通过下面的命令来为当前终端启用 buildx 插件:

 export DOCKER_CLI_EXPERIMENTAL=enabled

验证开启:

dxy@DESKTOP-9RDR780:~$ docker buildx version
github.com/docker/buildx v0.5.1-docker 11057da37336192bfc57d81e02359ba7ba848e4a

如果在某些系统上设置环境变量 DOCKER_CLI_EXPERIMENTAL 不生效(比如 Arch Linux),你可以选择从源代码编译:

export DOCKER_BUILDKIT=1
docker build --platform=local -o . git://github.com/docker/buildx
mkdir -p ~/.docker/cli-plugins && mv buildx ~/.docker/cli-plugins/docker-buildx

2、启用 binfmt_misc

如果你使用的是 Docker 桌面版(MacOS 和 Windows),默认已经启用了 binfmt_misc,可以跳过这一步。

如果你使用的是 Linux,需要手动启用 binfmt_misc。大多数 Linux 发行版都很容易启用,不过还有一个更容易的办法,直接运行一个特权容器,容器里面写好了设置脚本:

docker run --rm --privileged docker/binfmt:66f9012c56a8316f9244ffd7622d7c21c1f6f28d

建议将 Linux 内核版本升级到 4.x 以上,特别是 CentOS 用户,你可能会遇到错误。

验证是 binfmt_misc 否开启:

dxy@DESKTOP-9RDR780:~$  ls -al /proc/sys/fs/binfmt_misc/
total 0
drwxr-xr-x 2 root root 0 Oct 13 17:10 .
dr-xr-xr-x 1 root root 0 Oct 13 17:10 ..
-rw-r--r-- 1 root root 0 Oct 13 17:10 WSLInterop
-rw-r--r-- 1 root root 0 Oct 13 17:10 qemu-aarch64
-rw-r--r-- 1 root root 0 Oct 13 17:10 qemu-arm
-rw-r--r-- 1 root root 0 Oct 13 17:10 qemu-mips64
-rw-r--r-- 1 root root 0 Oct 13 17:10 qemu-mips64el
-rw-r--r-- 1 root root 0 Oct 13 17:10 qemu-ppc64le
-rw-r--r-- 1 root root 0 Oct 13 17:10 qemu-riscv64
-rw-r--r-- 1 root root 0 Oct 13 17:10 qemu-s390x
--w------- 1 root root 0 Oct 13 17:10 register
-rw-r--r-- 1 root root 0 Oct 13 17:10 status

验证是否启用了相应的处理器:

dxy@DESKTOP-9RDR780:~$ cat /proc/sys/fs/binfmt_misc/qemu-aarch64
enabled
interpreter /usr/bin/qemu-aarch64
flags: OCF
offset 0
magic 7f454c460201010000000000000000000200b700
mask ffffffffffffff00fffffffffffffffffeffffff

3、从默认的构建器切换到多平台构建器

Docker 默认会使用不支持多 CPU 架构的构建器,我们需要手动切换。

先创建一个新的构建器:

dxy@DESKTOP-9RDR780:~$ docker buildx create --use --name mybuilder
mybuilder

启动构建器:

dxy@DESKTOP-9RDR780:~$ docker buildx inspect mybuilder --bootstrap
[+] Building 40.1s (1/1) FINISHED
 => [internal] booting buildkit                                                                                   39.9s
 => => pulling image moby/buildkit:buildx-stable-1                                                                38.1s
 => => creating container buildx_buildkit_mybuilder0                                                               1.8s
Name:   mybuilder
Driver: docker-container
​
Nodes:
Name:      mybuilder0
Endpoint:  unix:///var/run/docker.sock
Status:    running
Platforms: linux/amd64, linux/amd64/v2, linux/amd64/v3, linux/arm64, linux/riscv64, linux/ppc64le, linux/s390x, linux/386, linux/mips64le, linux/mips64, linux/arm/v7, linux/arm/v6

查看当前使用的构建器及构建器支持的 CPU 架构,可以看到支持很多 CPU 架构:

dxy@DESKTOP-9RDR780:~$  docker buildx ls
NAME/NODE     DRIVER/ENDPOINT             STATUS                 PLATFORMS
mybuilder *   docker-container
  mybuilder0  unix:///var/run/docker.sock running                linux/amd64, linux/amd64/v2, linux/amd64/v3, linux/arm64, linux/riscv64, linux/ppc64le, linux/s390x, linux/386, linux/mips64le, linux/mips64, linux/arm/v7, linux/arm/v6
desktop-linux                             protocol not available
default       docker
  default     default                     running                linux/amd64, linux/arm64, linux/riscv64, linux/ppc64le, linux/s390x, linux/386, linux/arm/v7, linux/arm/v6

4、镜像构建

构建前准备源文件,并编写dockerfile文件:

go代码:

package main
​
import (
        "fmt"
        "runtime"
)
​
func main() {
        fmt.Printf("Hello, %s!\n", runtime.GOARCH)
}

dockerfile:

FROM golang:alpine AS builder
RUN mkdir /app
ADD . /app/
WORKDIR /app
RUN go mod init hello
RUN go build -o hello .
​
FROM alpine
RUN mkdir /app
WORKDIR /app
COPY --from=builder /app/hello .
CMD ["./hello"]

使用buildx进行交叉编译:

dxy@DESKTOP-9RDR780:~$ sudo docker buildx build -t yangchuansheng/hello-arch --platform=linux/arm64 -o type=docker .
[+] Building 47.3s (16/16) FINISHED
 => [internal] load build definition from Dockerfile                                                                                                                                                                                    0.0s
 => => transferring dockerfile: 32B                                                                                                                                                                                                     0.0s
 => [internal] load .dockerignore                                                                                                                                                                                                       0.0s
 => => transferring context: 2B                                                                                                                                                                                                         0.0s
 => [internal] load metadata for docker.io/library/alpine:latest                                                                                                                                                                       24.1s
 => [internal] load metadata for docker.io/library/golang:alpine                                                                                                                                                                       24.1s
 => [internal] load build context                                                                                                                                                                                                       3.2s
 => => transferring context: 6.33MB                                                                                                                                                                                                     3.1s
 => [builder 1/6] FROM docker.io/library/golang:alpine@sha256:f3e683657ddf73726b5717c2ff80cdcd9e9efb7d81f77e4948fada9a10dc7257                                                                                                          0.0s
 => [stage-1 1/4] FROM docker.io/library/alpine@sha256:bc41182d7ef5ffc53a40b044e725193bc10142a1243f395ee852a8d9730fc2ad                                                                                                                 0.0s
 => CACHED [stage-1 2/4] RUN mkdir /app                                                                                                                                                                                                 0.0s
 => CACHED [stage-1 3/4] WORKDIR /app                                                                                                                                                                                                   0.0s
 => CACHED [builder 2/6] RUN mkdir /app                                                                                                                                                                                                 0.0s
 => [builder 3/6] ADD . /app/                                                                                                                                                                                                          14.4s
 => [builder 4/6] WORKDIR /app                                                                                                                                                                                                          0.0s
 => [builder 5/6] RUN go mod init hello                                                                                                                                                                                                 0.7s
 => [builder 6/6] RUN go build -o hello .                                                                                                                                                                                               3.7s
 => [stage-1 4/4] COPY --from=builder /app/hello .                                                                                                                                                                                      0.0s
 => exporting to image                                                                                                                                                                                                                  0.1s
 => => exporting layers                                                                                                                                                                                                                 0.1s
 => => writing image sha256:e7a8547f3d0888066f50b6eeaff576571901bbbf2d9ede9b71a290375f4e08d1                                                                                                                                            0.0s
 => => naming to docker.io/yangchuansheng/hello-arch

这里构建命令指定了type为docker,将镜像保存在本地;

5、测试多平台镜像

由于之前已经启用了 binfmt_misc,现在我们就可以运行任何 CPU 架构的 Docker 镜像了,因此可以在本地系统上测试之前生成的 镜像是否有问题。

首先列出每个镜像的 digests

dxy@DESKTOP-9RDR780:~$ docker buildx imagetools inspect yangchuansheng/hello-arch
Name:      docker.io/yangchuansheng/hello-arch:latest
MediaType: application/vnd.docker.distribution.manifest.list.v2+json
Digest:    sha256:ec55f5ece9a12db0c6c367acda8fd1214f50ee502902f97b72f7bff268ebc35a
​
Manifests:
  Name:      docker.io/yangchuansheng/hello-arch:latest@sha256:38e083870044cfde7f23a2eec91e307ec645282e76fd0356a29b32122b11c639
  MediaType: application/vnd.docker.distribution.manifest.v2+json
  Platform:  linux/arm/v7
​
  Name:      docker.io/yangchuansheng/hello-arch:latest@sha256:de273a2a3ce92a5dc1e6f2d796bb85a81fe1a61f82c4caaf08efed9cf05af66d
  MediaType: application/vnd.docker.distribution.manifest.v2+json
  Platform:  linux/arm64
​
  Name:      docker.io/yangchuansheng/hello-arch:latest@sha256:8b735708d7d30e9cd6eb993449b1047b7229e53fbcebe940217cb36194e9e3a2
  MediaType: application/vnd.docker.distribution.manifest.v2+json
  Platform:  linux/amd64

运行每一个镜像并观察输出结果:

dxy@DESKTOP-9RDR780:~$ docker run --rm docker.io/yangchuansheng/hello-arch:latest
WARNING: The requested image's platform (linux/arm64) does not match the detected host platform (linux/amd64) and no specific platform was requested
Hello, arm64!
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值