马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。
您需要 登录 才可以下载或查看,没有账号?立即注册
×
在 Ubuntu 20.04 基础镜像里构建带 ROS 的 Dockerfile,经常卡在这一句:apt-get update && apt-get upgrade -y && apt-get install -y net-tools ...,报 ERROR: failed to solve: process "/bin/bash -c ..." did not complete successfully: exit code: 100。反复 build 几次都是同一个错,多半不是 apt 本身的问题,而是镜像源地址在新版基础镜像里已经失效了。本文给出两种改法和一个必做的清理动作。
完整报错长什么样
ERROR: failed to solve: process "/bin/bash -c apt-get update && apt-get upgrade -y && apt-get install -y net-tools iputils-ping dnsutils libssl-dev ros-${ROS_DISTRO}-desktop ros-${ROS_DISTRO}-rmw-cyclonedds-cpp --no-install-recommends && rm -rf /var/lib/apt/lists/*" did not complete successfully: exit code: 100.
重复 build 了好几次都是这个错误,考虑镜像源问题,估计是 apt-get 相关的源地址访问不通。
修改方式一:换源到 /etc/apt/sources.list
在 Dockerfile 中,考虑在运行 apt-get 命令之前,插入下面几条 sed:
RUN sed -i 's@http://archive.ubuntu.com/@http://mirrors.tuna.tsinghua.edu.cn/@g' /etc/apt/sources.list \
&& sed -i 's@http://security.ubuntu.com/@http://mirrors.tuna.tsinghua.edu.cn/@g' /etc/apt/sources.list \
&& sed -i 's#http://ports.ubuntu.com/ubuntu-ports/#http://mirrors.tuna.tsinghua.edu.cn/ubuntu-ports/#g' /etc/apt/sources.list
问题来了:换源执行时间为 0.0s
改完上面那一段再跑,发现换源这步的执行时间为 0.0s。感觉镜像源可能没有写入 /etc/apt/sources.list,于是在 Dockerfile 里加了一行打印来确认:
RUN cat /etc/apt/sources.list
然后运行 docker build,加上 --progress=plain 让输出更细致:
docker build --rm --progress=plain --no-cache -f $BUILD_CONTEXT -t $DOCKERHUB_USERNAME/ros:rolling-$ARCH .
从输出中可以看到 /etc/apt/sources.list 文件的内容,其中提到 Ubuntu sources 已经移动到了 /etc/apt/sources.list.d/ubuntu.sources 文件。
修改方式二:把文件地址改成 ubuntu.sources
也就是说新版基础镜像里不再往 sources.list 写东西了,DEB822 格式的新文件在 sources.list.d/ubuntu.sources,所以 sed 的目标路径也要跟着改:
RUN sed -i 's@http://archive.ubuntu.com/@http://mirrors.tuna.tsinghua.edu.cn/@g' /etc/apt/sources.list.d/ubuntu.sources \
&& sed -i 's@http://security.ubuntu.com/@http://mirrors.tuna.tsinghua.edu.cn/@g' /etc/apt/sources.list.d/ubuntu.sources \
&& sed -i 's#http://ports.ubuntu.com/ubuntu-ports/#http://mirrors.tuna.tsinghua.edu.cn/ubuntu-ports/#g' /etc/apt/sources.list.d/ubuntu.sources
最后一步:清缓存再 build
不管上面哪种环境,最后跑之前都要先清缓存:
docker builder prune
然后运行 docker build 即可(可以自己写个循环 build 的脚本,原理一样)。最后结果:镜像构建成功。
小结与排错顺序
这套报错的根因是:基础镜像升级后 apt 源换成了 DEB822 格式的 ubuntu.sources,老教程里 sed 的 /etc/apt/sources.list 路径已经不存在或为空,sed 静默跑完(所以执行时间 0.0s),后面 apt-get update 再去连 archive.ubuntu.com,在国内网络环境下超时失败,exit code 100 就出现了。
遇到同类问题按这个顺序查:① 先在 Dockerfile 里插一行 RUN cat 看源到底写进哪个文件;② build 时加 --progress=plain 拿到详细输出;③ sed 的目标路径对准实际存在的文件;④ 改完跑 docker builder prune 清掉构建缓存,否则会沿用旧层。另外提速还有一个通用做法:直接把基础镜像换成国内镜像站的 ubuntu 镜像,或者在 RUN 最前面就换源,别等到拉 ROS 大包时才换。
qidao123.com企服评测-应用市场 编辑提示:本文为站点编辑整理的 Dockerfile 构建 Ubuntu 镜像报 exit code: 100 的排查与解决过程,命令已按原意规范化书写;文中镜像站地址仅作示例,请替换为自己实际可用的源;本站不提供镜像加速配置或加好友服务。 |