containerd 镜像构建工具 -- nerdctl 和 buildkit
自我介绍
kubernetes在1.24版本之后就要抛弃docker-shim组件,容器运行时也是从docker转换到了containerd,而containerd自带的ctr命令并不好用,并且自身不支持构建镜像,并不像docker一样可以通过docker build来构建镜像containerd有一个子项目:nerdctl,用来兼容docker cli,可以像docker命令一样来管理本地的镜像和容器
wget下载的时候,需要加上--no-check-certificate参数,不然可能会返回Unable to establish SSL connection.这样的报错- 精简版 10.22MB
- 仅有
nerdctl命令
- 无法使用
nerdctl build命令,执行nerdctl build会出现如下报错:ERRO[0000] buildctl needs to be installed and buildkitd needs to be running- 完整版 221.6MB
- 不仅有
netdctl命令,还包含了buildkitd、buildctl、ctr、runc等containerd相关的命令,以及cni插件的二进制文件
nerdctl 精简版使用方法
- 下载精简版二进制文件后,只需要把解压出来的文件放到
/usr/bin目录下就可以了,当然有特殊需求,也可以解压到指定的路径,追加到PATH变量也可以nerdctl命令默认链接containerd.sock文件路径是/run/containerd/containerd.sock,如果和containerd配置文件内配置的containerd.sock不同,使用nerdctl命令的时候需要加上-a参数来指定containerd.sock路径
tar xf nerdctl-1.0.0-linux-amd64.tar.gz -C /usr/bin
随后就可以跟
docker命令一样去查看容器和镜像了
配置 nerdctl 参数自动补齐
参数自动补齐,需要系统已经安装了
bash-completion.noarch工具
echo 'source <(nerdctl completion bash)' >> /etc/profile
# 重新加载 /etc/profile 文件
source /etc/profile
nerdctl 命令验证
containerd和docker在kubernetes上使用的区别在于:containerd作为容器运行时的情况下,需要把镜像放到k8s.io这个namespace下
下载镜像
nerdctl -n k8s.io image pull centos:7
ctr 命令验证
ctr -n k8s.io image ls
nerdctl 完整版使用方法
- 用完整版是为了可以使用
nerdctl build命令,而nerdctl build命令其实时使用了buildctl命令来构建镜像- 完整版的
lib目录下有现成的buildkit.service文件,不过需要注意buildkitd命令的路径,文件内默认的路径是/usr/local/bin/buildkitd,需要把二进制文件放到指定路径下,或者修改文件的默认路径
cp lib/systemd/system/buildkit.service /lib/systemd/system/
buildkitd-buildkit 服务端命令
buildkitd有两种可用的worker,一个是runc,一个是containerd;默认使用runc,在buildkitd参数中为oci-worker
- 使用
containerd作为worker,需要增加--oci-worker=false --containerd-worker=true参数
- 和
nerdctl命令一样,默认调用的是/run/containerd/containerd.sock文件,如果路径不一致,需要增加--containerd-worker-addr参数来指定containerd.sock文件的路径- 使用
containerd作为worker时,会自动创建buildkit这个namespace,可以通过nerdctl namespace ls命令来查看
- 如果使用
nerdctl build命令构建镜像,想把构建的镜像放到buildkit这个namespace下面,需要使用nerdctl -n buildkit build命令来指定namespace- 如果使用
buildctl命令构建镜像,会自动将构建好的镜像放到buildkit这个namespace下面buildctl-buildkit 客户端命令
- 执行
nerdctl build需要保证buildctl命令在系统PATH环境变量中可查
启动 buildkit
systemctl enable buildkit.service --now
nerdcrtl 构建镜像
简单写一个
Dockerfile验证一下
FROM alpine:3.16.3
ENV LANG=en_US.UTF-8
ENV TZ="Asia/Shanghai"
RUN echo '/bin/sleep 315360000' > start.sh
CMD ["sh","start.sh"]
构建镜像
nerdctl build -t alpine:3.16.3-test .
使用
buildctl命令构建镜像
buildctl build --frontend dockerfile.v0 \
--local context=. \
--local dockerfile=. \
--output type=image,name=alpine:3.16.3-buildctl
--frontend-使用 dockerfile.v0 作为前端,还有 gateway.v0 可以作为前端--local context=-Dockerfile 执行构建时的路径上下文,比如在从目录中拷贝文件到镜像里--local dockerfile=-Dockerfile 文件所在路径--output name=-构建后的镜像名称
挺麻烦的,我还是选择
nerdctl命令把######################################## 不华丽的分割线 ########################################
自 2022-12-22 更新
后续使用过程中发现了一些问题,使用nerdctl命令创建容器的时候,默认的cni插件路径是/opt/cni/bin目录,但是我部署的时候,cni组件不在这个路径下,可以自己增加一个alias来指定路径
alias nerdctl='nerdctl --cni-path /approot/data/k8s/bin/'
再次使用
nerdctl run就不会报错找不到cni插件了,当然,这里的路径需要改成自己的cni插件的路径

浙公网安备 33010602011771号