社区所有版块导航
Python
python开源   Django   Python   DjangoApp   pycharm  
DATA
docker   Elasticsearch  
aigc
aigc   chatgpt  
WEB开发
linux   MongoDB   Redis   DATABASE   NGINX   其他Web框架   web工具   zookeeper   tornado   NoSql   Bootstrap   js   peewee   Git   bottle   IE   MQ   Jquery  
机器学习
机器学习算法  
Python88.com
反馈   公告   社区推广  
产品
短视频  
印度
印度  
Py学习  »  docker

docker搭建流程指南

新机器视觉 • 1 周前 • 59 次点击  

1.前言


这里主要提供了一个通用的docker构建流程,在构建任何docker的时候都可以参考这个构建流程来搭建一个专用的docker镜像。文章飞书链接docker搭建流程指南(https://my.feishu.cn/docx/EBwodWAywoxR6OxMTJVc7xylnKe)



2.安装docker和docker-compose


wget http://fishros.com/install -O fishros && . fishrossudo apt install -y docker-compose # 新版的docker v2默认集成了docker compose的功能


图片



3.镜像拉取


  • ROS的docker images仓库链接:https://hub.docker.com/r/osrf/ros/tags


图片


在OSRF/ROS镜像仓库中可以找到几乎所有你想要的ROS docker镜像,并在对应的ROS镜像后面可以看到一行docker pull的指令,将其复制并粘贴到我们的设备上即可对相应的ROS镜像进行拉取。这里我使用ROS2进行镜像拉取的演示。


在终端中输入完成镜像拉取:


docker pull osrf/ros:humble-desktop-full


图片


在终端中输入完成进行查询:


docker images


图片



4.启动ROS的docker镜像


因为首先我们要在docker下使用cuda因此我们要先安装nvidia-docker2


sudo apt install -y nvidia-docker2sudo systemctl restart docker


图片


在完成了ROS的docker镜像拉取后我进行以下镜像打开,在终端中输入命令


docker run -it --env DISPLAY=${DISPLAY} --env NVIDIA_DRIVER_CAPABILITIES=all --env QT_X11_NO_MITSHM=1 --env USER_ID=${USER_ID:-1000} --env GROUP_ID=${GROUP_ID:-1000} --device /dev/snd:/dev/snd --device /dev/dri:/dev/dri --volume /tmp/.X11-unix:/tmp/.X11-unix --volume /home/huahua:/home/ROS2 --gpus all osrf/ros:humble-desktop-full


这里我对上面启动docker里面的参数进行解释


  • -it:这里是-i和-t的组合。-i表示保持标准输入打开,允许用户与容器交互;-t表示分配一个伪终端,让用户在容器内进行命令行可操作。


  • --env:表示设置容器内的环境变量。


  • --env DISPLAY=${DISPLAY}:表示将主机的X11显示服务器地址设置容器,让容器内的GUI程序能够在主机屏幕上显示,例如想要使用RVIZ则需要打开此功能。


  • --env NVIDIA_DRIVER_CAPABILITIES=all:表示启用显卡驱动的全部功能,如果电脑不带显卡或使用不上可以不使用。


  • --env QT_X11_NO_MITSHM=1:取消Q应用的X11共享内存机制,主要是防止RViz在中运行时出现图形显示异常。


  • --env USER_ID= USE拉我D:−1000−−envG拉哦UP我D=美国东南铁路我D:−1000−− e n v GRO U P我D= {GROUP_ID:-1000}:设置容器内用户的UID和GID,确保容器内操作主机映射目录时,文件权限与主机一致。


  • --device:表示将主机的硬件设备直接映射到容器,让容器能够访问主机硬件。


  • --device /dev/snd:/dev/snd:表示映射主机的音频设备(/dev/snd是Linux设备的统一路径),让容器内的程序能够输出或输入音频。


  • --volume:表示将主机的目录或文件共享到容器,实现数据持久化和文件交互。


  • --volume /tmp/.X11-unix:/tmp/.X11-unix:共享主机的 X11 导入目录(/tmp/.X11-unix 是 X 服务器的本地通信接口),让容器内部的 GUI 程序能够通过该架构与主机的 X 服务器通信,最终在主机屏幕上显示窗口。


  • --volume /home/huahua:/home/ROS2:表示将主机的/home/huahua目录映射到容器的/home/ROS2目录。


  • --gpus all:表示允许容器访问主机的所有NVIDIA GPU。


  • osrf/ros:humble-desktop-full:docker镜像名。



5. Dockerfile


可创建Dockerfile来快速完成对docker镜像中的环境配置


cd dockermkdir dockertouch Dockerfile


当你按照前两步进入到基础的ros2 docker镜像后,你需要对你的项目中进行依赖配置,例如我在某个项目中需要配置的依赖:


apt updateapt install -y gazeboapt install -y ros-humble-gazebo-ros-pkgsapt install ros-humble-xacro apt install ros-humble-ros2-controlapt install ros-humble-ros2-controllersapt install ros-humble-gazebo-ros2-controlapt install ros-humble-slam-toolboxapt install ros-humble-navigation2apt install ros-humble-nav2-bringupapt install ros-humble-twist-mux


这时你可以把这个堆的依赖和你的ROS docker镜像发给ai,让他给你生成一个Dockerfile文件,就是下面ai生成的Dockerfile。


FROM osrf/ros:humble-desktop-full
ENV DEBIAN_FRONTEND=noninteractive
RUN apt-get update && apt-get install -y --no-install-recommends \    gazebo \    ros-humble-gazebo-ros-pkgs \    ros-humble-xacro \    ros-humble-ros2-control \    ros-humble-ros2-controllers \    ros-humble-gazebo-ros2-control \    ros-humble-slam-toolbox \    ros-humble-navigation2 \    ros-humble-nav2-bringup \    ros-humble-twist-mux \    && apt-get clean \    && rm -rf /var/lib/apt/lists/*
ENV DEBIAN_FRONTEND=
WORKDIR /home/huahua
RUN echo "source /opt/ros/humble/setup.bash" >> ~/.bashrc
CMD ["/bin/bash"]


这里我对上面启动docker里面的参数进行解释


  • FROM osrf/ros:humble-desktop-full:使用基础ROS Docker镜像。


  • ENV DEBIAN_FRONTEND=noninteractive:非交互模式的环境变量设置,避免安装过程中弹出外汇配置窗口(比如让你选Y/N)。


  • RUN:在docker中要运行多个命令,例如apt install和pip3 install。


  • ENV DEBIAN_FRONTEND=:重新启动终端的交互模式。


  • WORKDIR /home/huahua:工作目录,docker启动后的默认路径。


  • CMD ["/bin/bash"]:docker启动后执行默认命令,启动bash终端。


在Dockerfile的路径下运行如下命令可完成环境的快速配置,并生成新的docker镜像


docker build -t ros2_sim .sudo docker exec -it ros2_sim bash



6. docker-compose.yml


配合Dockerfile一起使用可快速完成对docker环境的配置和新镜像的创建,实现一键式创建镜像、启动镜像和删除镜像等操作。请确保已经安装了Docker Compose工具。


cd dockertouch docker-compose.yml


可以将ROS2仿真环境docker搭建里的启动命令丢给ai,让他帮忙创建一个docker-compose.yml文件如下:


version: '3.8'  
services:  ros2_sim:    build:      context: .        dockerfile: Dockerfile     image: ros2-sim:latest    container_name: ros2_sim    tty: true    stdin_open: true    environment:      - DISPLAY=${DISPLAY}      - NVIDIA_DRIVER_CAPABILITIES=all      - QT_X11_NO_MITSHM=1      - USER_ID=${USER_ID:-1000}      - GROUP_ID=${GROUP_ID:-1000}    devices:      - /dev/snd:/dev/snd      - /dev/dri:/dev/dri    volumes:      - /tmp/ .X11-unix:/tmp/.X11-unix      - /home:/home      - /dev/shm:/dev/shm      deploy:      resources:        reservations:          devices:            - driver: nvidia  # 指定设备驱动              count: all      # 预留所有可用 NVIDIA GPU              capabilities: [gpu] # 声明 GPU 能力:容器内可调用 GPU 进行渲染/计算    network_mode: host    command: /bin/bash


这里我对上面docker-compose.yml里面的参数进行解释


  • version::Docker Compose文件版本。


  • services: :服务大类。


  • ros2_sim::自定义的服务具体名称(可通过 docker-compose 命令操作该服务,如启动/停止)。


  • build: :构建镜像的配置。


  • context: :构建上下文目录,默认推荐为.,docker-compose.yml和dockerfile推荐放在一个文件夹下。


  • dockerfile: :构建镜像的Dockerfile文件名,默认为Dockerfile。


  • image: :构建后的镜像名称。


  • container_name: :构建的容器名,有多个服务的时候需要区分。


  • tty: :是否为容器虚拟终端分配,true为分配,false为不分配,默认推荐true。


  • stdin_open::是否启动标准输入,对应docker exec -it中的-it。


  • 环境::具体的环境配置。


    DISPLAY=${DISPLAY}:缴交机DISPLAY变量,用于显示rviz2等GUI。


    NVIDIA_DRIVER_CAPABILITIES=all:NVIDIA驱动功能开放数量,多显卡环境选择显卡驱动,默认全部。


    QT_X11_NO_MITSHM=1 :禁用 QT 的 MIT-SHM 共享内存机制:解决 ROS GUI (如 RViz)黑屏、崩溃问题。


    USER_ID=${USER_ID:-1000}:容器内用户UID:默认1000(Linux普通用户默认UID),避免文件权限问题。


    GROUP_ID=${GROUP_ID:-1000}:容器内用户组GID:与UID对应,确保挂载目录权限一致。


  • devices::设备挂载,如显卡音频等。


  • Volumes: :目录挂载,简易机与容器文件共享。


    /tmp/.X11-unix:/tmp/.X11-unix :共享 X11 帮助,实现容器 GUI 显示,之前是一个机器为 docker。


    /home:/home:挂载一个机器目录到容器,这里为选择将一个机器的home(之前)挂载到docker的home(今晚)下。


    /dev/shm:/dev/shm :共享内存优化。


  • 部署::针对GPU资源分配。


  • network_mode::网络模式,使用以太网机网络(主机模式)。


  • command: :容器启动后执行的默认命令,可以使用如下完成多个指令的执行:


command: >      /bin/bash -c "      export DISPLAY=:0 &&      cd xingdong_ws &&      source install/setup.bash &&      ros2 launch gazebo gazebo.launch.py      "


  • extends: :对服务模块的复用。 docker-compose.yml 进阶玩法:配置多服务完成不同的功能


version: '3.8'  
services:  ros2_sim:    build:      context: .        dockerfile: Dockerfile     image: ros2-sim:latest    container_name: ros2_sim    tty: true    stdin_open: true    environment:      - DISPLAY=${DISPLAY}      - NVIDIA_DRIVER_CAPABILITIES=all      - QT_X11_NO_MITSHM=1      - USER_ID=${USER_ID:-1000}      - GROUP_ID=${GROUP_ID:-1000}    devices:      - /dev/snd:/dev/snd      - /dev/dri:/dev/dri    volumes:      - /tmp/.X11-unix:/tmp/.X11-unix      - /home:/home      - /dev/shm:/dev/shm      deploy:      resources:        reservations:          devices:            - driver: nvidia              count: all              capabilities: [gpu]    network_mode: host    command: >      /bin/bash -c "      export DISPLAY=:0 &&      cd xingdong_ws &&      source install/setup.bash &&      ros2 launch gazebo gazebo.launch.py      "    ros2_sim:    build:      context: .        dockerfile: Dockerfile     image: ros2-sim:latest    container_name: ros2_sim    tty: true    stdin_open: true    environment:      - DISPLAY=${DISPLAY}      - NVIDIA_DRIVER_CAPABILITIES=all      - QT_X11_NO_MITSHM=1      - USER_ID=${USER_ID:-1000}      - GROUP_ID=${GROUP_ID:-1000}    devices:      - /dev/snd:/dev/snd      - /dev/dri:/dev/dri    volumes:      - /tmp/.X11-unix:/tmp/.X11-unix      - /home:/home      - /dev/shm:/dev/shm      deploy:      resources:        reservations:          devices:            - driver: nvidia              count: all              capabilities: [gpu]     network_mode: host    command: >      /bin/bash -c "      export DISPLAY=:0 &&      cd xingdong_ws &&      source install/setup.bash &&      ros2 launch gazebo gazebo.launch.py      "


使用方法,在docker-compose.yml文件的路径下运行如下命令可实现对应功能。


docker-compose up -d --build --remove-orphans        #容器构建docker-compose up -d ros2_sim                        #启动容器,-d为不进入docker终端,ros2_sim是众多服务中的一个服务docker-compose ps                                    #容器查看docker-compose exec ros2_sim bash                    #进入容器docker-compose down                                  #容器删除


Docker v2默认完成集成了docker-compose因此可以使用下面的命令相应功能


docker compose up -d --build --remove-orphans        #容器构建docker compose up -d ros2_sim                        #启动容器,-d为不进入docker终端,ros2_sim是众多服务中的一个服务docker compose ps                                    #容器查看docker compose exec ros2_sim bash                    #进入容器docker compose down  


图片



7. 问题与解决


问题


如遇到Error response from daemon: failed to resolve reference "docker.io/osrf/ros:humble-desktop-full": failed to do request: Head "https://registry-1.docker.io/v2/osrf/ros/manifests/humble-desktop-full": dial tcp [2a03:2880:f10c:83:face:b00c:0:25de]:443: i/o timeout的问题。


解决办法


这里我参考了博客【血泪经验】Docker拉取镜像超时竟是这个原因!镜像配置加速器还不够?_docker拉取镜像网络超时-CSDN博客 (https://blog.csdn.net/2301_76849350/article/details/147227440?ops_request_misc=%257B%2522request%255Fid%2522%253A%25221040468e6d5ba5cf547b6e85d6187080%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257D&request_id=1040468e6d5ba5cf547b6e85d6187080&biz_id=0&utm_medium=distribute.pc_search_result.none-task-blog-2~all~top_positive~default-1-147227440-null-null.142%5Ev102%5Epc_search_result_base4&utm_term=docker%E6%8B%89%E5%8F%96%E9%95%9C%E5%83%8F%E8%B6%85%E6%97%B6&spm=1018.2226.3001.4187),当然如果你科学上网比较稳定其实应该是能直接获取到镜像的。使用docker info可以查看当前配置。


1.打开daemon.json


sudo gedit /etc/docker/daemon.json


2.将下面的内容填入daemon.json


{  "registry-mirrors": [    "https://docker.registry.cyou",    "https://docker-cf.registry.cyou",    "https://dockercf.jsdelivr.fyi",    "https://docker.jsdelivr.fyi",    "https://dockertest.jsdelivr.fyi",    "https://mirror.aliyuncs.com",    "https://dockerproxy.com",    "https://mirror.baidubce.com",    "https://docker.m.daocloud.io",    "https://docker.nju.edu.cn",    "https://docker.mirrors.sjtug.sjtu.edu.cn",    "https://docker.mirrors.ustc.edu.cn",    "https://mirror.iscas.ac.cn",    "https://docker.rainbond.cc",    "https://do.nark.eu.org",    "https://dc.j8.work",    "https://gst6rzl9.mirror.aliyuncs.com",    "https://registry.docker-cn.com",    "http://hub-mirror.c.163.com",    "http://mirrors.ustc.edu.cn/",    "https://mirrors.tuna.tsinghua.edu.cn/",    "http://mirrors.sohu.com/"  ],  "insecure-registries": [    "registry.docker-cn.com",    "docker.mirrors.ustc.edu.cn"  ],  "debug": true,  "experimental": false}


4.重启docker服务


sudo systemctl daemon-reexecsudo systemctl restart docker


5. 检测配置成功与否


docker info


出现下面信息为成功。


图片


现在就可以拉取镜像了。


图片



参考


docker容器中安装ROS1/ROS2(不用配任何环境,10分钟搞定)_ros2 docker-CSDN博客(https://blog.csdn.net/zysss_/article/details/134125740?ops_request_misc=%257B%2522request%255Fid%2522%253A%2522fc4599c84b149d3e32b9650f66b38436%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257D&request_id=fc4599c84b149d3e32b9650f66b38436&biz_id=0&utm_medium=distribute.pc_search_result.none-task-blog-2~all~sobaiduend~default-4-134125740-null-null.142%5Ev102%5Epc_search_result_base4&utm_term=ros2%20docker&spm=1018.2226.3001.4187)


Python社区是高质量的Python/Django开发社区
本文地址:http://www.python88.com/topic/199386