This repository contains helper resources to generate Docker images for developing and running ROS 2 application with RTI Connext DDS inside Docker containers.
The following workflow uses the included helper scripts to create a Docker container which mounts a local directory from the host, allowing you to easily build your project inside a preconfigured environment with ROS 2 and RTI Connext DDS.
The process relies on creating a Docker image which contains the required software components (ROS 2, RTI Connext DDS, and rmw_connextdds), and a non-root user which is mapped to the current user on the host.
-
Clone this repository:
git clone https://github.com/rticommunity/rticonnextdds-ros2-docker
-
Build image
rmw_connextdds:latest, a base Docker image with ROS 2, RTI Connext DDS, andrmw_connextdds. You can use scriptbuild_image_rmw_connextdds.shfor this purpose.If you prefer, you can control the name of the generated image using variable
DOCKER_IMAGE.By default, the image will use ROS 2 Galactic, provided by image
osrf/ros:galactic-desktop. If you prefer a different ROS 2 version, select an image from those available on Docker Hub and specify it using variableBASE_IMAGE.You can choose between 4 different ways to generate this image, based on how RTI Connext DDS and
rmw_connextddsare provisioned inside it:-
Use an RTI Connext DDS installation from the host, and build
rmw_connextddsfrom source (default):CONNEXTDDS_DIR=/path/to/rti_connext_dds-6.1.0 \ rticonnextdds-ros2-docker/scripts/build_image_rmw_connextdds.sh
-
Specify the Connext installation with variables
CONNEXTDDS_DIR, orNDDSHOME. -
You can optionally use
CONNEXTDDS_ARCHto specify the target architecture to use.
-
-
Install RTI Connext DDS using the official installers, and build
rmw_connextddsfrom source:CONNEXTDDS_FROM_RTIPKG=y \ CONNEXTDDS_INSTALLER_HOST=/path/to/<HOST_INSTALLER> \ CONNEXTDDS_INSTALLER_TARGET=/path/to/<TARGET_INSTALLER> \ CONNEXTDDS_INSTALLER_LICENSE=/path/to/<LICENSE_FILE> \ CONNEXTDDS_VERSION=6.1.0 \ rticonnextdds-ros2-docker/scripts/build_image_rmw_connextdds.sh
-
The following files are required:
- A host installer, e.g.
rti_connext_dds-6.1.0-pro-host-x64Linux.run(CONNEXTDDS_INSTALLER_HOST). - A target installer, e.g.
rti_connext_dds-6.1.0-pro-target-x64Linux4gcc7.3.0.rtipkg(CONNEXTDDS_INSTALLER_TARGET). - A license file, e.g.
rti_license.dat(CONNEXTDDS_INSTALLER_LICENSE).
- A host installer, e.g.
-
Variable
CONNEXTDDS_VERSIONis required to let the Dockerfile detect the generated RTI Connext DDS installation directory.
-
-
Install RTI Connext DDS using a Debian package and build
rmw_connextddsfrom source (x86_64 only):CONNEXTDDS_FROM_DEB=y \ rticonnextdds-ros2-docker/scripts/build_image_rmw_connextdds.sh
- The community-licensed version of Connext included in the binary package distributed via the ROS 2 Debian repository can only be used for non-commercial and pre-production applications.
-
Install RTI Connext DDS and
rmw_connextddsusing Debian packages (x86_64 only):RMW_CONNEXTDDS_FROM_DEB=y \ rticonnextdds-ros2-docker/scripts/build_image_rmw_connextdds.sh
-
This installation method requires the base image to include a version of ROS 2 installed from Debian packages (e.g. "osrf/ros:galactic-desktop").
-
rmw_connextddsis available as a Debian package only for ROS 2 Galactic and newer. -
The community-licensed version of Connext included in the binary package distributed via the ROS 2 Debian repository can only be used for non-commercial and pre-production applications.
-
-
-
Build image
ros2_workspace:latest.This image builds on top of the
rmw_connextddsimage by adding a non-root user to match your user, allowing you to mount and edit a directory from the host. You can generate this image using scriptbuild_image_ros2_workspace.sh.If you used a custom name for the base image, specify it using variable
BASE_IMAGE(default:rmw_connextdds:latest).You can control the name of the generated image using variable
DOCKER_IMAGE(default:ros2_workspace:latest).rticonnextdds-ros2-docker/scripts/build_image_ros2_workspace.sh
-
Start a Docker container with the generated image. You can use the
run_ros2_workspace.shscript to do so, which will automatically start the container or attach to it with a new terminal if it is already running.Use variable
WORKSPACE_DIRto specify a directory to mount inside the container (under path/workspace, default: current directory).You can control the name of the container and the image to use with variables
DOCKER_CONTAINER(default:ros2_workspace-dev) andDOCKER_IMAGE(default:ros2_workspace:latest) respectively.WORKSPACE_DIR=/path/to/my/workspace rticonnextdds-ros2-docker/scripts/run_ros2_workspace.sh
The repository includes a test ROS 2 package which you may use as a workspace directory to test the Docker images.
After building the ros2_workspace image, use the run_ros2_workspace.sh script
to build and run the example_workspace directory inside a container:
cd rticonnextdds-ros2-docker/example_workspace
../scripts/run_ros2_workspace.sh
# Inside the container, build the included ROS 2 package
colcon build --symlink-install
source install/setup.bash
# Use the example launch file to start two nodes with a custom
# QoS configuration file.
ros2 launch example_workspace talker-listener.launch.pyThe repository includes a docker-compose example which shows how to use the
rmw_connextdds images to run some example ROS 2 applications with RTI Connext
DDS.
After building the rmw_connextdds image, use the following command to run the
talker/listener example from package demo_nodes_cpp in two different
containers while forcing all communications to occur via the shared memory
transport:
cd rticonnextdds-ros2-docker/example_workspace
WORKSPACE_DIR=$(pwd) \
docker-compose -f ../docker_compose/docker-compose-talker_listener.yml upUse CTRL+C to terminate the containers.
Docker images to use ROS on ARM targets must be built manually using repository osrf/docker_images.
In order to provision Connext, you must first install it on an x86_64 Linux host,
and then copy the installation to the ARM device where you will build the Docker
images. If you only plan on using Connext to support rmw_connextdds,
you may restrict this copy to only a subset of the installation.
It is also recommended to replace script resource/cmake/FindRTIConnextDDS.cmake
in the Connext installation with the
most recent version made available by RTI.
-
On a x86_64 Linux host, install the Connext "host" bundle, then use
rtipkginstallto install a "target" bundle for the desired ARM target, e.g.:./rti_connext_dds-6.1.1-lm-x64Linux4gcc7.3.0.run ~/rti_connext_dds-6.1.1/bin/rtipkginstall rti_connext_dds-6.1.1-lm-target-armv8Linux4gcc7.3.0.rtipkg -
Update
resource/cmake/FindRTIConnextDDS.cmake:wget -o ~/rti_connext_dds-6.1.1/resource/cmake/FindRTIConnextDDS.cmake \ https://raw.githubusercontent.com/rticommunity/rticonnextdds-cmake-utils/main/cmake/Modules/FindRTIConnextDDS.cmake -
Generate an archive with the files required to support
rmw_connextdds, e.g.:tar czf rti_connext_dds-6.1.1-rmw-runtime.tar.gz \ rti_connext_dds-6.1.1/include \ rti_connext_dds-6.1.1/lib/armv8Linux4gcc7.3.0 \ rti_connext_dds-6.1.1/resource/cmake \ rti_connext_dds-6.1.1/resource/scripts \ rti_connext_dds-6.1.1/rti_versions.xmlYou can also generate the archive using script generate_connext_rmw_runtime.sh:
git clone https://github.com/rticommunity/rticonnextdds-ros2-docker rticonnextdds-ros2-docker/scripts/generate_connext_rmw_runtime.sh \ ~/rti_connext_dds-6.1.1 \ armv8Linux4gcc7.3.0 -
Copy and extract archive on ARM target, e.g. (replace
arm-targetwith the host name/IP address of your device):scp rti_connext_dds-6.1.1-rmw-runtime.tar.gz arm-target:~/ ssh arm-target tar xzf rti_connext_dds-6.1.1-rmw-runtime.tar.gzor, without first copying the archive:
cat rti_connext_dds-6.1.1-rmw-runtime.tar.gz | ssh arm-target tar xzf -or, without even creating an intermediate archive:
tar cz \ rti_connext_dds-6.1.1/include \ rti_connext_dds-6.1.1/lib/armv8Linux4gcc7.3.0 \ rti_connext_dds-6.1.1/resource/cmake \ rti_connext_dds-6.1.1/resource/scripts \ rti_connext_dds-6.1.1/rti_versions.xml | ssh arm-target tar xzf - -
On the ARM target, clone
osrf/docker_imagesand build the base ROS image, e.g.:git clone https://github.com/osrf/docker_images docker build -t ros:humble-desktop docker_images/ros/humble/ubuntu/jammy/desktop
-
Clone this repository and build the
rmw_connextddsimage:git clone https://github.com/rticommunity/rticonnextdds-ros2-docker CONNEXTDDS_DIR=~/rti_connext_dds-6.1.1 \ BASE_IMAGE=ros:humble-desktop \ DOCKER_IMAGE=rmw_connextdds:humble-desktop-6.1.1 \ rticonnextdds-ros2-docker/scripts/build_image_rmw_connextdds.sh -
(Optional) Build the
ros2_workspaceimage:BASE_IMAGE=rmw_connextdds:humble-desktop-6.1.1 \ DOCKER_IMAGE=ros2_workspace:humble-desktop-6.1.1 \ rticonnextdds-ros2-docker/scripts/build_image_ros2_workspace.sh
-
(Optional) Use the
ros2_workspaceimage:DOCKER_IMAGE=ros2_workspace:humble-desktop-6.1.1 \ rticonnextdds-ros2-docker/scripts/run_ros2_workspace.sh
All of the rmw_connextdds images should be built on top of one of the
ROS 2 images provided by OpenRobotics.
The Dockerfile.rmw_connextdds.* files all follow a similar workflow:
- Install RTI Connext DDS, then clone and build
rmw_connextdds, or... - Install both RTI Connext DDS and
rmw_connextddsfrom a Debian binary packages. - Set
rmw_connextddsas the default RMW_IMPLEMENTATION - Add a bashrc file to automatically load ROS 2 with RTI Connext DDS.
The ros2_workspace image uses the rmw_connextdds images to generate a
development environment suitable for mounting and editing a local directory
from the host machine.
This Dockerfile will generate a Docker image which includes a copy of RTI Connext DDS installed using the community-licensed package distributed via the ROS 2 Debian repository.
rmw_connextdds will also be installed using the binary Debian package provided
in the ROS 2 Debian repository.
| Variable | Description | Default Value |
|---|---|---|
BASE_IMAGE |
Base Docker image. | osrf/ros:galactic-desktop |
docker build rticonnextdds-ros2-docker/docker \
-t rmw_connextdds:latest \
-f rticonnextdds-ros2-docker/docker/Dockerfile.rmw_connextdds.binThis Dockerfile will generate a Docker image which includes a copy of RTI Connext DDS installed using the community-licensed package distributed via the ROS 2 Debian repository.
rmw_connextdds will be built from source.
| Variable | Description | Default Value |
|---|---|---|
BASE_IMAGE |
Base Docker image. | osrf/ros:galactic-desktop |
RMW_CONNEXTDDS_BRANCH |
Branch to build in rmw_connextdds's Git repository |
Automatically detected based on ROS_DISTRO |
RMW_CONNEXTDDS_DIR |
Container directory where to clone rmw_connextdds. |
/opt/rmw_connextdds |
RMW_CONNEXTDDS_URL |
Clone URL of rmw_connextdds's Git repository |
https://github.com/ros2/rmw_connextdds |
docker build rticonnextdds-ros2-docker/docker \
-t rmw_connextdds:latest \
-f rticonnextdds-ros2-docker/docker/Dockerfile.rmw_connextdds.debThis Dockerfile will generate a Docker image which contains a copy of RTI Connext DDS pre-installed on the host machine.
The Dockerfile will copy this installation specified by argument
CONNEXTDDS_HOST_DIR "as is".
This directory must be located under archives/ in the build context, and it
must contain a valid license file and target libraries.
If multiple target libraries are installed, the desired target architecture should
be specified using argument CONNEXTDDS_ARCH.
rmw_connextdds will be built from source.
| Variable | Description | Default Value |
|---|---|---|
BASE_IMAGE |
Base Docker image. | osrf/ros:galactic-desktop |
CONNEXTDDS_ARCH |
Target architecture to use. | |
CONNEXTDDS_HOST_DIR |
Name of the subdirectory of archives/, containing the installation of RTI Connext DDS to use inside the container |
|
RMW_CONNEXTDDS_BRANCH |
Branch to build in rmw_connextdds's Git repository |
Automatically detected based on ROS_DISTRO |
RMW_CONNEXTDDS_DIR |
Container directory where to clone rmw_connextdds. |
/opt/rmw_connextdds |
RMW_CONNEXTDDS_URL |
Clone URL of rmw_connextdds's Git repository |
https://github.com/ros2/rmw_connextdds |
This example assumes that the full path of the RTI Connext DDS host installation
is exported by variable CONNEXTDDS_DIR in the current shell environment.
# Create archives/ directory and copy Connext installation
mkdir rticonnextdds-ros2-docker/docker/archives
cp -r ${CONNEXTDDS_DIR} rticonnextdds-ros2-docker/docker/archives
docker build rticonnextdds-ros2-docker/docker \
-t rmw_connextdds:latest \
-f rticonnextdds-ros2-docker/docker/Dockerfile.rmw_connextdds.host \
--build-arg CONNEXTDDS_HOST_DIR=$(basename ${CONNEXTDDS_DIR})This Dockerfile will generate a Docker image which contains a copy of RTI Connext DDS installed from the official installers provided by RTI.
The Dockerfile expects to find the required installers in subdirectory
archives/ of the docker build context.
Beside the target and host installers, you will also need to provide a valid license file.
You can specify the name of the files (without paths)
using arguments CONNEXTDDS_INSTALLER_HOST, CONNEXTDDS_INSTALLER_TARGET,
and CONNEXTDDS_INSTALLER_LICENSE.
You must also make sure to specify argument CONNEXTDDS_VERSION with a 3-digit
version identifier for the selected version of RTI Connext DDS.
| Variable | Description | Default Value |
|---|---|---|
BASE_IMAGE |
Base Docker image. | osrf/ros:galactic-desktop |
CONNEXTDDS_INSTALLER_HOST |
File name (without path) of the host bundle | rti_connext_dds-6.1.0-pro-host-x64Linux.run |
CONNEXTDDS_INSTALLER_LICENSE |
File name (without path) of the license file. | rti_license.dat |
CONNEXTDDS_INSTALLER_TARGET |
File name (without path) of the target bundle | rti_connext_dds-6.1.0-pro-target-x64Linux4gcc7.3.0.rtipkg |
CONNEXTDDS_VERSION |
Version identifier for Connext DDS. | 6.1.0 |
CONNEXTDDS_ARCH |
Target architecture to use. | |
RMW_CONNEXTDDS_BRANCH |
Branch to build in rmw_connextdds's Git repository |
Automatically detected based on ROS_DISTRO |
RMW_CONNEXTDDS_DIR |
Container directory where to clone rmw_connextdds. |
/opt/rmw_connextdds |
RMW_CONNEXTDDS_URL |
Clone URL of rmw_connextdds's Git repository |
https://github.com/ros2/rmw_connextdds |
# Create archives/ directory and copy the Connext installer and license files
mkdir rticonnextdds-ros2-docker/docker/archives
cp /path/to/<HOST_INSTALLER> \
/path/to/<TARGET_INSTALLER> \
/path/to/<LICENSE_FILE> \
rticonnextdds-ros2-docker/docker/archives
docker build rticonnextdds-ros2-docker/docker \
-t rmw_connextdds:latest \
-f rticonnextdds-ros2-docker/docker/Dockerfile.rmw_connextdds.rtipkg \
--build-args CONNEXTDDS_INSTALLER_HOST=<HOST_INSTALLER> \
--build-args CONNEXTDDS_INSTALLER_TARGET=<TARGET_INSTALLER> \
--build-args CONNEXTDDS_INSTALLER_LICENSE=<LICENSE_FILE>This Dockerfile will generate a Docker image that can be used for local development of a ROS 2 application on the host machine.
The image requires one of the rmw_connextdds images to have been previously
built, and it will:
- Add a non-root user to match the user which owns the workspace directory on the host.
- Configure a custom entrypoint script which will automatically configure
the development environment, and possibly start a custom command passed to
docker run(see entrypoint.sh)
| Variable | Description | Default Value |
|---|---|---|
BASE_IMAGE |
Base Docker image. | rmw_connextdds:latest |
DOCKER_GID |
Id of the main group for the container's non-root user | 1000 |
DOCKER_UID |
Id of the container's non-root user | 1000 |
DOCKER_USER |
Name of the non-root user created inside the container to map the host's user | admin |
docker build rticonnextdds-ros2-docker/docker \
-t ros2_workspace:latest \
-f rticonnextdds-ros2-docker/docker/Dockerfile.ros2_workspace \
--build-arg BASE_IMAGE=rmw_connextdds:latest \
--build-arg DOCKER_USER=$(whoami) \
--build-arg DOCKER_UID=$(id -u) \
--build-arg DOCKER_GID=$(id -g) \