Hi again! I was making tests for our nodes and couldn't get ros2_client subscribers to hear ros2_client publishers. When listening on the topic using ros2 topic echo /topic_name, I was able to see output.
As an example, I made a test for ros2-client in a newly created tests/topic.rs:
//! Ensures that two `ros2_client` nodes can speak to each other.
use std::{pin::pin, time::Duration};
use futures::{future::select, StreamExt};
use ros2_client::{
Context, MessageTypeName, Name, NodeName, NodeOptions, Publisher, Subscription,
DEFAULT_PUBLISHER_QOS,
};
#[tokio::test]
async fn topic_communication() {
select(pin!(make_publisher()), pin!(make_subscriber())).await;
}
async fn make_subscriber() {
// make context
let ctx = Context::new().unwrap();
// node, topic, subscriber
let mut node = ctx
.new_node(
NodeName::new("/", "topic_test_sub_node").unwrap(),
NodeOptions::new(),
)
.unwrap();
let topic = node
.create_topic(
&Name::new("/", "pub_sub_topic").unwrap(),
MessageTypeName::new("std_msgs", "String"),
&DEFAULT_PUBLISHER_QOS.clone(),
)
.unwrap();
let subscriber: Subscription<String> = node.create_subscription(&topic, None).unwrap();
// spin node in background
tokio::task::spawn(node.spinner().unwrap().spin());
// start listening.
//
// if we don't get a message within five seconds, fail the test.
let (msg, _msg_info) = tokio::time::timeout(
Duration::from_secs(5),
Box::pin(subscriber.async_stream()).next(),
)
.await
.expect("Test timed out - publisher never sent anything!")
.expect("we should've got a message.")
.expect("message should've sent correctly!");
assert_eq!(msg, "hello subscriber!");
}
async fn make_publisher() {
let ctx = Context::new().unwrap();
let mut node = ctx
.new_node(
NodeName::new("/", "topic_test_pub_node").unwrap(),
NodeOptions::new(),
)
.unwrap();
let topic = node
.create_topic(
&Name::new("/", "pub_sub_topic").unwrap(),
MessageTypeName::new("std_msgs", "String"),
&DEFAULT_PUBLISHER_QOS.clone(),
)
.unwrap();
let publisher: Publisher<String> = node.create_publisher(&topic, None).unwrap();
tokio::task::spawn(node.spinner().unwrap().spin());
// send messages every 0.25 seconds
loop {
publisher
.async_publish("hello subscriber!".into())
.await
.unwrap();
tokio::time::sleep(Duration::from_millis(250)).await;
}
}
Output from the test:
test result: ok. 4 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 0.00s
Running tests/topic.rs (target/debug/deps/topic-f3f388d49a16d225)
running 1 test
test topic_communication ... FAILED
failures:
---- topic_communication stdout ----
thread 'topic_communication' panicked at tests/topic.rs:47:4:
Test timed out - publisher never sent anything!: Elapsed(())
note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace
failures:
topic_communication
test result: FAILED. 0 passed; 1 failed; 0 ignored; 0 measured; 0 filtered out; finished in 5.06s
error: test failed, to rerun pass `--test topic`
Output from ros2 topic echo /pub_sub_topic:
$ ros2 topic echo /pub_sub_topic
data: hello subscriber!
---
data: hello subscriber!
---
data: hello subscriber!
---
data: hello subscriber!
---
data: hello subscriber!
---
data: hello subscriber!
---
data: hello subscriber!
---
Please note that this test uses tokio (as mentioned in #26), though the same problem seems to appear when doing things synchronously, too.
In addition, you can force the test to pass by using ros2 topic pub:
$ ros2 topic pub /pub_sub_topic std_msgs/String {data: "hello subscriber!"}
publisher: beginning loop
publishing #1: std_msgs.msg.String(data='hello subscriber!')
publishing #2: std_msgs.msg.String(data='hello subscriber!')
publishing #3: std_msgs.msg.String(data='hello subscriber!')
publishing #4: std_msgs.msg.String(data='hello subscriber!')
Running tests/topic.rs (target/debug/deps/topic-f3f388d49a16d225)
running 1 test
test topic_communication ... ok
test result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 2.58s
Hi again! I was making tests for our nodes and couldn't get
ros2_clientsubscribers to hearros2_clientpublishers. When listening on the topic usingros2 topic echo /topic_name, I was able to see output.As an example, I made a test for
ros2-clientin a newly createdtests/topic.rs:Output from the test:
Output from
ros2 topic echo /pub_sub_topic:Please note that this test uses
tokio(as mentioned in #26), though the same problem seems to appear when doing things synchronously, too.In addition, you can force the test to pass by using
ros2 topic pub: