DORA (Dataflow-Oriented Robotic Application) is middleware designed to streamline and simplify the creation of AI-based robotic applications. It offers low latency, composable, and distributed dataflow capabilities. Applications are modeled as directed graphs, also referred to as pipelines.
The service detection requires a background event loop provided by the Spinner type. This spinner needs to be run in parallel to the main thread. The easiest way to do that is to create a multi-threaded executor and spawn it there. For example, using the ThreadPool executor provided by the futures crate:
let pool = futures::executor::ThreadPool::new()?;
let spinner = ros_node.spinner();
pool.spawn(async {
if let Err(err) = spinner.spin().await {
eprintln!("ros2 spinner failed: {err:?}");
}
})
.context("failed to spawn ros2 spinner")?;
If you're already using an async runtime such as tokio or smol, you can spawn the spinner there as well (provided that you're using a multi-threaded executor).
The generated type format might still change because we want to support service calls from C++ nodes as well. The cxx crate, which we use for bridging Rust to C++ code, doesn't work with generics, so we have to find another way.
We might want to provide direct service support in our node API. For example, we might want to spawn the spinner thread already in the library or provide a way to merge service responses into the event stream.
rust-ros2-dataflow
example with ROS2 service callNotes
ros2-client
crate, but I ran into issues (see https://github.com/jhelovuo/ros2-client/issues/24)The service detection requires a background event loop provided by the
Spinner
type. This spinner needs to be run in parallel to the main thread. The easiest way to do that is to create a multi-threaded executor and spawn it there. For example, using theThreadPool
executor provided by thefutures
crate:If you're already using an async runtime such as
tokio
orsmol
, you can spawn the spinner there as well (provided that you're using a multi-threaded executor).cxx
crate, which we use for bridging Rust to C++ code, doesn't work with generics, so we have to find another way.