#0
ros的docker镜像分为1。ros官方镜像,2。第三方镜像
官方方案无法解决rviz和gazebo可视化问题,
第三方镜像的可视化解决方案,
安装glvnd,要求必须是Nvidia的显卡,
安装vnc
安装桌面环境,如xfce4,其可以一个提供轻量级桌面环境; LXDE,全名为Lightweight X11 Desktop Environment,也是一个开源桌面环境。
每个解决方案都有自己优劣点。
#一、构建自己的ROS镜像Dockerfile
##1.1 ROS kinetic版本(ubuntu16.04)
网上现有的和osrf/ros:kinetic
无法运行gazebo和rviz,必须要自己构建Dockerfile,引入glvnd
,才能正常使用其中的RVIZ和Gazebo这种图形化界面。
https://blog.csdn.net/zdegrh_2/article/details/102936547
构建ros的镜像需要从本地copy一个名为10_nvidia.json
的文件。
新建10_nvidia.json
文件,内容为下面
{
"file_format_version" : "1.0.0",
"ICD" : {
"library_path" : "libEGL_nvidia.so.0"
}
}
新建Dockerfile文件,内容为下面
ARG from
FROM nvidia/opengl:1.0-glvnd-runtime-ubuntu16.04 as glvnd
FROM osrf/ros:kinetic-desktop-full
COPY --from=glvnd /usr/local/lib/x86_64-linux-gnu /usr/local/lib/x86_64-linux-gnu
COPY --from=glvnd /usr/local/lib/i386-linux-gnu /usr/local/lib/i386-linux-gnu
COPY 10_nvidia.json /usr/local/share/glvnd/egl_vendor.d/10_nvidia.json
RUN echo '/usr/local/lib/x86_64-linux-gnu' >> /etc/ld.so.conf.d/glvnd.conf && \
echo '/usr/local/lib/i386-linux-gnu' >> /etc/ld.so.conf.d/glvnd.conf && \
ldconfig
ENV LD_LIBRARY_PATH /usr/local/lib/x86_64-linux-gnu:/usr/local/lib/i386-linux-gnu${LD_LIBRARY_PATH:+:${LD_LIBRARY_PATH}}
# nvidia-container-runtime
ENV NVIDIA_VISIBLE_DEVICES \
${NVIDIA_VISIBLE_DEVICES:-all}
ENV NVIDIA_DRIVER_CAPABILITIES \
${NVIDIA_DRIVER_CAPABILITIES:+$NVIDIA_DRIVER_CAPABILITIES,}graphics
RUN apt-get update && \
apt-get install -y \
build-essential \
libgl1-mesa-dev \
libglew-dev \
libsdl2-dev \
libsdl2-image-dev \
libglm-dev \
libfreetype6-dev \
libglfw3-dev \
libglfw3 \
libglu1-mesa-dev \
freeglut3-dev \
dbus
##1.2 ROS melodic版本(ubuntu18.04)
与ros kinetic类似,网上现有的osrf/ros:melodic
无法运行gazebo和rviz界面,必须要自己构建Dockerfile,引入glvnd
,才能正常使用其中的RVIZ和Gazebo这种图形化界面。
https://blog.csdn.net/liuqixuan1994/article/details/114089786
# FROM ubuntu:18.04
FROM nvidia/cudagl:10.2-base-ubuntu18.04
LABEL Description="A Dockerfile to setup $RES_NAME:$TAG" Author="liuqixuan" Version="1.0"
# Official sources.list
#ARG sourcelist="http://packages.ros.org/ros/ubuntu"
# Mirrors sources.list
# ARG sourcelist="http://mirrors.ustc.edu.cn/ros/ubuntu/"
ARG sourcelist="http://mirrors.tuna.tsinghua.edu.cn/ros/ubuntu/"
# ARG sourcelist="http://mirrors.sjtug.sjtu.edu.cn/ros/ubuntu/"
ARG workdir="/root/catkin_ws"
ARG DEBIAN_FRONTEND=noninteractive
ARG APT_KEY_DONT_WARN_ON_DANGEROUS_USAGE=YES
ENV XDG_RUNTIME_DIR="/tmp/runtime-root"
RUN set -x \
&& apt-get update \
&& apt install apt-transport-https \
&& apt install ca-certificates \
&& apt update \
&& cp /etc/apt/sources.list /etc/apt/sources.list.bak \
&& echo "deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ bionic main restricted universe multiverse" > /etc/apt/sources.list \
&& echo "deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ bionic-updates main restricted universe multiverse" >> /etc/apt/sources.list \
&& echo "deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ bionic-backports main restricted universe multiverse" >> /etc/apt/sources.list \
&& echo "deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ bionic-security main restricted universe multiverse" >> /etc/apt/sources.list \
&& apt-get update \
&& apt-get install -y --no-install-recommends apt-utils gnupg2 curl vim git xarclock \
&& sh -c '. /etc/lsb-release && echo "deb \${sourcelist} \${DISTRIB_CODENAME} main" > /etc/apt/sources.list.d/ros-latest.list' \
&& apt-key adv --keyserver 'hkp://keyserver.ubuntu.com:80' --recv-key C1CF6E31E6BADE8868B172B4F42ED6FBAB17C654 \
&& apt-get update \
&& apt-get install -y ros-melodic-desktop-full \
&& echo "source /opt/ros/melodic/setup.bash" >> ~/.bashrc \
&& bash -c '. ~/.bashrc'
RUN apt-get install -y python-rosdep python-rosinstall python-rosinstall-generator python-wstool build-essential
RUN apt-get install dbus
RUN echo "185.199.111.133 raw.githubusercontent.com" >> /etc/hosts
#RUN rosdep init \
# && rosdep update
#RUN useradd noroot -u 1000 -s /bin/bash \
# && echo "user added!"
#USER noroot
#USER root
#SHELL ["/bin/bash", "-c"]
RUN apt-get autoremove -y \
&& rm -rf /var/lib/apt/lists/* \
&& mkdir \${XDG_RUNTIME_DIR} && chmod 700 \${XDG_RUNTIME_DIR} \
&& mkdir \${workdir} \
&& set +x
WORKDIR \${workdir}
ENTRYPOINT ["/bin/bash"]
1.2.1 构建好的镜像可以打开rviz,但是打开gazebo会报错,[Err] [REST.cc:205] Error in REST request
,此时进入容器的/root目录下(也是~/目录),修改:.ignition/fuel/config.yaml文件:
将
url: [https://api.ignitionfuel.org]
改为
url: [https://api.ignitionrobotics.org]
注意空格对齐,否则也汇报错
##1.3 比较osrf/ros:melodic和自己的dockerfile区别
首先,nvidia/cudagl:10.2-base-ubuntu18.04这个镜像是怎么来的
其次如何构建自己的melodic镜像
在安装ros的时候,要把ubuntu的镜像源改为清华的,否则有些包就因为网络问题,没法安装上去。把它当成一个ubuntu双系统去对待。
...
&& cp /etc/apt/sources.list /etc/apt/sources.list.bak \
&& echo "deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ bionic main restricted universe multiverse" > /etc/apt/sources.list \
&& echo "deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ bionic-updates main restricted universe multiverse" >> /etc/apt/sources.list \
&& echo "deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ bionic-backports main restricted universe multiverse" >> /etc/apt/sources.list \
&& echo "deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ bionic-security main restricted universe multiverse" >> /etc/apt/sources.list \
...
dbus包是x11 server需要的,不装会报错,无法显示图形界面。
默认的源是http的,但替换用的镜像源是https,所以休要额外的安装关于HTTPS的包。
...
&& apt install apt-transport-https \
&& apt install ca-certificates \
...
apt-utils是apt-get install的包,gnupg2是验证gpg的包,curl来传输网络数据,vim git是常用工具,xarclock是一个gui钟表,用来测试用,也可以不装。
...
&& apt-get install -y --no-install-recommends apt-utils gnupg2 curl vim git xarclock \
...
下面就是常规ros安装过程了。
&& sh -c '. /etc/lsb-release && echo "deb \${sourcelist} \${DISTRIB_CODENAME} main" > /etc/apt/sources.list.d/ros-latest.list' \
&& apt-key adv --keyserver 'hkp://keyserver.ubuntu.com:80' --recv-key C1CF6E31E6BADE8868B172B4F42ED6FBAB17C654 \
&& apt-get update \
&& apt-get install -y ros-melodic-desktop-full \
&& echo "source /opt/ros/melodic/setup.bash" >> ~/.bashrc \
&& bash -c '. ~/.bashrc'
在docker里面安装包,必须先执行apt-get update
命令,因为系统中并没有相应链接的缓存!
#二、基于Dockerfile构建镜像
创建好Dockerfile之后,通过docker build命令来创建镜像,该命令首先会上传Dockerfile文件给Docker服务器端,服务器端将逐行执行Dockerfile中定义的指令。
通常建议放置Dockerfile的目录为空目录。另外可以在目录下创建.dockerignore文件,让Docker忽略路径下的文件和目录,这一点与Git中的配置很相似。
通过 -t 指定镜像的标签信息,例如:docker build -t regenzm/first_image .
,注意最后一个**.**指定的是Dockerfile所在的路径。
镜像构建文件名称必须是Dockerfile
,否则要-f
参数指定文件名称
使用示例:
docker build -t ros:kinetic
#三、创建容器
容器使用的时候需要安装nvidia-container-toolkit
##3.1 添加nvidia-container-toolkit
的源
distribution=$(. /etc/os-release;echo $ID$VERSION_ID) \
&& curl -s -L https://nvidia.github.io/nvidia-docker/gpgkey | sudo apt-key add - \
&& curl -s -L https://nvidia.github.io/nvidia-docker/$distribution/nvidia-docker.list | sudo tee /etc/apt/sources.list.d/nvidia-docker.list
##3.2 安装nvidia-container-toolkit
sudo apt-get update && sudo apt-get install -y nvidia-container-toolkit
sudo systemctl restart docker
##3.3 使用脚本执行docker命令,进入到环境中
加上--rm
参数后退出容器时,会自动删除容器
docker run --gpus all -ti --rm -e DISPLAY -v /tmp/.X11-unix:/tmp/.X11-unix ros:kinetic
挂载数据卷启动容器
docker run --gpus all -ti -e DISPLAY -v /tmp/.X11-unix:/tmp/.X11-unix -v /home/xx/ceshi:/home ros:kinetic
技巧:把run镜像的命令写成脚本
注意:如果无法显示图形界面,可能需要运行显示界面的映射
xhost +
#四、分发docker镜像
##4.1 离线模式
1.主机A有镜像nginx,版本为v1.0版本。执行命令:
docker save -o nginx:v1.0 /root/nginx.tar
—> 将nginx:v1.0保存为nginx.tar包
2.通过scp命令将nginx.tar包拷贝给主机B。
3.在主机B上执行命令:
docker load -i /root/nginx.tar
—> 从nginx.tar包load为镜像nginx:v1.0
注意:执行docker save nginx:v1.0 -o /root/nginx.tar
命令,如果不加版本v1.0
,会将主机A上所有版本nginx镜像都save到一个nginx.tar包。
##4.2 在线模式
注册dockerhub账号,上传上去后,再通过阿里云加速,暂时用不到,建议用离线镜像部署。
#总结
rviz可视化显示,所以要解决一下问题
0 构建自己的镜像,要引入nvidia的那个镜像。(rviz那个报错需要宿主机安装nvidia驱动)
1 安装nvidia docker,并且要在run的时候加上–gpus参数
2 apt-get install dbus
3 xhost + 运行显示界面的映射
4 运行参数要加上显示设置的参数
docker run --gpus all -ti --rm -e DISPLAY --env="QT_X11_NO_MITSHM=1" -v /tmp/.X11-unix:/tmp/.X11-unix ros:kinetic
-e DISPLAY 是开启显示,否则无法显示
–env="QT_X11_NO_MITSHM=1"如果不设置,gazebo无法正常显示
-v /tmp/.X11-unix:/tmp/.X11-unix 显示传输的缓存地址