Introducing ros2in1_support

With ROS 1 now being End of Life (EOL), many developers face an urgent question: how to transition to ROS 2 without large disruptions. To address this, we’ve created and open-sourced ros2in1_support, a solution designed specifically to enable bridge-less communication between ROS 1 and ROS 2 nodes both ways. We have been using this tool for the past 2 years, and we hope it is useful for you too!

Why did we create this?

The End of Life for ROS 1 presents a significant challenge for the robotics community. With no more updates, bug fixes, or compatibility with newer Ubuntu versions, developers must decide how to adapt their systems for the future. For many, a step-change from ROS 1 to ROS 2 is simply not practical—it requires time, resources, and large step changes are notoriously difficult to get right. Such a migration path may look like:

Recognizing this need in our own projects, we developed - and now open-sourced - ros2in1_support, a build tool specifically designed to address this problem. With ros2in1_support, you can build your ROS 1 nodes and allow them to communicate bridgelessly with ROS 2 nodes. We believe this solution fills a critical gap for the community, providing an efficient and practical way to transition while not being stuck with broken things.

In this article, we’ll explain what makes it different from existing solutions and how a typical usage looks like.

How it does NOT work

The classical way to have a hybrid ROS 1 and ROS 2 system is to put a bridge server between the ROS 1 nodes and the ROS 2 nodes. All data flows through the bridge, in both directions, and the bridge is responsible for copying and translating the data between ROS 1 and ROS 2. Bridges are however very inefficient, introduce delays and are sources of message drops. The existing bridge is implemented as a ROS 2 package, named ros1_bridge:

In addition, to manage these inefficiencies, the ros1_bridge is quite complex to set up, changes the 'flow' behavior of your application and is often hard to diagnose.

How it does work

So ros2in1_support does something different: it catches your ROS 1 pub/sub function calls and does the pub/sub on both ROS 1 and ROS 2 topics at the same time, from within your ROS node. It effectively 'stretches' your ROS 1 node into the ROS 2 environment, and yes, links with both the ROS 1 roscpp and the ROS 2 rclcpp libraries:

Advantages

The main benefits we see when migrating this way from ROS 1 to ROS 2 are:

  • It is the most efficient design to work in both ROS 1 and ROS 2 domains

  • It also works with custom message types (see next section though)

  • All the ROS 1 topics and services are visible in the ROS 2 tools. So you can work by default with the ROS 2 tools while the old nodes are still ROS 1.

  • You no longer depend on nor need ros1_bridge

Things it does not solve (yet)

The README file in the repository goes more into detail, but the two most important hurdles you still have to handle are:

  • for each message type, a conversion header is required and must be written by hand. ros2in1_support already includes some common ones, but you may need to extend it for your own messages.

  • migrating the ROS master parameter server. There is no 1:1 alternative for this in ROS2 

  • migrating your Python ROS 1 nodes. ros2in1_support is currently C++ only. A Python ROS 1 node will only pub/sub to other ROS 1 nodes.

Getting Started with ros2in1_support

The impatient can head over to our github repository and follow the installation instructions :-)

But at a high level, the steps you will take are:

  1. clone the ros2in1_support repo into your ROS 1 package tree

  2. For each ROS 1 package you want to stretch into ROS 2:
    1. Once:
      1. add the ros2in1_support dependency in every package.xml file

      2. add the necessary cmake snippet in the main CMakeLists.txt file

      3. add the necessary C++ ROS 2 executor snippet in every ROS node handle file

    2. For each topic and service:
      1. add/rewrite the necessary C++ include & typedef snippets in every ROS node header file


⇒ at this point, your ROS 1 workspace will still build a pure ROS 1 build!


  1. do a catkin config to enable ROS2_SUPPORT

  2. build the ros 2 workspace first

  3. build your ros 1 workspace with catkin build

  4. Launch your ROS 1 nodes as usual

  5. See them with ros2 topic or service list !

Migrating is a separate thing!

The above steps did not really migrate your ROS 1 package to ROS 2. It's now time to pick a ROS 1 node (say an easy one) and put that node in your ROS 2 workspace. There you remove all ROS2_SUPPORT code, run the conversion scripts (see https://docs.ros.org/en/iron/How-To-Guides/Migrating-from-ROS1.html ) and focus on making it work in ROS 2.

Will it work for me?

Big chance it does! We applied ros2in1_support to the famous ROS 1 turtlesim package and migrated it to the ROS 2 world. There is a separate git repository showing this migration patch so that it gives you a good idea of which files are touched and how: https://github.com/Intermodalics/ros2in1_demo