Compare commits
17 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
4f14a0cc14 | ||
|
|
83b086a9ef | ||
|
|
2ed85420d5 | ||
|
|
cc65905efa | ||
|
|
88768eaabd | ||
|
|
696d9ed1be | ||
|
|
74daff052b | ||
|
|
a667583821 | ||
|
|
552c1a8deb | ||
|
|
5cecbf99bb | ||
|
|
f703314f95 | ||
|
|
0fa68d54e7 | ||
|
|
cbde45481e | ||
|
|
2a653c47f8 | ||
|
|
bba9dce253 | ||
|
|
898a30e0e2 | ||
|
|
6e8aaa2ae6 |
@@ -2,22 +2,20 @@
|
||||
Changelog for package rclcpp
|
||||
^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
2.0.2 (2020-07-07)
|
||||
3.0.0 (2020-06-18)
|
||||
------------------
|
||||
* Link against thread library where necessary (`#1210 <https://github.com/ros2/rclcpp/issues/1210>`_) (`#1214 <https://github.com/ros2/rclcpp/issues/1214>`_)
|
||||
* Fix exception message on rcl_clock_init (`#1182 <https://github.com/ros2/rclcpp/issues/1182>`_) (`#1193 <https://github.com/ros2/rclcpp/issues/1193>`_)
|
||||
* Contributors: Dirk Thomas, tomoya
|
||||
|
||||
2.0.1 (2020-06-23)
|
||||
------------------
|
||||
* Add create_publisher include to create_subscription (`#1180 <https://github.com/ros2/rclcpp/issues/1180>`_) (`#1192 <https://github.com/ros2/rclcpp/issues/1192>`_)
|
||||
* Fix get_node_time_source_interface() docstring (`#988 <https://github.com/ros2/rclcpp/issues/988>`_) (`#1185 <https://github.com/ros2/rclcpp/issues/1185>`_)
|
||||
* Fixed doxygen warnings (`#1163 <https://github.com/ros2/rclcpp/issues/1163>`_) (`#1191 <https://github.com/ros2/rclcpp/issues/1191>`_)
|
||||
* Check period duration in create_wall_timer (`#1178 <https://github.com/ros2/rclcpp/issues/1178>`_)
|
||||
* Fix get_node_time_source_interface() docstring (`#988 <https://github.com/ros2/rclcpp/issues/988>`_)
|
||||
* Add message lost subscription event (`#1164 <https://github.com/ros2/rclcpp/issues/1164>`_)
|
||||
* Add spin_all method to Executor (`#1156 <https://github.com/ros2/rclcpp/issues/1156>`_)
|
||||
* Reorganize test directory and split CMakeLists.txt (`#1173 <https://github.com/ros2/rclcpp/issues/1173>`_)
|
||||
* Check if context is valid when looping in spin_some (`#1167 <https://github.com/ros2/rclcpp/issues/1167>`_)
|
||||
* Add check for invalid topic statistics publish period (`#1151 <https://github.com/ros2/rclcpp/issues/1151>`_)
|
||||
* Fix spin_until_future_complete: check spinning value (`#1023 <https://github.com/ros2/rclcpp/issues/1023>`_)
|
||||
Make Executor::spin_once_impl private before backporting, to avoid API compatibility issues
|
||||
* Add check for invalid topic statistics publish period (`#1151 <https://github.com/ros2/rclcpp/issues/1151>`_) (`#1172 <https://github.com/ros2/rclcpp/issues/1172>`_)
|
||||
* Contributors: Alejandro Hernández Cordero, Devin Bonnie, DongheeYe, Ivan Santiago Paunovic, Jacob Perron, Stephen Brawner
|
||||
* Fix doxygen warnings (`#1163 <https://github.com/ros2/rclcpp/issues/1163>`_)
|
||||
* Fix reference to rclcpp in its Quality declaration (`#1161 <https://github.com/ros2/rclcpp/issues/1161>`_)
|
||||
* Allow spin_until_future_complete to accept any future like object (`#1113 <https://github.com/ros2/rclcpp/issues/1113>`_)
|
||||
* Contributors: Alejandro Hernández Cordero, Christophe Bedard, Devin Bonnie, Dirk Thomas, DongheeYe, Ivan Santiago Paunovic, Jacob Perron, Sarthak Mittal, brawner, tomoya
|
||||
|
||||
2.0.0 (2020-06-01)
|
||||
------------------
|
||||
|
||||
@@ -2,8 +2,6 @@ cmake_minimum_required(VERSION 3.5)
|
||||
|
||||
project(rclcpp)
|
||||
|
||||
find_package(Threads REQUIRED)
|
||||
|
||||
find_package(ament_cmake_ros REQUIRED)
|
||||
find_package(builtin_interfaces REQUIRED)
|
||||
find_package(libstatistics_collector REQUIRED)
|
||||
@@ -168,7 +166,6 @@ target_include_directories(${PROJECT_NAME} PUBLIC
|
||||
"$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/include>"
|
||||
"$<BUILD_INTERFACE:${CMAKE_CURRENT_BINARY_DIR}/include>"
|
||||
"$<INSTALL_INTERFACE:include>")
|
||||
target_link_libraries(${PROJECT_NAME} ${CMAKE_THREAD_LIBS_INIT})
|
||||
# specific order: dependents before dependencies
|
||||
ament_target_dependencies(${PROJECT_NAME}
|
||||
"libstatistics_collector"
|
||||
@@ -215,442 +212,10 @@ ament_export_dependencies(statistics_msgs)
|
||||
ament_export_dependencies(tracetools)
|
||||
|
||||
if(BUILD_TESTING)
|
||||
find_package(ament_cmake_gtest REQUIRED)
|
||||
find_package(ament_lint_auto REQUIRED)
|
||||
ament_lint_auto_find_test_dependencies()
|
||||
|
||||
find_package(rmw_implementation_cmake REQUIRED)
|
||||
find_package(rosidl_default_generators REQUIRED)
|
||||
|
||||
find_package(test_msgs REQUIRED)
|
||||
|
||||
include(cmake/rclcpp_add_build_failure_test.cmake)
|
||||
|
||||
add_definitions(-DTEST_RESOURCES_DIRECTORY="${CMAKE_CURRENT_BINARY_DIR}/test/resources")
|
||||
|
||||
rosidl_generate_interfaces(${PROJECT_NAME}_test_msgs
|
||||
test/msg/Header.msg
|
||||
test/msg/MessageWithHeader.msg
|
||||
DEPENDENCIES builtin_interfaces
|
||||
LIBRARY_NAME ${PROJECT_NAME}
|
||||
SKIP_INSTALL
|
||||
)
|
||||
|
||||
ament_add_gtest(test_client test/test_client.cpp)
|
||||
if(TARGET test_client)
|
||||
ament_target_dependencies(test_client
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_client ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_create_timer test/test_create_timer.cpp)
|
||||
if(TARGET test_create_timer)
|
||||
ament_target_dependencies(test_create_timer
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rcl"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_create_timer ${PROJECT_NAME})
|
||||
target_include_directories(test_create_timer PRIVATE test/)
|
||||
endif()
|
||||
ament_add_gtest(test_expand_topic_or_service_name test/test_expand_topic_or_service_name.cpp)
|
||||
if(TARGET test_expand_topic_or_service_name)
|
||||
ament_target_dependencies(test_expand_topic_or_service_name
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_expand_topic_or_service_name ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_function_traits test/test_function_traits.cpp)
|
||||
if(TARGET test_function_traits)
|
||||
target_include_directories(test_function_traits PUBLIC include)
|
||||
ament_target_dependencies(test_function_traits
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
endif()
|
||||
ament_add_gmock(test_intra_process_manager test/test_intra_process_manager.cpp)
|
||||
if(TARGET test_intra_process_manager)
|
||||
ament_target_dependencies(test_intra_process_manager
|
||||
"rcl"
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_intra_process_manager ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_ring_buffer_implementation test/test_ring_buffer_implementation.cpp)
|
||||
if(TARGET test_ring_buffer_implementation)
|
||||
ament_target_dependencies(test_ring_buffer_implementation
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_ring_buffer_implementation ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_intra_process_buffer test/test_intra_process_buffer.cpp)
|
||||
if(TARGET test_intra_process_buffer)
|
||||
ament_target_dependencies(test_intra_process_buffer
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_intra_process_buffer ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_loaned_message test/test_loaned_message.cpp)
|
||||
ament_target_dependencies(test_loaned_message
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_loaned_message ${PROJECT_NAME})
|
||||
|
||||
ament_add_gtest(test_node test/test_node.cpp TIMEOUT 240)
|
||||
if(TARGET test_node)
|
||||
ament_target_dependencies(test_node
|
||||
"rcl_interfaces"
|
||||
"rcpputils"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_node ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_node_interfaces__get_node_interfaces
|
||||
test/node_interfaces/test_get_node_interfaces.cpp)
|
||||
if(TARGET test_node_interfaces__get_node_interfaces)
|
||||
target_link_libraries(test_node_interfaces__get_node_interfaces ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
# TODO(wjwwood): reenable these build failure tests when I can get Jenkins to ignore their output
|
||||
# rclcpp_add_build_failure_test(build_failure__get_node_topics_interface_const_ref_rclcpp_node
|
||||
# test/node_interfaces/test_does_not_compile/get_node_topics_interface_const_ref_rclcpp_node.cpp)
|
||||
# target_link_libraries(build_failure__get_node_topics_interface_const_ref_rclcpp_node
|
||||
# ${PROJECT_NAME})
|
||||
|
||||
# rclcpp_add_build_failure_test(build_failure__get_node_topics_interface_const_ptr_rclcpp_node
|
||||
# test/node_interfaces/test_does_not_compile/get_node_topics_interface_const_ptr_rclcpp_node.cpp)
|
||||
# target_link_libraries(build_failure__get_node_topics_interface_const_ptr_rclcpp_node
|
||||
# ${PROJECT_NAME})
|
||||
|
||||
# rclcpp_add_build_failure_test(build_failure__get_node_topics_interface_const_ref_wrapped_node
|
||||
# test/node_interfaces/test_does_not_compile/get_node_topics_interface_const_ref_wrapped_node.cpp)
|
||||
# target_link_libraries(build_failure__get_node_topics_interface_const_ref_rclcpp_node
|
||||
# ${PROJECT_NAME})
|
||||
|
||||
# rclcpp_add_build_failure_test(build_failure__get_node_topics_interface_const_ptr_wrapped_node
|
||||
# test/node_interfaces/test_does_not_compile/get_node_topics_interface_const_ptr_wrapped_node.cpp)
|
||||
# target_link_libraries(build_failure__get_node_topics_interface_const_ptr_rclcpp_node
|
||||
# ${PROJECT_NAME})
|
||||
|
||||
ament_add_gtest(test_node_global_args test/test_node_global_args.cpp)
|
||||
if(TARGET test_node_global_args)
|
||||
ament_target_dependencies(test_node_global_args
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_node_global_args ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_node_options test/test_node_options.cpp)
|
||||
if(TARGET test_node_options)
|
||||
ament_target_dependencies(test_node_options "rcl")
|
||||
target_link_libraries(test_node_options ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_parameter_client test/test_parameter_client.cpp)
|
||||
if(TARGET test_parameter_client)
|
||||
ament_target_dependencies(test_parameter_client
|
||||
"rcl_interfaces"
|
||||
)
|
||||
target_link_libraries(test_parameter_client ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_parameter_events_filter test/test_parameter_events_filter.cpp)
|
||||
if(TARGET test_parameter_events_filter)
|
||||
ament_target_dependencies(test_parameter_events_filter
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_parameter_events_filter ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_parameter test/test_parameter.cpp)
|
||||
if(TARGET test_parameter)
|
||||
ament_target_dependencies(test_parameter
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_parameter ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_parameter_map test/test_parameter_map.cpp)
|
||||
if(TARGET test_parameter_map)
|
||||
target_link_libraries(test_parameter_map ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_publisher test/test_publisher.cpp)
|
||||
if(TARGET test_publisher)
|
||||
ament_target_dependencies(test_publisher
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_publisher ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_publisher_subscription_count_api test/test_publisher_subscription_count_api.cpp)
|
||||
if(TARGET test_publisher_subscription_count_api)
|
||||
ament_target_dependencies(test_publisher_subscription_count_api
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_publisher_subscription_count_api ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_qos test/test_qos.cpp)
|
||||
if(TARGET test_qos)
|
||||
ament_target_dependencies(test_qos
|
||||
"rmw"
|
||||
)
|
||||
target_link_libraries(test_qos
|
||||
${PROJECT_NAME}
|
||||
)
|
||||
endif()
|
||||
ament_add_gtest(test_qos_event test/test_qos_event.cpp)
|
||||
if(TARGET test_qos_event)
|
||||
ament_target_dependencies(test_qos_event
|
||||
"rmw"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_qos_event
|
||||
${PROJECT_NAME}
|
||||
)
|
||||
endif()
|
||||
ament_add_gtest(test_rate test/test_rate.cpp)
|
||||
if(TARGET test_rate)
|
||||
ament_target_dependencies(test_rate
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_rate
|
||||
${PROJECT_NAME}
|
||||
)
|
||||
endif()
|
||||
ament_add_gtest(test_serialized_message_allocator test/test_serialized_message_allocator.cpp)
|
||||
if(TARGET test_serialized_message_allocator)
|
||||
ament_target_dependencies(test_serialized_message_allocator
|
||||
test_msgs
|
||||
)
|
||||
target_link_libraries(test_serialized_message_allocator
|
||||
${PROJECT_NAME}
|
||||
)
|
||||
endif()
|
||||
ament_add_gtest(test_serialized_message test/test_serialized_message.cpp)
|
||||
if(TARGET test_serialized_message)
|
||||
ament_target_dependencies(test_serialized_message
|
||||
test_msgs
|
||||
)
|
||||
target_link_libraries(test_serialized_message
|
||||
${PROJECT_NAME}
|
||||
)
|
||||
endif()
|
||||
ament_add_gtest(test_service test/test_service.cpp)
|
||||
if(TARGET test_service)
|
||||
ament_target_dependencies(test_service
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_service ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_subscription test/test_subscription.cpp)
|
||||
if(TARGET test_subscription)
|
||||
ament_target_dependencies(test_subscription
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_subscription ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_subscription_publisher_count_api test/test_subscription_publisher_count_api.cpp)
|
||||
if(TARGET test_subscription_publisher_count_api)
|
||||
ament_target_dependencies(test_subscription_publisher_count_api
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_subscription_publisher_count_api ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_subscription_traits test/test_subscription_traits.cpp)
|
||||
if(TARGET test_subscription_traits)
|
||||
ament_target_dependencies(test_subscription_traits
|
||||
"rcl"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_subscription_traits ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_find_weak_nodes test/test_find_weak_nodes.cpp)
|
||||
if(TARGET test_find_weak_nodes)
|
||||
ament_target_dependencies(test_find_weak_nodes
|
||||
"rcl"
|
||||
)
|
||||
target_link_libraries(test_find_weak_nodes ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
set(append_library_dirs "${CMAKE_CURRENT_BINARY_DIR}")
|
||||
if(WIN32)
|
||||
set(append_library_dirs "${append_library_dirs}/$<CONFIG>")
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_externally_defined_services test/test_externally_defined_services.cpp)
|
||||
ament_target_dependencies(test_externally_defined_services
|
||||
"rcl"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_externally_defined_services ${PROJECT_NAME})
|
||||
|
||||
ament_add_gtest(test_duration test/test_duration.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_duration)
|
||||
ament_target_dependencies(test_duration
|
||||
"rcl")
|
||||
target_link_libraries(test_duration ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_executor test/test_executor.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_executor)
|
||||
ament_target_dependencies(test_executor
|
||||
"rcl")
|
||||
target_link_libraries(test_executor ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_logger test/test_logger.cpp)
|
||||
target_link_libraries(test_logger ${PROJECT_NAME})
|
||||
|
||||
ament_add_gmock(test_logging test/test_logging.cpp)
|
||||
target_link_libraries(test_logging ${PROJECT_NAME})
|
||||
|
||||
ament_add_gtest(test_time test/test_time.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_time)
|
||||
ament_target_dependencies(test_time
|
||||
"rcl")
|
||||
target_link_libraries(test_time ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_timer test/test_timer.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_timer)
|
||||
ament_target_dependencies(test_timer
|
||||
"rcl")
|
||||
target_link_libraries(test_timer ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_time_source test/test_time_source.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_time_source)
|
||||
ament_target_dependencies(test_time_source
|
||||
"rcl")
|
||||
target_link_libraries(test_time_source ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_utilities test/test_utilities.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_utilities)
|
||||
ament_target_dependencies(test_utilities
|
||||
"rcl")
|
||||
target_link_libraries(test_utilities ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_init test/test_init.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_init)
|
||||
ament_target_dependencies(test_init
|
||||
"rcl")
|
||||
target_link_libraries(test_init ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_interface_traits test/test_interface_traits.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_interface_traits)
|
||||
ament_target_dependencies(test_interface_traits
|
||||
"rcl")
|
||||
target_link_libraries(test_interface_traits ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_multi_threaded_executor test/executors/test_multi_threaded_executor.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_multi_threaded_executor)
|
||||
ament_target_dependencies(test_multi_threaded_executor
|
||||
"rcl")
|
||||
target_link_libraries(test_multi_threaded_executor ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_guard_condition test/test_guard_condition.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_guard_condition)
|
||||
target_link_libraries(test_guard_condition ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_wait_set test/test_wait_set.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_wait_set)
|
||||
ament_target_dependencies(test_wait_set "test_msgs")
|
||||
target_link_libraries(test_wait_set ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_subscription_topic_statistics test/topic_statistics/test_subscription_topic_statistics.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}"
|
||||
)
|
||||
if(TARGET test_subscription_topic_statistics)
|
||||
ament_target_dependencies(test_subscription_topic_statistics
|
||||
"builtin_interfaces"
|
||||
"libstatistics_collector"
|
||||
"rcl_interfaces"
|
||||
"rcutils"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"statistics_msgs"
|
||||
"test_msgs")
|
||||
rosidl_target_interfaces(test_subscription_topic_statistics ${PROJECT_NAME}_test_msgs "rosidl_typesupport_cpp")
|
||||
target_link_libraries(test_subscription_topic_statistics ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_subscription_options test/test_subscription_options.cpp)
|
||||
if(TARGET test_subscription_options)
|
||||
ament_target_dependencies(test_subscription_options "rcl")
|
||||
target_link_libraries(test_subscription_options ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
# Install test resources
|
||||
install(
|
||||
DIRECTORY test/resources
|
||||
DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/test)
|
||||
add_subdirectory(test)
|
||||
endif()
|
||||
|
||||
ament_package()
|
||||
|
||||
@@ -191,7 +191,7 @@ It is **Quality Level 4**, see its [Quality Declaration document](https://github
|
||||
|
||||
#### `tracetools`
|
||||
|
||||
The `tracetools` package provides utilities for instrumenting the code in `rcl` so that it may be traced for debugging and performance analysis.
|
||||
The `tracetools` package provides utilities for instrumenting the code in `rclcpp` so that it may be traced for debugging and performance analysis.
|
||||
|
||||
It is **Quality Level 4**, see its [Quality Declaration document](https://gitlab.com/micro-ROS/ros_tracing/ros2_tracing/-/blob/master/tracetools/QUALITY_DECLARATION.md).
|
||||
|
||||
|
||||
@@ -29,7 +29,6 @@
|
||||
#include "rclcpp/node_interfaces/node_timers_interface.hpp"
|
||||
#include "rclcpp/node_interfaces/node_topics_interface.hpp"
|
||||
|
||||
#include "rclcpp/create_publisher.hpp"
|
||||
#include "rclcpp/create_timer.hpp"
|
||||
#include "rclcpp/qos.hpp"
|
||||
#include "rclcpp/subscription_factory.hpp"
|
||||
|
||||
@@ -76,14 +76,14 @@ create_timer(
|
||||
* \tparam DurationRepT
|
||||
* \tparam DurationT
|
||||
* \tparam CallbackT
|
||||
* \param period period to exectute callback
|
||||
* \param period period to execute callback. This duration must be 0 <= period < nanoseconds::max()
|
||||
* \param callback callback to execute via the timer period
|
||||
* \param group
|
||||
* \param node_base
|
||||
* \param node_timers
|
||||
* \return
|
||||
* \throws std::invalid argument if either node_base or node_timers
|
||||
* are null
|
||||
* are null, or period is negative or too large
|
||||
*/
|
||||
template<typename DurationRepT, typename DurationT, typename CallbackT>
|
||||
typename rclcpp::WallTimer<CallbackT>::SharedPtr
|
||||
@@ -102,10 +102,38 @@ create_wall_timer(
|
||||
throw std::invalid_argument{"input node_timers cannot be null"};
|
||||
}
|
||||
|
||||
if (period < std::chrono::duration<DurationRepT, DurationT>::zero()) {
|
||||
throw std::invalid_argument{"timer period cannot be negative"};
|
||||
}
|
||||
|
||||
// Casting to a double representation might lose precision and allow the check below to succeed
|
||||
// but the actual cast to nanoseconds fail. Using 1 DurationT worth of nanoseconds less than max.
|
||||
constexpr auto maximum_safe_cast_ns =
|
||||
std::chrono::nanoseconds::max() - std::chrono::duration<DurationRepT, DurationT>(1);
|
||||
|
||||
// If period is greater than nanoseconds::max(), the duration_cast to nanoseconds will overflow
|
||||
// a signed integer, which is undefined behavior. Checking whether any std::chrono::duration is
|
||||
// greater than nanoseconds::max() is a difficult general problem. This is a more conservative
|
||||
// version of Howard Hinnant's (the <chrono> guy>) response here:
|
||||
// https://stackoverflow.com/a/44637334/2089061
|
||||
// However, this doesn't solve the issue for all possible duration types of period.
|
||||
// Follow-up issue: https://github.com/ros2/rclcpp/issues/1177
|
||||
constexpr auto ns_max_as_double =
|
||||
std::chrono::duration_cast<std::chrono::duration<double, std::chrono::nanoseconds::period>>(
|
||||
maximum_safe_cast_ns);
|
||||
if (period > ns_max_as_double) {
|
||||
throw std::invalid_argument{
|
||||
"timer period must be less than std::chrono::nanoseconds::max()"};
|
||||
}
|
||||
|
||||
const auto period_ns = std::chrono::duration_cast<std::chrono::nanoseconds>(period);
|
||||
if (period_ns < std::chrono::nanoseconds::zero()) {
|
||||
throw std::runtime_error{
|
||||
"Casting timer period to nanoseconds resulted in integer overflow."};
|
||||
}
|
||||
|
||||
auto timer = rclcpp::WallTimer<CallbackT>::make_shared(
|
||||
std::chrono::duration_cast<std::chrono::nanoseconds>(period),
|
||||
std::move(callback),
|
||||
node_base->get_context());
|
||||
period_ns, std::move(callback), node_base->get_context());
|
||||
node_timers->add_timer(timer, group);
|
||||
return timer;
|
||||
}
|
||||
|
||||
@@ -160,7 +160,7 @@ public:
|
||||
void
|
||||
spin_node_some(std::shared_ptr<rclcpp::Node> node);
|
||||
|
||||
/// Complete all available queued work without blocking.
|
||||
/// Collect work once and execute all available work, optionally within a duration.
|
||||
/**
|
||||
* This function can be overridden. The default implementation is suitable for a
|
||||
* single-threaded model of execution.
|
||||
@@ -175,6 +175,23 @@ public:
|
||||
virtual void
|
||||
spin_some(std::chrono::nanoseconds max_duration = std::chrono::nanoseconds(0));
|
||||
|
||||
/// Collect and execute work repeatedly within a duration or until no more work is available.
|
||||
/**
|
||||
* This function can be overridden. The default implementation is suitable for a
|
||||
* single-threaded model of execution.
|
||||
* Adding subscriptions, timers, services, etc. with blocking callbacks will cause this function
|
||||
* to block (which may have unintended consequences).
|
||||
* If the time that waitables take to be executed is longer than the period on which new waitables
|
||||
* become ready, this method will execute work repeatedly until `max_duration` has elapsed.
|
||||
*
|
||||
* \param[in] max_duration The maximum amount of time to spend executing work. Must be positive.
|
||||
* Note that spin_all() may take longer than this time as it only returns once max_duration has
|
||||
* been exceeded.
|
||||
*/
|
||||
RCLCPP_PUBLIC
|
||||
virtual void
|
||||
spin_all(std::chrono::nanoseconds max_duration);
|
||||
|
||||
RCLCPP_PUBLIC
|
||||
virtual void
|
||||
spin_once(std::chrono::nanoseconds timeout = std::chrono::nanoseconds(-1));
|
||||
@@ -189,10 +206,10 @@ public:
|
||||
* code.
|
||||
* \return The return code, one of `SUCCESS`, `INTERRUPTED`, or `TIMEOUT`.
|
||||
*/
|
||||
template<typename ResponseT, typename TimeRepT = int64_t, typename TimeT = std::milli>
|
||||
template<typename FutureT, typename TimeRepT = int64_t, typename TimeT = std::milli>
|
||||
FutureReturnCode
|
||||
spin_until_future_complete(
|
||||
const std::shared_future<ResponseT> & future,
|
||||
const FutureT & future,
|
||||
std::chrono::duration<TimeRepT, TimeT> timeout = std::chrono::duration<TimeRepT, TimeT>(-1))
|
||||
{
|
||||
// TODO(wjwwood): does not work recursively; can't call spin_node_until_future_complete
|
||||
@@ -270,6 +287,10 @@ protected:
|
||||
rclcpp::node_interfaces::NodeBaseInterface::SharedPtr node,
|
||||
std::chrono::nanoseconds timeout);
|
||||
|
||||
RCLCPP_PUBLIC
|
||||
void
|
||||
spin_some_impl(std::chrono::nanoseconds max_duration, bool exhaustive);
|
||||
|
||||
/// Find the next available executable and do the work associated with it.
|
||||
/**
|
||||
* \param[in] any_exec Union structure that can hold any executable type (timer, subscription,
|
||||
@@ -342,13 +363,12 @@ protected:
|
||||
|
||||
RCLCPP_DISABLE_COPY(Executor)
|
||||
|
||||
std::list<rclcpp::node_interfaces::NodeBaseInterface::WeakPtr> weak_nodes_;
|
||||
std::list<const rcl_guard_condition_t *> guard_conditions_;
|
||||
|
||||
private:
|
||||
RCLCPP_PUBLIC
|
||||
void
|
||||
spin_once_impl(std::chrono::nanoseconds timeout);
|
||||
|
||||
std::list<rclcpp::node_interfaces::NodeBaseInterface::WeakPtr> weak_nodes_;
|
||||
std::list<const rcl_guard_condition_t *> guard_conditions_;
|
||||
};
|
||||
|
||||
namespace executor
|
||||
|
||||
@@ -66,12 +66,12 @@ using rclcpp::executors::SingleThreadedExecutor;
|
||||
* If the time spent inside the blocking loop exceeds this timeout, return a `TIMEOUT` return code.
|
||||
* \return The return code, one of `SUCCESS`, `INTERRUPTED`, or `TIMEOUT`.
|
||||
*/
|
||||
template<typename ResponseT, typename TimeRepT = int64_t, typename TimeT = std::milli>
|
||||
template<typename FutureT, typename TimeRepT = int64_t, typename TimeT = std::milli>
|
||||
rclcpp::FutureReturnCode
|
||||
spin_node_until_future_complete(
|
||||
rclcpp::Executor & executor,
|
||||
rclcpp::node_interfaces::NodeBaseInterface::SharedPtr node_ptr,
|
||||
const std::shared_future<ResponseT> & future,
|
||||
const FutureT & future,
|
||||
std::chrono::duration<TimeRepT, TimeT> timeout = std::chrono::duration<TimeRepT, TimeT>(-1))
|
||||
{
|
||||
// TODO(wjwwood): does not work recursively; can't call spin_node_until_future_complete
|
||||
@@ -82,13 +82,13 @@ spin_node_until_future_complete(
|
||||
return retcode;
|
||||
}
|
||||
|
||||
template<typename NodeT = rclcpp::Node, typename ResponseT, typename TimeRepT = int64_t,
|
||||
template<typename NodeT = rclcpp::Node, typename FutureT, typename TimeRepT = int64_t,
|
||||
typename TimeT = std::milli>
|
||||
rclcpp::FutureReturnCode
|
||||
spin_node_until_future_complete(
|
||||
rclcpp::Executor & executor,
|
||||
std::shared_ptr<NodeT> node_ptr,
|
||||
const std::shared_future<ResponseT> & future,
|
||||
const FutureT & future,
|
||||
std::chrono::duration<TimeRepT, TimeT> timeout = std::chrono::duration<TimeRepT, TimeT>(-1))
|
||||
{
|
||||
return rclcpp::executors::spin_node_until_future_complete(
|
||||
@@ -104,7 +104,7 @@ template<typename FutureT, typename TimeRepT = int64_t, typename TimeT = std::mi
|
||||
rclcpp::FutureReturnCode
|
||||
spin_until_future_complete(
|
||||
rclcpp::node_interfaces::NodeBaseInterface::SharedPtr node_ptr,
|
||||
const std::shared_future<FutureT> & future,
|
||||
const FutureT & future,
|
||||
std::chrono::duration<TimeRepT, TimeT> timeout = std::chrono::duration<TimeRepT, TimeT>(-1))
|
||||
{
|
||||
rclcpp::executors::SingleThreadedExecutor executor;
|
||||
@@ -116,7 +116,7 @@ template<typename NodeT = rclcpp::Node, typename FutureT, typename TimeRepT = in
|
||||
rclcpp::FutureReturnCode
|
||||
spin_until_future_complete(
|
||||
std::shared_ptr<NodeT> node_ptr,
|
||||
const std::shared_future<FutureT> & future,
|
||||
const FutureT & future,
|
||||
std::chrono::duration<TimeRepT, TimeT> timeout = std::chrono::duration<TimeRepT, TimeT>(-1))
|
||||
{
|
||||
return rclcpp::spin_until_future_complete(node_ptr->get_node_base_interface(), future, timeout);
|
||||
|
||||
@@ -143,10 +143,10 @@ public:
|
||||
* exec.add_node(node);
|
||||
* exec.spin_until_future_complete(future);
|
||||
*/
|
||||
template<typename ResponseT, typename TimeRepT = int64_t, typename TimeT = std::milli>
|
||||
template<typename FutureT, typename TimeRepT = int64_t, typename TimeT = std::milli>
|
||||
rclcpp::FutureReturnCode
|
||||
spin_until_future_complete(
|
||||
std::shared_future<ResponseT> & future,
|
||||
FutureT & future,
|
||||
std::chrono::duration<TimeRepT, TimeT> timeout = std::chrono::duration<TimeRepT, TimeT>(-1))
|
||||
{
|
||||
std::future_status status = future.wait_for(std::chrono::seconds(0));
|
||||
|
||||
@@ -68,7 +68,7 @@ public:
|
||||
* \param[in] node_base NodeBaseInterface pointer that is used in part of the setup.
|
||||
* \param[in] topic Name of the topic to publish to.
|
||||
* \param[in] qos QoS profile for Subcription.
|
||||
* \param[in] options options for the subscription.
|
||||
* \param[in] options Options for the subscription.
|
||||
*/
|
||||
Publisher(
|
||||
rclcpp::node_interfaces::NodeBaseInterface * node_base,
|
||||
|
||||
@@ -34,6 +34,7 @@ using QOSDeadlineRequestedInfo = rmw_requested_deadline_missed_status_t;
|
||||
using QOSDeadlineOfferedInfo = rmw_offered_deadline_missed_status_t;
|
||||
using QOSLivelinessChangedInfo = rmw_liveliness_changed_status_t;
|
||||
using QOSLivelinessLostInfo = rmw_liveliness_lost_status_t;
|
||||
using QOSMessageLostInfo = rmw_message_lost_status_t;
|
||||
using QOSOfferedIncompatibleQoSInfo = rmw_offered_qos_incompatible_event_status_t;
|
||||
using QOSRequestedIncompatibleQoSInfo = rmw_requested_qos_incompatible_event_status_t;
|
||||
|
||||
@@ -41,6 +42,7 @@ using QOSDeadlineRequestedCallbackType = std::function<void (QOSDeadlineRequeste
|
||||
using QOSDeadlineOfferedCallbackType = std::function<void (QOSDeadlineOfferedInfo &)>;
|
||||
using QOSLivelinessChangedCallbackType = std::function<void (QOSLivelinessChangedInfo &)>;
|
||||
using QOSLivelinessLostCallbackType = std::function<void (QOSLivelinessLostInfo &)>;
|
||||
using QOSMessageLostCallbackType = std::function<void (QOSMessageLostInfo &)>;
|
||||
using QOSOfferedIncompatibleQoSCallbackType = std::function<void (QOSOfferedIncompatibleQoSInfo &)>;
|
||||
using QOSRequestedIncompatibleQoSCallbackType =
|
||||
std::function<void (QOSRequestedIncompatibleQoSInfo &)>;
|
||||
@@ -59,6 +61,7 @@ struct SubscriptionEventCallbacks
|
||||
QOSDeadlineRequestedCallbackType deadline_callback;
|
||||
QOSLivelinessChangedCallbackType liveliness_callback;
|
||||
QOSRequestedIncompatibleQoSCallbackType incompatible_qos_callback;
|
||||
QOSMessageLostCallbackType message_lost_callback;
|
||||
};
|
||||
|
||||
class UnsupportedEventTypeException : public exceptions::RCLErrorBase, public std::runtime_error
|
||||
|
||||
@@ -92,7 +92,7 @@ public:
|
||||
* \param[in] topic_name Name of the topic to subscribe to.
|
||||
* \param[in] qos QoS profile for Subcription.
|
||||
* \param[in] callback User defined callback to call when a message is received.
|
||||
* \param[in] options options for the subscription.
|
||||
* \param[in] options Options for the subscription.
|
||||
* \param[in] message_memory_strategy The memory strategy to be used for managing message memory.
|
||||
* \param[in] subscription_topic_statistics Optional pointer to a topic statistics subcription.
|
||||
* \throws std::invalid_argument if the QoS is uncompatible with intra-process (if one
|
||||
@@ -144,6 +144,11 @@ public:
|
||||
// pass
|
||||
}
|
||||
}
|
||||
if (options.event_callbacks.message_lost_callback) {
|
||||
this->add_event_handler(
|
||||
options.event_callbacks.message_lost_callback,
|
||||
RCL_SUBSCRIPTION_MESSAGE_LOST);
|
||||
}
|
||||
|
||||
// Setup intra process publishing if requested.
|
||||
if (rclcpp::detail::resolve_use_intra_process(options, *node_base)) {
|
||||
|
||||
@@ -66,7 +66,7 @@ public:
|
||||
* \param[in] node_base NodeBaseInterface pointer used in parts of the setup.
|
||||
* \param[in] type_support_handle rosidl type support struct, for the Message type of the topic.
|
||||
* \param[in] topic_name Name of the topic to subscribe to.
|
||||
* \param[in] subscription_options options for the subscription.
|
||||
* \param[in] subscription_options Options for the subscription.
|
||||
* \param[in] is_serialized is true if the message will be delivered still serialized
|
||||
*/
|
||||
RCLCPP_PUBLIC
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
<?xml-model href="http://download.ros.org/schema/package_format2.xsd" schematypens="http://www.w3.org/2001/XMLSchema"?>
|
||||
<package format="2">
|
||||
<name>rclcpp</name>
|
||||
<version>2.0.2</version>
|
||||
<version>3.0.0</version>
|
||||
<description>The ROS client library in C++.</description>
|
||||
<maintainer email="dthomas@osrfoundation.org">Dirk Thomas</maintainer>
|
||||
<license>Apache License 2.0</license>
|
||||
|
||||
@@ -32,7 +32,7 @@ public:
|
||||
{
|
||||
rcl_ret_t ret = rcl_clock_init(clock_type, &rcl_clock_, &allocator_);
|
||||
if (ret != RCL_RET_OK) {
|
||||
exceptions::throw_from_rcl_error(ret, "failed to initialize rcl clock");
|
||||
exceptions::throw_from_rcl_error(ret, "could not get current time stamp");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -28,6 +28,8 @@
|
||||
|
||||
#include "rcutils/logging_macros.h"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
using rclcpp::exceptions::throw_from_rcl_error;
|
||||
using rclcpp::AnyExecutable;
|
||||
using rclcpp::Executor;
|
||||
@@ -212,8 +214,21 @@ Executor::spin_node_some(std::shared_ptr<rclcpp::Node> node)
|
||||
this->spin_node_some(node->get_node_base_interface());
|
||||
}
|
||||
|
||||
void Executor::spin_some(std::chrono::nanoseconds max_duration)
|
||||
{
|
||||
return this->spin_some_impl(max_duration, false);
|
||||
}
|
||||
|
||||
void Executor::spin_all(std::chrono::nanoseconds max_duration)
|
||||
{
|
||||
if (max_duration <= 0ns) {
|
||||
throw std::invalid_argument("max_duration must be positive");
|
||||
}
|
||||
return this->spin_some_impl(max_duration, true);
|
||||
}
|
||||
|
||||
void
|
||||
Executor::spin_some(std::chrono::nanoseconds max_duration)
|
||||
Executor::spin_some_impl(std::chrono::nanoseconds max_duration, bool exhaustive)
|
||||
{
|
||||
auto start = std::chrono::steady_clock::now();
|
||||
auto max_duration_not_elapsed = [max_duration, start]() {
|
||||
@@ -232,14 +247,20 @@ Executor::spin_some(std::chrono::nanoseconds max_duration)
|
||||
throw std::runtime_error("spin_some() called while already spinning");
|
||||
}
|
||||
RCLCPP_SCOPE_EXIT(this->spinning.store(false); );
|
||||
// non-blocking call to pre-load all available work
|
||||
wait_for_work(std::chrono::milliseconds::zero());
|
||||
bool work_available = false;
|
||||
while (rclcpp::ok(context_) && spinning.load() && max_duration_not_elapsed()) {
|
||||
AnyExecutable any_exec;
|
||||
if (!work_available) {
|
||||
wait_for_work(std::chrono::milliseconds::zero());
|
||||
}
|
||||
if (get_next_ready_executable(any_exec)) {
|
||||
execute_any_executable(any_exec);
|
||||
work_available = true;
|
||||
} else {
|
||||
break;
|
||||
if (!work_available || !exhaustive) {
|
||||
break;
|
||||
}
|
||||
work_available = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
434
rclcpp/test/CMakeLists.txt
Normal file
434
rclcpp/test/CMakeLists.txt
Normal file
@@ -0,0 +1,434 @@
|
||||
find_package(ament_cmake_gtest REQUIRED)
|
||||
|
||||
find_package(rmw_implementation_cmake REQUIRED)
|
||||
find_package(rosidl_default_generators REQUIRED)
|
||||
|
||||
find_package(test_msgs REQUIRED)
|
||||
|
||||
include(cmake/rclcpp_add_build_failure_test.cmake)
|
||||
|
||||
add_definitions(-DTEST_RESOURCES_DIRECTORY="${CMAKE_CURRENT_BINARY_DIR}/resources")
|
||||
|
||||
rosidl_generate_interfaces(${PROJECT_NAME}_test_msgs
|
||||
msg/Header.msg
|
||||
msg/MessageWithHeader.msg
|
||||
DEPENDENCIES builtin_interfaces
|
||||
LIBRARY_NAME ${PROJECT_NAME}
|
||||
SKIP_INSTALL
|
||||
)
|
||||
|
||||
ament_add_gtest(test_client rclcpp/test_client.cpp)
|
||||
if(TARGET test_client)
|
||||
ament_target_dependencies(test_client
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_client ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_create_timer rclcpp/test_create_timer.cpp)
|
||||
if(TARGET test_create_timer)
|
||||
ament_target_dependencies(test_create_timer
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rcl"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_create_timer ${PROJECT_NAME})
|
||||
target_include_directories(test_create_timer PRIVATE rclcpp/)
|
||||
endif()
|
||||
ament_add_gtest(test_expand_topic_or_service_name rclcpp/test_expand_topic_or_service_name.cpp)
|
||||
if(TARGET test_expand_topic_or_service_name)
|
||||
ament_target_dependencies(test_expand_topic_or_service_name
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_expand_topic_or_service_name ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_function_traits rclcpp/test_function_traits.cpp)
|
||||
if(TARGET test_function_traits)
|
||||
target_include_directories(test_function_traits PUBLIC ../include)
|
||||
ament_target_dependencies(test_function_traits
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
endif()
|
||||
ament_add_gmock(test_intra_process_manager rclcpp/test_intra_process_manager.cpp)
|
||||
if(TARGET test_intra_process_manager)
|
||||
ament_target_dependencies(test_intra_process_manager
|
||||
"rcl"
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_intra_process_manager ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_ring_buffer_implementation rclcpp/test_ring_buffer_implementation.cpp)
|
||||
if(TARGET test_ring_buffer_implementation)
|
||||
ament_target_dependencies(test_ring_buffer_implementation
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_ring_buffer_implementation ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_intra_process_buffer rclcpp/test_intra_process_buffer.cpp)
|
||||
if(TARGET test_intra_process_buffer)
|
||||
ament_target_dependencies(test_intra_process_buffer
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_intra_process_buffer ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_loaned_message rclcpp/test_loaned_message.cpp)
|
||||
ament_target_dependencies(test_loaned_message
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_loaned_message ${PROJECT_NAME})
|
||||
|
||||
ament_add_gtest(test_node rclcpp/test_node.cpp TIMEOUT 240)
|
||||
if(TARGET test_node)
|
||||
ament_target_dependencies(test_node
|
||||
"rcl_interfaces"
|
||||
"rcpputils"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_node ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_node_interfaces__get_node_interfaces
|
||||
rclcpp/node_interfaces/test_get_node_interfaces.cpp)
|
||||
if(TARGET test_node_interfaces__get_node_interfaces)
|
||||
target_link_libraries(test_node_interfaces__get_node_interfaces ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
# TODO(wjwwood): reenable these build failure tests when I can get Jenkins to ignore their output
|
||||
# rclcpp_add_build_failure_test(build_failure__get_node_topics_interface_const_ref_rclcpp_node
|
||||
# rclcpp/node_interfaces/test_does_not_compile/get_node_topics_interface_const_ref_rclcpp_node.cpp)
|
||||
# target_link_libraries(build_failure__get_node_topics_interface_const_ref_rclcpp_node
|
||||
# ${PROJECT_NAME})
|
||||
|
||||
# rclcpp_add_build_failure_test(build_failure__get_node_topics_interface_const_ptr_rclcpp_node
|
||||
# rclcpp/node_interfaces/test_does_not_compile/get_node_topics_interface_const_ptr_rclcpp_node.cpp)
|
||||
# target_link_libraries(build_failure__get_node_topics_interface_const_ptr_rclcpp_node
|
||||
# ${PROJECT_NAME})
|
||||
|
||||
# rclcpp_add_build_failure_test(build_failure__get_node_topics_interface_const_ref_wrapped_node
|
||||
# rclcpp/node_interfaces/test_does_not_compile/get_node_topics_interface_const_ref_wrapped_node.cpp)
|
||||
# target_link_libraries(build_failure__get_node_topics_interface_const_ref_rclcpp_node
|
||||
# ${PROJECT_NAME})
|
||||
|
||||
# rclcpp_add_build_failure_test(build_failure__get_node_topics_interface_const_ptr_wrapped_node
|
||||
# rclcpp/node_interfaces/test_does_not_compile/get_node_topics_interface_const_ptr_wrapped_node.cpp)
|
||||
# target_link_libraries(build_failure__get_node_topics_interface_const_ptr_rclcpp_node
|
||||
# ${PROJECT_NAME})
|
||||
|
||||
ament_add_gtest(test_node_global_args rclcpp/test_node_global_args.cpp)
|
||||
if(TARGET test_node_global_args)
|
||||
ament_target_dependencies(test_node_global_args
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_node_global_args ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_node_options rclcpp/test_node_options.cpp)
|
||||
if(TARGET test_node_options)
|
||||
ament_target_dependencies(test_node_options "rcl")
|
||||
target_link_libraries(test_node_options ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_parameter_client rclcpp/test_parameter_client.cpp)
|
||||
if(TARGET test_parameter_client)
|
||||
ament_target_dependencies(test_parameter_client
|
||||
"rcl_interfaces"
|
||||
)
|
||||
target_link_libraries(test_parameter_client ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_parameter_events_filter rclcpp/test_parameter_events_filter.cpp)
|
||||
if(TARGET test_parameter_events_filter)
|
||||
ament_target_dependencies(test_parameter_events_filter
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_parameter_events_filter ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_parameter rclcpp/test_parameter.cpp)
|
||||
if(TARGET test_parameter)
|
||||
ament_target_dependencies(test_parameter
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_parameter ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_parameter_map rclcpp/test_parameter_map.cpp)
|
||||
if(TARGET test_parameter_map)
|
||||
target_link_libraries(test_parameter_map ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_publisher rclcpp/test_publisher.cpp)
|
||||
if(TARGET test_publisher)
|
||||
ament_target_dependencies(test_publisher
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_publisher ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_publisher_subscription_count_api rclcpp/test_publisher_subscription_count_api.cpp)
|
||||
if(TARGET test_publisher_subscription_count_api)
|
||||
ament_target_dependencies(test_publisher_subscription_count_api
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_publisher_subscription_count_api ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_qos rclcpp/test_qos.cpp)
|
||||
if(TARGET test_qos)
|
||||
ament_target_dependencies(test_qos
|
||||
"rmw"
|
||||
)
|
||||
target_link_libraries(test_qos
|
||||
${PROJECT_NAME}
|
||||
)
|
||||
endif()
|
||||
ament_add_gtest(test_qos_event rclcpp/test_qos_event.cpp)
|
||||
if(TARGET test_qos_event)
|
||||
ament_target_dependencies(test_qos_event
|
||||
"rmw"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_qos_event
|
||||
${PROJECT_NAME}
|
||||
)
|
||||
endif()
|
||||
ament_add_gtest(test_rate rclcpp/test_rate.cpp)
|
||||
if(TARGET test_rate)
|
||||
ament_target_dependencies(test_rate
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_rate
|
||||
${PROJECT_NAME}
|
||||
)
|
||||
endif()
|
||||
ament_add_gtest(test_serialized_message_allocator rclcpp/test_serialized_message_allocator.cpp)
|
||||
if(TARGET test_serialized_message_allocator)
|
||||
ament_target_dependencies(test_serialized_message_allocator
|
||||
test_msgs
|
||||
)
|
||||
target_link_libraries(test_serialized_message_allocator
|
||||
${PROJECT_NAME}
|
||||
)
|
||||
endif()
|
||||
ament_add_gtest(test_serialized_message rclcpp/test_serialized_message.cpp)
|
||||
if(TARGET test_serialized_message)
|
||||
ament_target_dependencies(test_serialized_message
|
||||
test_msgs
|
||||
)
|
||||
target_link_libraries(test_serialized_message
|
||||
${PROJECT_NAME}
|
||||
)
|
||||
endif()
|
||||
ament_add_gtest(test_service rclcpp/test_service.cpp)
|
||||
if(TARGET test_service)
|
||||
ament_target_dependencies(test_service
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
)
|
||||
target_link_libraries(test_service ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_subscription rclcpp/test_subscription.cpp)
|
||||
if(TARGET test_subscription)
|
||||
ament_target_dependencies(test_subscription
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_subscription ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_subscription_publisher_count_api rclcpp/test_subscription_publisher_count_api.cpp)
|
||||
if(TARGET test_subscription_publisher_count_api)
|
||||
ament_target_dependencies(test_subscription_publisher_count_api
|
||||
"rcl_interfaces"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_subscription_publisher_count_api ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_subscription_traits rclcpp/test_subscription_traits.cpp)
|
||||
if(TARGET test_subscription_traits)
|
||||
ament_target_dependencies(test_subscription_traits
|
||||
"rcl"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_subscription_traits ${PROJECT_NAME})
|
||||
endif()
|
||||
ament_add_gtest(test_find_weak_nodes rclcpp/test_find_weak_nodes.cpp)
|
||||
if(TARGET test_find_weak_nodes)
|
||||
ament_target_dependencies(test_find_weak_nodes
|
||||
"rcl"
|
||||
)
|
||||
target_link_libraries(test_find_weak_nodes ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
set(append_library_dirs "${CMAKE_CURRENT_BINARY_DIR}")
|
||||
if(WIN32)
|
||||
set(append_library_dirs "${append_library_dirs}/$<CONFIG>")
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_externally_defined_services rclcpp/test_externally_defined_services.cpp)
|
||||
ament_target_dependencies(test_externally_defined_services
|
||||
"rcl"
|
||||
"test_msgs"
|
||||
)
|
||||
target_link_libraries(test_externally_defined_services ${PROJECT_NAME})
|
||||
|
||||
ament_add_gtest(test_duration rclcpp/test_duration.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_duration)
|
||||
ament_target_dependencies(test_duration
|
||||
"rcl")
|
||||
target_link_libraries(test_duration ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_executor rclcpp/test_executor.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_executor)
|
||||
ament_target_dependencies(test_executor
|
||||
"rcl")
|
||||
target_link_libraries(test_executor ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_logger rclcpp/test_logger.cpp)
|
||||
target_link_libraries(test_logger ${PROJECT_NAME})
|
||||
|
||||
ament_add_gmock(test_logging rclcpp/test_logging.cpp)
|
||||
target_link_libraries(test_logging ${PROJECT_NAME})
|
||||
|
||||
ament_add_gtest(test_time rclcpp/test_time.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_time)
|
||||
ament_target_dependencies(test_time
|
||||
"rcl")
|
||||
target_link_libraries(test_time ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_timer rclcpp/test_timer.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_timer)
|
||||
ament_target_dependencies(test_timer
|
||||
"rcl")
|
||||
target_link_libraries(test_timer ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_time_source rclcpp/test_time_source.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_time_source)
|
||||
ament_target_dependencies(test_time_source
|
||||
"rcl")
|
||||
target_link_libraries(test_time_source ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_utilities rclcpp/test_utilities.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_utilities)
|
||||
ament_target_dependencies(test_utilities
|
||||
"rcl")
|
||||
target_link_libraries(test_utilities ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_init rclcpp/test_init.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_init)
|
||||
ament_target_dependencies(test_init
|
||||
"rcl")
|
||||
target_link_libraries(test_init ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_interface_traits rclcpp/test_interface_traits.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_interface_traits)
|
||||
ament_target_dependencies(test_interface_traits
|
||||
"rcl")
|
||||
target_link_libraries(test_interface_traits ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_multi_threaded_executor rclcpp/executors/test_multi_threaded_executor.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_multi_threaded_executor)
|
||||
ament_target_dependencies(test_multi_threaded_executor
|
||||
"rcl")
|
||||
target_link_libraries(test_multi_threaded_executor ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_guard_condition rclcpp/test_guard_condition.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_guard_condition)
|
||||
target_link_libraries(test_guard_condition ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_wait_set rclcpp/test_wait_set.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}")
|
||||
if(TARGET test_wait_set)
|
||||
ament_target_dependencies(test_wait_set "test_msgs")
|
||||
target_link_libraries(test_wait_set ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_subscription_topic_statistics rclcpp/topic_statistics/test_subscription_topic_statistics.cpp
|
||||
APPEND_LIBRARY_DIRS "${append_library_dirs}"
|
||||
)
|
||||
if(TARGET test_subscription_topic_statistics)
|
||||
ament_target_dependencies(test_subscription_topic_statistics
|
||||
"builtin_interfaces"
|
||||
"libstatistics_collector"
|
||||
"rcl_interfaces"
|
||||
"rcutils"
|
||||
"rmw"
|
||||
"rosidl_runtime_cpp"
|
||||
"rosidl_typesupport_cpp"
|
||||
"statistics_msgs"
|
||||
"test_msgs")
|
||||
rosidl_target_interfaces(test_subscription_topic_statistics ${PROJECT_NAME}_test_msgs "rosidl_typesupport_cpp")
|
||||
target_link_libraries(test_subscription_topic_statistics ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
ament_add_gtest(test_subscription_options rclcpp/test_subscription_options.cpp)
|
||||
if(TARGET test_subscription_options)
|
||||
ament_target_dependencies(test_subscription_options "rcl")
|
||||
target_link_libraries(test_subscription_options ${PROJECT_NAME})
|
||||
endif()
|
||||
|
||||
# Install test resources
|
||||
install(
|
||||
DIRECTORY resources
|
||||
DESTINATION ${CMAKE_CURRENT_BINARY_DIR})
|
||||
@@ -12,8 +12,8 @@
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#ifndef NODE_INTERFACES__NODE_WRAPPER_HPP_
|
||||
#define NODE_INTERFACES__NODE_WRAPPER_HPP_
|
||||
#ifndef RCLCPP__NODE_INTERFACES__NODE_WRAPPER_HPP_
|
||||
#define RCLCPP__NODE_INTERFACES__NODE_WRAPPER_HPP_
|
||||
|
||||
#include <memory>
|
||||
#include <string>
|
||||
@@ -61,4 +61,4 @@ private:
|
||||
rclcpp::Node::SharedPtr node;
|
||||
};
|
||||
|
||||
#endif // NODE_INTERFACES__NODE_WRAPPER_HPP_
|
||||
#endif // RCLCPP__NODE_INTERFACES__NODE_WRAPPER_HPP_
|
||||
118
rclcpp/test/rclcpp/test_create_timer.cpp
Normal file
118
rclcpp/test/rclcpp/test_create_timer.cpp
Normal file
@@ -0,0 +1,118 @@
|
||||
// Copyright 2019 Open Source Robotics Foundation, Inc.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include <atomic>
|
||||
#include <chrono>
|
||||
#include <memory>
|
||||
|
||||
#include "node_interfaces/node_wrapper.hpp"
|
||||
#include "rclcpp/create_timer.hpp"
|
||||
#include "rclcpp/executors.hpp"
|
||||
#include "rclcpp/node.hpp"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
TEST(TestCreateTimer, timer_executes)
|
||||
{
|
||||
rclcpp::init(0, nullptr);
|
||||
auto node = std::make_shared<rclcpp::Node>("test_create_timer_node");
|
||||
|
||||
std::atomic<bool> got_callback{false};
|
||||
|
||||
rclcpp::TimerBase::SharedPtr timer;
|
||||
timer = rclcpp::create_timer(
|
||||
node,
|
||||
node->get_clock(),
|
||||
rclcpp::Duration(0ms),
|
||||
[&got_callback, &timer]() {
|
||||
got_callback = true;
|
||||
timer->cancel();
|
||||
});
|
||||
|
||||
rclcpp::spin_some(node);
|
||||
|
||||
ASSERT_TRUE(got_callback);
|
||||
rclcpp::shutdown();
|
||||
}
|
||||
|
||||
TEST(TestCreateTimer, call_with_node_wrapper_compiles)
|
||||
{
|
||||
rclcpp::init(0, nullptr);
|
||||
NodeWrapper node("test_create_timer_call_with_node_wrapper_compiles");
|
||||
|
||||
rclcpp::TimerBase::SharedPtr timer;
|
||||
timer = rclcpp::create_timer(
|
||||
node,
|
||||
node.get_node_clock_interface()->get_clock(),
|
||||
rclcpp::Duration(0ms),
|
||||
[]() {});
|
||||
rclcpp::shutdown();
|
||||
}
|
||||
|
||||
TEST(TestCreateTimer, call_wall_timer_with_bad_arguments)
|
||||
{
|
||||
rclcpp::init(0, nullptr);
|
||||
NodeWrapper node("test_create_wall_timers_with_bad_arguments");
|
||||
auto callback = []() {};
|
||||
rclcpp::CallbackGroup::SharedPtr group = nullptr;
|
||||
auto node_interface =
|
||||
rclcpp::node_interfaces::get_node_base_interface(node).get();
|
||||
auto timers_interface =
|
||||
rclcpp::node_interfaces::get_node_timers_interface(node).get();
|
||||
|
||||
// Negative period
|
||||
EXPECT_THROW(
|
||||
rclcpp::create_wall_timer(-1ms, callback, group, node_interface, timers_interface),
|
||||
std::invalid_argument);
|
||||
|
||||
// Very negative period
|
||||
constexpr auto nanoseconds_min = std::chrono::nanoseconds::min();
|
||||
EXPECT_THROW(
|
||||
rclcpp::create_wall_timer(
|
||||
nanoseconds_min, callback, group, node_interface, timers_interface),
|
||||
std::invalid_argument);
|
||||
|
||||
// Period must be less than nanoseconds::max()
|
||||
constexpr auto nanoseconds_max = std::chrono::nanoseconds::min();
|
||||
EXPECT_THROW(
|
||||
rclcpp::create_wall_timer(
|
||||
nanoseconds_max, callback, group, node_interface, timers_interface),
|
||||
std::invalid_argument);
|
||||
|
||||
EXPECT_NO_THROW(
|
||||
rclcpp::create_wall_timer(
|
||||
nanoseconds_max - 1us, callback, group, node_interface, timers_interface));
|
||||
|
||||
EXPECT_NO_THROW(
|
||||
rclcpp::create_wall_timer(0ms, callback, group, node_interface, timers_interface));
|
||||
|
||||
// Period must be less than nanoseconds::max()
|
||||
constexpr auto hours_max = std::chrono::hours::max();
|
||||
EXPECT_THROW(
|
||||
rclcpp::create_wall_timer(hours_max, callback, group, node_interface, timers_interface),
|
||||
std::invalid_argument);
|
||||
|
||||
// node_interface is null
|
||||
EXPECT_THROW(
|
||||
rclcpp::create_wall_timer(1ms, callback, group, nullptr, timers_interface),
|
||||
std::invalid_argument);
|
||||
|
||||
// timers_interface is null
|
||||
EXPECT_THROW(
|
||||
rclcpp::create_wall_timer(1ms, callback, group, node_interface, nullptr),
|
||||
std::invalid_argument);
|
||||
rclcpp::shutdown();
|
||||
}
|
||||
199
rclcpp/test/rclcpp/test_executor.cpp
Normal file
199
rclcpp/test/rclcpp/test_executor.cpp
Normal file
@@ -0,0 +1,199 @@
|
||||
// Copyright 2017 Open Source Robotics Foundation, Inc.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include <algorithm>
|
||||
#include <chrono>
|
||||
#include <limits>
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
#include "rcl/error_handling.h"
|
||||
#include "rcl/time.h"
|
||||
#include "rclcpp/clock.hpp"
|
||||
#include "rclcpp/duration.hpp"
|
||||
#include "rclcpp/rclcpp.hpp"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
class TestExecutors : public ::testing::Test
|
||||
{
|
||||
protected:
|
||||
static void SetUpTestCase()
|
||||
{
|
||||
rclcpp::init(0, nullptr);
|
||||
}
|
||||
|
||||
void SetUp()
|
||||
{
|
||||
node = std::make_shared<rclcpp::Node>("my_node");
|
||||
}
|
||||
|
||||
void TearDown()
|
||||
{
|
||||
node.reset();
|
||||
}
|
||||
|
||||
rclcpp::Node::SharedPtr node;
|
||||
};
|
||||
|
||||
// Make sure that executors detach from nodes when destructing
|
||||
TEST_F(TestExecutors, detachOnDestruction) {
|
||||
{
|
||||
rclcpp::executors::SingleThreadedExecutor executor;
|
||||
executor.add_node(node);
|
||||
}
|
||||
{
|
||||
rclcpp::executors::SingleThreadedExecutor executor;
|
||||
EXPECT_NO_THROW(executor.add_node(node));
|
||||
}
|
||||
}
|
||||
|
||||
// Make sure that the executor can automatically remove expired nodes correctly
|
||||
TEST_F(TestExecutors, addTemporaryNode) {
|
||||
rclcpp::executors::SingleThreadedExecutor executor;
|
||||
executor.add_node(std::make_shared<rclcpp::Node>("temporary_node"));
|
||||
EXPECT_NO_THROW(executor.spin_some());
|
||||
}
|
||||
|
||||
// Make sure that the spin_until_future_complete works correctly with std::future
|
||||
TEST_F(TestExecutors, testSpinUntilFutureComplete) {
|
||||
rclcpp::executors::SingleThreadedExecutor executor;
|
||||
std::future<void> future;
|
||||
rclcpp::FutureReturnCode ret;
|
||||
|
||||
// test success
|
||||
future = std::async(
|
||||
[]() {
|
||||
return;
|
||||
});
|
||||
ret = executor.spin_until_future_complete(future, 1s);
|
||||
EXPECT_EQ(rclcpp::FutureReturnCode::SUCCESS, ret);
|
||||
|
||||
// test timeout
|
||||
future = std::async(
|
||||
[]() {
|
||||
std::this_thread::sleep_for(1s);
|
||||
return;
|
||||
});
|
||||
ret = executor.spin_until_future_complete(future, 100ms);
|
||||
EXPECT_EQ(rclcpp::FutureReturnCode::TIMEOUT, ret);
|
||||
}
|
||||
|
||||
// Make sure that the spin_until_future_complete works correctly with std::shared_future
|
||||
TEST_F(TestExecutors, testSpinUntilFutureCompleteSharedFuture) {
|
||||
rclcpp::executors::SingleThreadedExecutor executor;
|
||||
std::future<void> future;
|
||||
rclcpp::FutureReturnCode ret;
|
||||
|
||||
// test success
|
||||
future = std::async(
|
||||
[]() {
|
||||
return;
|
||||
});
|
||||
ret = executor.spin_until_future_complete(future.share(), 1s);
|
||||
EXPECT_EQ(rclcpp::FutureReturnCode::SUCCESS, ret);
|
||||
|
||||
// test timeout
|
||||
future = std::async(
|
||||
[]() {
|
||||
std::this_thread::sleep_for(1s);
|
||||
return;
|
||||
});
|
||||
ret = executor.spin_until_future_complete(future.share(), 100ms);
|
||||
EXPECT_EQ(rclcpp::FutureReturnCode::TIMEOUT, ret);
|
||||
}
|
||||
|
||||
class TestWaitable : public rclcpp::Waitable
|
||||
{
|
||||
public:
|
||||
TestWaitable()
|
||||
{
|
||||
rcl_guard_condition_options_t guard_condition_options =
|
||||
rcl_guard_condition_get_default_options();
|
||||
|
||||
gc_ = rcl_get_zero_initialized_guard_condition();
|
||||
rcl_ret_t ret = rcl_guard_condition_init(
|
||||
&gc_,
|
||||
rclcpp::contexts::get_global_default_context()->get_rcl_context().get(),
|
||||
guard_condition_options);
|
||||
if (RCL_RET_OK != ret) {
|
||||
rclcpp::exceptions::throw_from_rcl_error(ret);
|
||||
}
|
||||
}
|
||||
|
||||
bool
|
||||
add_to_wait_set(rcl_wait_set_t * wait_set) override
|
||||
{
|
||||
rcl_ret_t ret = rcl_wait_set_add_guard_condition(wait_set, &gc_, NULL);
|
||||
if (RCL_RET_OK != ret) {
|
||||
return false;
|
||||
}
|
||||
ret = rcl_trigger_guard_condition(&gc_);
|
||||
return RCL_RET_OK == ret;
|
||||
}
|
||||
|
||||
bool
|
||||
is_ready(rcl_wait_set_t * wait_set) override
|
||||
{
|
||||
(void)wait_set;
|
||||
return true;
|
||||
}
|
||||
|
||||
void
|
||||
execute() override
|
||||
{
|
||||
count_++;
|
||||
std::this_thread::sleep_for(100ms);
|
||||
}
|
||||
|
||||
size_t
|
||||
get_number_of_ready_guard_conditions() override {return 1;}
|
||||
|
||||
size_t
|
||||
get_count()
|
||||
{
|
||||
return count_;
|
||||
}
|
||||
|
||||
private:
|
||||
size_t count_ = 0;
|
||||
rcl_guard_condition_t gc_;
|
||||
};
|
||||
|
||||
TEST_F(TestExecutors, testSpinAllvsSpinSome) {
|
||||
{
|
||||
rclcpp::executors::SingleThreadedExecutor executor;
|
||||
auto waitable_interfaces = node->get_node_waitables_interface();
|
||||
auto my_waitable = std::make_shared<TestWaitable>();
|
||||
waitable_interfaces->add_waitable(my_waitable, nullptr);
|
||||
executor.add_node(node);
|
||||
executor.spin_all(1s);
|
||||
executor.remove_node(node);
|
||||
EXPECT_GT(my_waitable->get_count(), 1u);
|
||||
waitable_interfaces->remove_waitable(my_waitable, nullptr);
|
||||
}
|
||||
{
|
||||
rclcpp::executors::SingleThreadedExecutor executor;
|
||||
auto waitable_interfaces = node->get_node_waitables_interface();
|
||||
auto my_waitable = std::make_shared<TestWaitable>();
|
||||
waitable_interfaces->add_waitable(my_waitable, nullptr);
|
||||
executor.add_node(node);
|
||||
executor.spin_some(1s);
|
||||
executor.remove_node(node);
|
||||
EXPECT_EQ(my_waitable->get_count(), 1u);
|
||||
waitable_interfaces->remove_waitable(my_waitable, nullptr);
|
||||
}
|
||||
}
|
||||
@@ -22,8 +22,8 @@
|
||||
|
||||
#include "statistics_msgs/msg/metrics_message.hpp"
|
||||
|
||||
#ifndef TOPIC_STATISTICS__TEST_TOPIC_STATS_UTILS_HPP_
|
||||
#define TOPIC_STATISTICS__TEST_TOPIC_STATS_UTILS_HPP_
|
||||
#ifndef RCLCPP__TOPIC_STATISTICS__TEST_TOPIC_STATS_UTILS_HPP_
|
||||
#define RCLCPP__TOPIC_STATISTICS__TEST_TOPIC_STATS_UTILS_HPP_
|
||||
|
||||
namespace rclcpp
|
||||
{
|
||||
@@ -149,4 +149,4 @@ private:
|
||||
} // namespace topic_statistics
|
||||
} // namespace rclcpp
|
||||
|
||||
#endif // TOPIC_STATISTICS__TEST_TOPIC_STATS_UTILS_HPP_
|
||||
#endif // RCLCPP__TOPIC_STATISTICS__TEST_TOPIC_STATS_UTILS_HPP_
|
||||
@@ -1,63 +0,0 @@
|
||||
// Copyright 2019 Open Source Robotics Foundation, Inc.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include <atomic>
|
||||
#include <chrono>
|
||||
#include <memory>
|
||||
|
||||
#include "rclcpp/create_timer.hpp"
|
||||
#include "rclcpp/executors.hpp"
|
||||
#include "rclcpp/node.hpp"
|
||||
#include "node_interfaces/node_wrapper.hpp"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
TEST(TestCreateTimer, timer_executes)
|
||||
{
|
||||
rclcpp::init(0, nullptr);
|
||||
auto node = std::make_shared<rclcpp::Node>("test_create_timer_node");
|
||||
|
||||
std::atomic<bool> got_callback{false};
|
||||
|
||||
rclcpp::TimerBase::SharedPtr timer;
|
||||
timer = rclcpp::create_timer(
|
||||
node,
|
||||
node->get_clock(),
|
||||
rclcpp::Duration(0ms),
|
||||
[&got_callback, &timer]() {
|
||||
got_callback = true;
|
||||
timer->cancel();
|
||||
});
|
||||
|
||||
rclcpp::spin_some(node);
|
||||
|
||||
ASSERT_TRUE(got_callback);
|
||||
rclcpp::shutdown();
|
||||
}
|
||||
|
||||
TEST(TestCreateTimer, call_with_node_wrapper_compiles)
|
||||
{
|
||||
rclcpp::init(0, nullptr);
|
||||
NodeWrapper node("test_create_timer_call_with_node_wrapper_compiles");
|
||||
|
||||
rclcpp::TimerBase::SharedPtr timer;
|
||||
timer = rclcpp::create_timer(
|
||||
node,
|
||||
node.get_node_clock_interface()->get_clock(),
|
||||
rclcpp::Duration(0ms),
|
||||
[]() {});
|
||||
rclcpp::shutdown();
|
||||
}
|
||||
@@ -1,69 +0,0 @@
|
||||
// Copyright 2017 Open Source Robotics Foundation, Inc.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include <algorithm>
|
||||
#include <chrono>
|
||||
#include <limits>
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
#include "rcl/error_handling.h"
|
||||
#include "rcl/time.h"
|
||||
#include "rclcpp/clock.hpp"
|
||||
#include "rclcpp/duration.hpp"
|
||||
#include "rclcpp/rclcpp.hpp"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
class TestExecutors : public ::testing::Test
|
||||
{
|
||||
protected:
|
||||
static void SetUpTestCase()
|
||||
{
|
||||
rclcpp::init(0, nullptr);
|
||||
}
|
||||
|
||||
void SetUp()
|
||||
{
|
||||
node = std::make_shared<rclcpp::Node>("my_node");
|
||||
}
|
||||
|
||||
void TearDown()
|
||||
{
|
||||
node.reset();
|
||||
}
|
||||
|
||||
rclcpp::Node::SharedPtr node;
|
||||
};
|
||||
|
||||
// Make sure that executors detach from nodes when destructing
|
||||
TEST_F(TestExecutors, detachOnDestruction) {
|
||||
{
|
||||
rclcpp::executors::SingleThreadedExecutor executor;
|
||||
executor.add_node(node);
|
||||
}
|
||||
{
|
||||
rclcpp::executors::SingleThreadedExecutor executor;
|
||||
EXPECT_NO_THROW(executor.add_node(node));
|
||||
}
|
||||
}
|
||||
|
||||
// Make sure that the executor can automatically remove expired nodes correctly
|
||||
TEST_F(TestExecutors, addTemporaryNode) {
|
||||
rclcpp::executors::SingleThreadedExecutor executor;
|
||||
executor.add_node(std::make_shared<rclcpp::Node>("temporary_node"));
|
||||
EXPECT_NO_THROW(executor.spin_some());
|
||||
}
|
||||
@@ -3,13 +3,12 @@ Changelog for package rclcpp_action
|
||||
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
|
||||
2.0.2 (2020-07-07)
|
||||
3.0.0 (2020-06-18)
|
||||
------------------
|
||||
|
||||
2.0.1 (2020-06-23)
|
||||
------------------
|
||||
* Fixed doxygen warnings (`#1163 <https://github.com/ros2/rclcpp/issues/1163>`_) (`#1191 <https://github.com/ros2/rclcpp/issues/1191>`_)
|
||||
* Contributors: Alejandro Hernández Cordero
|
||||
* Add rcl_action_client_options when creating action client. (`#1133 <https://github.com/ros2/rclcpp/issues/1133>`_)
|
||||
* Fix doxygen warnings (`#1163 <https://github.com/ros2/rclcpp/issues/1163>`_)
|
||||
* Increase rclcpp_action test coverage (`#1153 <https://github.com/ros2/rclcpp/issues/1153>`_)
|
||||
* Contributors: Alejandro Hernández Cordero, Michel Hidalgo, tomoya
|
||||
|
||||
2.0.0 (2020-06-01)
|
||||
------------------
|
||||
|
||||
@@ -317,7 +317,7 @@ public:
|
||||
rclcpp::node_interfaces::NodeGraphInterface::SharedPtr node_graph,
|
||||
rclcpp::node_interfaces::NodeLoggingInterface::SharedPtr node_logging,
|
||||
const std::string & action_name,
|
||||
const rcl_action_client_options_t client_options = rcl_action_client_get_default_options()
|
||||
const rcl_action_client_options_t & client_options = rcl_action_client_get_default_options()
|
||||
)
|
||||
: ClientBase(
|
||||
node_base, node_graph, node_logging, action_name,
|
||||
|
||||
@@ -37,6 +37,7 @@ namespace rclcpp_action
|
||||
* \param[in] name The action name.
|
||||
* \param[in] group The action client will be added to this callback group.
|
||||
* If `nullptr`, then the action client is added to the default callback group.
|
||||
* \param[in] options Options to pass to the underlying `rcl_action_client_t`.
|
||||
*/
|
||||
template<typename ActionT>
|
||||
typename Client<ActionT>::SharedPtr
|
||||
@@ -46,7 +47,8 @@ create_client(
|
||||
rclcpp::node_interfaces::NodeLoggingInterface::SharedPtr node_logging_interface,
|
||||
rclcpp::node_interfaces::NodeWaitablesInterface::SharedPtr node_waitables_interface,
|
||||
const std::string & name,
|
||||
rclcpp::CallbackGroup::SharedPtr group = nullptr)
|
||||
rclcpp::CallbackGroup::SharedPtr group = nullptr,
|
||||
const rcl_action_client_options_t & options = rcl_action_client_get_default_options())
|
||||
{
|
||||
std::weak_ptr<rclcpp::node_interfaces::NodeWaitablesInterface> weak_node =
|
||||
node_waitables_interface;
|
||||
@@ -59,20 +61,19 @@ create_client(
|
||||
return;
|
||||
}
|
||||
auto shared_node = weak_node.lock();
|
||||
if (!shared_node) {
|
||||
return;
|
||||
}
|
||||
// API expects a shared pointer, give it one with a deleter that does nothing.
|
||||
std::shared_ptr<Client<ActionT>> fake_shared_ptr(ptr, [](Client<ActionT> *) {});
|
||||
if (shared_node) {
|
||||
// API expects a shared pointer, give it one with a deleter that does nothing.
|
||||
std::shared_ptr<Client<ActionT>> fake_shared_ptr(ptr, [](Client<ActionT> *) {});
|
||||
|
||||
if (group_is_null) {
|
||||
// Was added to default group
|
||||
shared_node->remove_waitable(fake_shared_ptr, nullptr);
|
||||
} else {
|
||||
// Was added to a specfic group
|
||||
auto shared_group = weak_group.lock();
|
||||
if (shared_group) {
|
||||
shared_node->remove_waitable(fake_shared_ptr, shared_group);
|
||||
if (group_is_null) {
|
||||
// Was added to default group
|
||||
shared_node->remove_waitable(fake_shared_ptr, nullptr);
|
||||
} else {
|
||||
// Was added to a specific group
|
||||
auto shared_group = weak_group.lock();
|
||||
if (shared_group) {
|
||||
shared_node->remove_waitable(fake_shared_ptr, shared_group);
|
||||
}
|
||||
}
|
||||
}
|
||||
delete ptr;
|
||||
@@ -83,7 +84,8 @@ create_client(
|
||||
node_base_interface,
|
||||
node_graph_interface,
|
||||
node_logging_interface,
|
||||
name),
|
||||
name,
|
||||
options),
|
||||
deleter);
|
||||
|
||||
node_waitables_interface->add_waitable(action_client, group);
|
||||
@@ -96,13 +98,15 @@ create_client(
|
||||
* \param[in] name The action name.
|
||||
* \param[in] group The action client will be added to this callback group.
|
||||
* If `nullptr`, then the action client is added to the default callback group.
|
||||
* \param[in] options Options to pass to the underlying `rcl_action_client_t`.
|
||||
*/
|
||||
template<typename ActionT, typename NodeT>
|
||||
typename Client<ActionT>::SharedPtr
|
||||
create_client(
|
||||
NodeT node,
|
||||
const std::string & name,
|
||||
rclcpp::CallbackGroup::SharedPtr group = nullptr)
|
||||
rclcpp::CallbackGroup::SharedPtr group = nullptr,
|
||||
const rcl_action_client_options_t & options = rcl_action_client_get_default_options())
|
||||
{
|
||||
return rclcpp_action::create_client<ActionT>(
|
||||
node->get_node_base_interface(),
|
||||
@@ -110,7 +114,8 @@ create_client(
|
||||
node->get_node_logging_interface(),
|
||||
node->get_node_waitables_interface(),
|
||||
name,
|
||||
group);
|
||||
group,
|
||||
options);
|
||||
}
|
||||
} // namespace rclcpp_action
|
||||
|
||||
|
||||
@@ -49,7 +49,7 @@ namespace rclcpp_action
|
||||
* The return from this callback only indicates if the server will try to cancel a goal.
|
||||
* It does not indicate if the goal was actually canceled.
|
||||
* \param[in] handle_accepted A callback that is called to give the user a handle to the goal.
|
||||
* \param[in] options options to pass to the underlying `rcl_action_server_t`.
|
||||
* \param[in] options Options to pass to the underlying `rcl_action_server_t`.
|
||||
* \param[in] group The action server will be added to this callback group.
|
||||
* If `nullptr`, then the action server is added to the default callback group.
|
||||
*/
|
||||
@@ -78,20 +78,19 @@ create_server(
|
||||
return;
|
||||
}
|
||||
auto shared_node = weak_node.lock();
|
||||
if (!shared_node) {
|
||||
return;
|
||||
}
|
||||
// API expects a shared pointer, give it one with a deleter that does nothing.
|
||||
std::shared_ptr<Server<ActionT>> fake_shared_ptr(ptr, [](Server<ActionT> *) {});
|
||||
if (shared_node) {
|
||||
// API expects a shared pointer, give it one with a deleter that does nothing.
|
||||
std::shared_ptr<Server<ActionT>> fake_shared_ptr(ptr, [](Server<ActionT> *) {});
|
||||
|
||||
if (group_is_null) {
|
||||
// Was added to default group
|
||||
shared_node->remove_waitable(fake_shared_ptr, nullptr);
|
||||
} else {
|
||||
// Was added to a specfic group
|
||||
auto shared_group = weak_group.lock();
|
||||
if (shared_group) {
|
||||
shared_node->remove_waitable(fake_shared_ptr, shared_group);
|
||||
if (group_is_null) {
|
||||
// Was added to default group
|
||||
shared_node->remove_waitable(fake_shared_ptr, nullptr);
|
||||
} else {
|
||||
// Was added to a specific group
|
||||
auto shared_group = weak_group.lock();
|
||||
if (shared_group) {
|
||||
shared_node->remove_waitable(fake_shared_ptr, shared_group);
|
||||
}
|
||||
}
|
||||
}
|
||||
delete ptr;
|
||||
@@ -124,7 +123,7 @@ create_server(
|
||||
* The return from this callback only indicates if the server will try to cancel a goal.
|
||||
* It does not indicate if the goal was actually canceled.
|
||||
* \param[in] handle_accepted A callback that is called to give the user a handle to the goal.
|
||||
* \param[in] options options to pass to the underlying `rcl_action_server_t`.
|
||||
* \param[in] options Options to pass to the underlying `rcl_action_server_t`.
|
||||
* \param[in] group The action server will be added to this callback group.
|
||||
* If `nullptr`, then the action server is added to the default callback group.
|
||||
*/
|
||||
|
||||
@@ -296,7 +296,7 @@ public:
|
||||
* \param[in] name the name of an action.
|
||||
* The same name and type must be used by both the action client and action server to
|
||||
* communicate.
|
||||
* \param[in] options options to pass to the underlying `rcl_action_server_t`.
|
||||
* \param[in] options Options to pass to the underlying `rcl_action_server_t`.
|
||||
* \param[in] handle_goal a callback that decides if a goal should be accepted or rejected.
|
||||
* \param[in] handle_cancel a callback that decides if a goal should be attemted to be canceled.
|
||||
* The return from this callback only indicates if the server will try to cancel a goal.
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
<?xml-model href="http://download.ros.org/schema/package_format2.xsd" schematypens="http://www.w3.org/2001/XMLSchema"?>
|
||||
<package format="2">
|
||||
<name>rclcpp_action</name>
|
||||
<version>2.0.2</version>
|
||||
<version>3.0.0</version>
|
||||
<description>Adds action APIs for C++.</description>
|
||||
<maintainer email="dthomas@osrfoundation.org">Dirk Thomas</maintainer>
|
||||
<license>Apache License 2.0</license>
|
||||
|
||||
@@ -32,6 +32,7 @@
|
||||
|
||||
#include <test_msgs/action/fibonacci.hpp>
|
||||
|
||||
#include <future>
|
||||
#include <map>
|
||||
#include <memory>
|
||||
#include <string>
|
||||
@@ -73,7 +74,7 @@ protected:
|
||||
rclcpp::init(0, nullptr);
|
||||
}
|
||||
|
||||
void SetUp()
|
||||
void SetUpServer()
|
||||
{
|
||||
rcl_allocator_t allocator = rcl_get_default_allocator();
|
||||
|
||||
@@ -211,7 +212,10 @@ protected:
|
||||
ASSERT_TRUE(status_publisher != nullptr);
|
||||
allocator.deallocate(status_topic_name, allocator.state);
|
||||
server_executor.add_node(server_node);
|
||||
}
|
||||
|
||||
void SetUp() override
|
||||
{
|
||||
client_node = std::make_shared<rclcpp::Node>(client_node_name, namespace_name);
|
||||
client_executor.add_node(client_node);
|
||||
|
||||
@@ -219,7 +223,12 @@ protected:
|
||||
ASSERT_EQ(RCL_RET_OK, rcl_set_ros_time_override(clock.get_clock_handle(), RCL_S_TO_NS(1)));
|
||||
}
|
||||
|
||||
void TearDown()
|
||||
static void TearDownTestCase()
|
||||
{
|
||||
rclcpp::shutdown();
|
||||
}
|
||||
|
||||
void TearDownServer()
|
||||
{
|
||||
status_publisher.reset();
|
||||
feedback_publisher.reset();
|
||||
@@ -227,6 +236,10 @@ protected:
|
||||
result_service.reset();
|
||||
goal_service.reset();
|
||||
server_node.reset();
|
||||
}
|
||||
|
||||
void TearDown() override
|
||||
{
|
||||
client_node.reset();
|
||||
}
|
||||
|
||||
@@ -265,15 +278,42 @@ protected:
|
||||
typename rclcpp::Publisher<ActionStatusMessage>::SharedPtr status_publisher;
|
||||
};
|
||||
|
||||
class TestClientAgainstServer : public TestClient
|
||||
{
|
||||
protected:
|
||||
void SetUp() override
|
||||
{
|
||||
SetUpServer();
|
||||
TestClient::SetUp();
|
||||
}
|
||||
|
||||
void TearDown() override
|
||||
{
|
||||
TestClient::TearDown();
|
||||
TearDownServer();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
TEST_F(TestClient, construction_and_destruction)
|
||||
{
|
||||
ASSERT_NO_THROW(rclcpp_action::create_client<ActionType>(client_node, action_name).reset());
|
||||
}
|
||||
|
||||
TEST_F(TestClient, construction_and_destruction_after_node)
|
||||
{
|
||||
ASSERT_NO_THROW(
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
client_node.reset();
|
||||
});
|
||||
}
|
||||
|
||||
TEST_F(TestClient, construction_and_destruction_callback_group)
|
||||
{
|
||||
auto group = client_node->create_callback_group(
|
||||
rclcpp::CallbackGroupType::MutuallyExclusive);
|
||||
const rcl_action_client_options_t & options = rcl_action_client_get_default_options();
|
||||
ASSERT_NO_THROW(
|
||||
rclcpp_action::create_client<ActionType>(
|
||||
client_node->get_node_base_interface(),
|
||||
@@ -281,11 +321,29 @@ TEST_F(TestClient, construction_and_destruction_callback_group)
|
||||
client_node->get_node_logging_interface(),
|
||||
client_node->get_node_waitables_interface(),
|
||||
action_name,
|
||||
group
|
||||
group,
|
||||
options
|
||||
).reset());
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_send_goal_no_callbacks)
|
||||
TEST_F(TestClient, wait_for_action_server)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
EXPECT_FALSE(action_client->wait_for_action_server(0ms));
|
||||
EXPECT_FALSE(action_client->wait_for_action_server(100ms));
|
||||
auto future = std::async(
|
||||
std::launch::async, [&action_client]() {
|
||||
return action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT);
|
||||
});
|
||||
SetUpServer();
|
||||
EXPECT_TRUE(future.get());
|
||||
TearDownServer();
|
||||
|
||||
client_node.reset(); // Drop node before action client
|
||||
EXPECT_THROW(action_client->wait_for_action_server(0ms), rclcpp::exceptions::InvalidNodeError);
|
||||
}
|
||||
|
||||
TEST_F(TestClientAgainstServer, async_send_goal_no_callbacks)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
@@ -306,7 +364,24 @@ TEST_F(TestClient, async_send_goal_no_callbacks)
|
||||
EXPECT_FALSE(goal_handle->is_result_aware());
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_send_goal_no_callbacks_wait_for_result)
|
||||
TEST_F(TestClientAgainstServer, bad_goal_handles)
|
||||
{
|
||||
auto action_client0 = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client0->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
|
||||
ActionGoal goal;
|
||||
goal.order = 0;
|
||||
auto future_goal_handle = action_client0->async_send_goal(goal);
|
||||
dual_spin_until_future_complete(future_goal_handle);
|
||||
auto goal_handle = future_goal_handle.get();
|
||||
|
||||
auto action_client1 = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
using rclcpp_action::exceptions::UnknownGoalHandleError;
|
||||
EXPECT_THROW(action_client1->async_get_result(goal_handle), UnknownGoalHandleError);
|
||||
EXPECT_THROW(action_client1->async_cancel_goal(goal_handle), UnknownGoalHandleError);
|
||||
}
|
||||
|
||||
TEST_F(TestClientAgainstServer, async_send_goal_no_callbacks_wait_for_result)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
@@ -329,13 +404,33 @@ TEST_F(TestClient, async_send_goal_no_callbacks_wait_for_result)
|
||||
EXPECT_EQ(5, wrapped_result.result->sequence[5]);
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_send_goal_with_goal_response_callback_wait_for_result)
|
||||
TEST_F(TestClientAgainstServer, async_send_goal_no_callbacks_then_invalidate)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
|
||||
ActionGoal goal;
|
||||
goal.order = 4;
|
||||
goal.order = 5;
|
||||
auto future_goal_handle = action_client->async_send_goal(goal);
|
||||
dual_spin_until_future_complete(future_goal_handle);
|
||||
auto goal_handle = future_goal_handle.get();
|
||||
ASSERT_NE(nullptr, goal_handle);
|
||||
EXPECT_EQ(rclcpp_action::GoalStatus::STATUS_ACCEPTED, goal_handle->get_status());
|
||||
auto future_result = action_client->async_get_result(goal_handle);
|
||||
EXPECT_TRUE(goal_handle->is_result_aware());
|
||||
|
||||
action_client.reset(); // Ensure goal handle is invalidated once client goes out of scope
|
||||
|
||||
EXPECT_EQ(rclcpp_action::GoalStatus::STATUS_UNKNOWN, goal_handle->get_status());
|
||||
using rclcpp_action::exceptions::UnawareGoalHandleError;
|
||||
EXPECT_THROW(future_result.get(), UnawareGoalHandleError);
|
||||
}
|
||||
|
||||
TEST_F(TestClientAgainstServer, async_send_goal_with_goal_response_callback_wait_for_result)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
|
||||
bool goal_response_received = false;
|
||||
auto send_goal_ops = rclcpp_action::Client<ActionType>::SendGoalOptions();
|
||||
send_goal_ops.goal_response_callback =
|
||||
@@ -347,23 +442,37 @@ TEST_F(TestClient, async_send_goal_with_goal_response_callback_wait_for_result)
|
||||
goal_response_received = true;
|
||||
}
|
||||
};
|
||||
auto future_goal_handle = action_client->async_send_goal(goal, send_goal_ops);
|
||||
dual_spin_until_future_complete(future_goal_handle);
|
||||
auto goal_handle = future_goal_handle.get();
|
||||
EXPECT_TRUE(goal_response_received);
|
||||
EXPECT_EQ(rclcpp_action::GoalStatus::STATUS_ACCEPTED, goal_handle->get_status());
|
||||
EXPECT_FALSE(goal_handle->is_feedback_aware());
|
||||
EXPECT_FALSE(goal_handle->is_result_aware());
|
||||
auto future_result = action_client->async_get_result(goal_handle);
|
||||
EXPECT_TRUE(goal_handle->is_result_aware());
|
||||
dual_spin_until_future_complete(future_result);
|
||||
auto wrapped_result = future_result.get();
|
||||
|
||||
ASSERT_EQ(5u, wrapped_result.result->sequence.size());
|
||||
EXPECT_EQ(3, wrapped_result.result->sequence.back());
|
||||
{
|
||||
ActionGoal bad_goal;
|
||||
bad_goal.order = -1;
|
||||
auto future_goal_handle = action_client->async_send_goal(bad_goal, send_goal_ops);
|
||||
dual_spin_until_future_complete(future_goal_handle);
|
||||
auto goal_handle = future_goal_handle.get();
|
||||
EXPECT_FALSE(goal_response_received);
|
||||
EXPECT_EQ(nullptr, goal_handle);
|
||||
}
|
||||
|
||||
{
|
||||
ActionGoal goal;
|
||||
goal.order = 4;
|
||||
auto future_goal_handle = action_client->async_send_goal(goal, send_goal_ops);
|
||||
dual_spin_until_future_complete(future_goal_handle);
|
||||
auto goal_handle = future_goal_handle.get();
|
||||
EXPECT_TRUE(goal_response_received);
|
||||
EXPECT_EQ(rclcpp_action::GoalStatus::STATUS_ACCEPTED, goal_handle->get_status());
|
||||
EXPECT_FALSE(goal_handle->is_feedback_aware());
|
||||
EXPECT_FALSE(goal_handle->is_result_aware());
|
||||
auto future_result = action_client->async_get_result(goal_handle);
|
||||
EXPECT_TRUE(goal_handle->is_result_aware());
|
||||
dual_spin_until_future_complete(future_result);
|
||||
auto wrapped_result = future_result.get();
|
||||
ASSERT_EQ(5u, wrapped_result.result->sequence.size());
|
||||
EXPECT_EQ(3, wrapped_result.result->sequence.back());
|
||||
}
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_send_goal_with_feedback_callback_wait_for_result)
|
||||
TEST_F(TestClientAgainstServer, async_send_goal_with_feedback_callback_wait_for_result)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
@@ -397,7 +506,7 @@ TEST_F(TestClient, async_send_goal_with_feedback_callback_wait_for_result)
|
||||
EXPECT_EQ(5, feedback_count);
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_send_goal_with_result_callback_wait_for_result)
|
||||
TEST_F(TestClientAgainstServer, async_send_goal_with_result_callback_wait_for_result)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
@@ -432,7 +541,7 @@ TEST_F(TestClient, async_send_goal_with_result_callback_wait_for_result)
|
||||
EXPECT_EQ(3, wrapped_result.result->sequence.back());
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_get_result_with_callback)
|
||||
TEST_F(TestClientAgainstServer, async_get_result_with_callback)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
@@ -467,7 +576,7 @@ TEST_F(TestClient, async_get_result_with_callback)
|
||||
EXPECT_EQ(3, wrapped_result.result->sequence.back());
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_cancel_one_goal)
|
||||
TEST_F(TestClientAgainstServer, async_cancel_one_goal)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
@@ -485,7 +594,7 @@ TEST_F(TestClient, async_cancel_one_goal)
|
||||
EXPECT_EQ(ActionCancelGoalResponse::ERROR_NONE, cancel_response->return_code);
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_cancel_one_goal_with_callback)
|
||||
TEST_F(TestClientAgainstServer, async_cancel_one_goal_with_callback)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
@@ -519,7 +628,7 @@ TEST_F(TestClient, async_cancel_one_goal_with_callback)
|
||||
EXPECT_TRUE(cancel_response_received);
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_cancel_all_goals)
|
||||
TEST_F(TestClientAgainstServer, async_cancel_all_goals)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
@@ -555,7 +664,7 @@ TEST_F(TestClient, async_cancel_all_goals)
|
||||
EXPECT_EQ(rclcpp_action::GoalStatus::STATUS_CANCELED, goal_handle1->get_status());
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_cancel_all_goals_with_callback)
|
||||
TEST_F(TestClientAgainstServer, async_cancel_all_goals_with_callback)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
@@ -605,7 +714,7 @@ TEST_F(TestClient, async_cancel_all_goals_with_callback)
|
||||
EXPECT_EQ(rclcpp_action::GoalStatus::STATUS_CANCELED, goal_handle1->get_status());
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_cancel_some_goals)
|
||||
TEST_F(TestClientAgainstServer, async_cancel_some_goals)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
@@ -636,7 +745,7 @@ TEST_F(TestClient, async_cancel_some_goals)
|
||||
EXPECT_EQ(rclcpp_action::GoalStatus::STATUS_CANCELED, goal_handle0->get_status());
|
||||
}
|
||||
|
||||
TEST_F(TestClient, async_cancel_some_goals_with_callback)
|
||||
TEST_F(TestClientAgainstServer, async_cancel_some_goals_with_callback)
|
||||
{
|
||||
auto action_client = rclcpp_action::create_client<ActionType>(client_node, action_name);
|
||||
ASSERT_TRUE(action_client->wait_for_action_server(WAIT_FOR_SERVER_TIMEOUT));
|
||||
|
||||
@@ -82,17 +82,42 @@ TEST_F(TestServer, construction_and_destruction)
|
||||
{
|
||||
auto node = std::make_shared<rclcpp::Node>("construct_node", "/rclcpp_action/construct");
|
||||
|
||||
using GoalHandle = rclcpp_action::ServerGoalHandle<Fibonacci>;
|
||||
auto as = rclcpp_action::create_server<Fibonacci>(
|
||||
node, "fibonacci",
|
||||
[](const GoalUUID &, std::shared_ptr<const Fibonacci::Goal>) {
|
||||
return rclcpp_action::GoalResponse::REJECT;
|
||||
},
|
||||
[](std::shared_ptr<GoalHandle>) {
|
||||
return rclcpp_action::CancelResponse::REJECT;
|
||||
},
|
||||
[](std::shared_ptr<GoalHandle>) {});
|
||||
(void)as;
|
||||
ASSERT_NO_THROW(
|
||||
{
|
||||
using GoalHandle = rclcpp_action::ServerGoalHandle<Fibonacci>;
|
||||
auto as = rclcpp_action::create_server<Fibonacci>(
|
||||
node, "fibonacci",
|
||||
[](const GoalUUID &, std::shared_ptr<const Fibonacci::Goal>) {
|
||||
return rclcpp_action::GoalResponse::REJECT;
|
||||
},
|
||||
[](std::shared_ptr<GoalHandle>) {
|
||||
return rclcpp_action::CancelResponse::REJECT;
|
||||
},
|
||||
[](std::shared_ptr<GoalHandle>) {});
|
||||
(void)as;
|
||||
});
|
||||
}
|
||||
|
||||
TEST_F(TestServer, construction_and_destruction_after_node)
|
||||
{
|
||||
auto node = std::make_shared<rclcpp::Node>("construct_node", "/rclcpp_action/construct");
|
||||
|
||||
ASSERT_NO_THROW(
|
||||
{
|
||||
using GoalHandle = rclcpp_action::ServerGoalHandle<Fibonacci>;
|
||||
auto as = rclcpp_action::create_server<Fibonacci>(
|
||||
node, "fibonacci",
|
||||
[](const GoalUUID &, std::shared_ptr<const Fibonacci::Goal>) {
|
||||
return rclcpp_action::GoalResponse::REJECT;
|
||||
},
|
||||
[](std::shared_ptr<GoalHandle>) {
|
||||
return rclcpp_action::CancelResponse::REJECT;
|
||||
},
|
||||
[](std::shared_ptr<GoalHandle>) {});
|
||||
(void)as;
|
||||
|
||||
node.reset();
|
||||
});
|
||||
}
|
||||
|
||||
TEST_F(TestServer, construction_and_destruction_callback_group)
|
||||
@@ -733,6 +758,84 @@ TEST_F(TestServer, get_result)
|
||||
|
||||
using GoalHandle = rclcpp_action::ServerGoalHandle<Fibonacci>;
|
||||
|
||||
auto handle_cancel = [](std::shared_ptr<GoalHandle>)
|
||||
{
|
||||
return rclcpp_action::CancelResponse::REJECT;
|
||||
};
|
||||
|
||||
std::shared_ptr<GoalHandle> received_handle;
|
||||
auto handle_accepted = [&received_handle](std::shared_ptr<GoalHandle> handle)
|
||||
{
|
||||
received_handle = handle;
|
||||
};
|
||||
|
||||
const std::chrono::milliseconds result_timeout{50};
|
||||
|
||||
rcl_action_server_options_t options = rcl_action_server_get_default_options();
|
||||
options.result_timeout.nanoseconds = RCL_MS_TO_NS(result_timeout.count());
|
||||
auto as = rclcpp_action::create_server<Fibonacci>(
|
||||
node, "fibonacci",
|
||||
handle_goal,
|
||||
handle_cancel,
|
||||
handle_accepted,
|
||||
options);
|
||||
(void)as;
|
||||
|
||||
send_goal_request(node, uuid);
|
||||
|
||||
// Send result request
|
||||
auto result_client = node->create_client<Fibonacci::Impl::GetResultService>(
|
||||
"fibonacci/_action/get_result");
|
||||
if (!result_client->wait_for_service(std::chrono::seconds(20))) {
|
||||
throw std::runtime_error("get result service didn't become available");
|
||||
}
|
||||
auto request = std::make_shared<Fibonacci::Impl::GetResultService::Request>();
|
||||
request->goal_id.uuid = uuid;
|
||||
auto future = result_client->async_send_request(request);
|
||||
|
||||
// Send a result
|
||||
auto result = std::make_shared<Fibonacci::Result>();
|
||||
result->sequence = {5, 8, 13, 21};
|
||||
received_handle->succeed(result);
|
||||
|
||||
// Wait for the result request to be received
|
||||
ASSERT_EQ(
|
||||
rclcpp::FutureReturnCode::SUCCESS,
|
||||
rclcpp::spin_until_future_complete(node, future));
|
||||
|
||||
auto response = future.get();
|
||||
EXPECT_EQ(action_msgs::msg::GoalStatus::STATUS_SUCCEEDED, response->status);
|
||||
EXPECT_EQ(result->sequence, response->result.sequence);
|
||||
|
||||
// Wait for goal expiration
|
||||
rclcpp::sleep_for(2 * result_timeout);
|
||||
|
||||
// Allow for expiration to take place
|
||||
rclcpp::spin_some(node);
|
||||
|
||||
// Send and wait for another result request
|
||||
future = result_client->async_send_request(request);
|
||||
ASSERT_EQ(
|
||||
rclcpp::FutureReturnCode::SUCCESS,
|
||||
rclcpp::spin_until_future_complete(node, future));
|
||||
|
||||
response = future.get();
|
||||
EXPECT_EQ(action_msgs::msg::GoalStatus::STATUS_UNKNOWN, response->status);
|
||||
}
|
||||
|
||||
TEST_F(TestServer, get_result_deferred)
|
||||
{
|
||||
auto node = std::make_shared<rclcpp::Node>("get_result", "/rclcpp_action/get_result");
|
||||
const GoalUUID uuid{{1, 2, 3, 4, 5, 6, 7, 80, 90, 10, 11, 12, 13, 14, 15, 160}};
|
||||
|
||||
auto handle_goal = [](
|
||||
const GoalUUID &, std::shared_ptr<const Fibonacci::Goal>)
|
||||
{
|
||||
return rclcpp_action::GoalResponse::ACCEPT_AND_EXECUTE;
|
||||
};
|
||||
|
||||
using GoalHandle = rclcpp_action::ServerGoalHandle<Fibonacci>;
|
||||
|
||||
auto handle_cancel = [](std::shared_ptr<GoalHandle>)
|
||||
{
|
||||
return rclcpp_action::CancelResponse::REJECT;
|
||||
@@ -763,6 +866,10 @@ TEST_F(TestServer, get_result)
|
||||
request->goal_id.uuid = uuid;
|
||||
auto future = result_client->async_send_request(request);
|
||||
|
||||
// Process request first
|
||||
rclcpp::sleep_for(std::chrono::milliseconds(10)); // Give a chance for the request to be served
|
||||
rclcpp::spin_some(node);
|
||||
|
||||
// Send a result
|
||||
auto result = std::make_shared<Fibonacci::Result>();
|
||||
result->sequence = {5, 8, 13, 21};
|
||||
|
||||
@@ -2,16 +2,13 @@
|
||||
Changelog for package rclcpp_components
|
||||
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
2.0.2 (2020-07-07)
|
||||
------------------
|
||||
|
||||
2.0.1 (2020-06-23)
|
||||
3.0.0 (2020-06-18)
|
||||
------------------
|
||||
|
||||
2.0.0 (2020-06-01)
|
||||
------------------
|
||||
* Added missing virtual destructors (`#1149 <https://github.com/ros2/rclcpp/issues/1149>`_)
|
||||
* Add Security Vulnerability Policy pointing to REP-2006 (`#1130 <https://github.com/ros2/rclcpp/issues/1130>`_)
|
||||
* Added missing virtual destructors. (`#1149 <https://github.com/ros2/rclcpp/issues/1149>`_)
|
||||
* Add Security Vulnerability Policy pointing to REP-2006. (`#1130 <https://github.com/ros2/rclcpp/issues/1130>`_)
|
||||
* Contributors: Chris Lalancette, Ivan Santiago Paunovic
|
||||
|
||||
1.1.0 (2020-05-26)
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
<?xml-model href="http://download.ros.org/schema/package_format2.xsd" schematypens="http://www.w3.org/2001/XMLSchema"?>
|
||||
<package format="2">
|
||||
<name>rclcpp_components</name>
|
||||
<version>2.0.2</version>
|
||||
<version>3.0.0</version>
|
||||
<description>Package containing tools for dynamically loadable components</description>
|
||||
<maintainer email="michael@openrobotics.org">Michael Carroll</maintainer>
|
||||
<license>Apache License 2.0</license>
|
||||
|
||||
@@ -3,12 +3,9 @@ Changelog for package rclcpp_lifecycle
|
||||
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
|
||||
2.0.2 (2020-07-07)
|
||||
3.0.0 (2020-06-18)
|
||||
------------------
|
||||
|
||||
2.0.1 (2020-06-23)
|
||||
------------------
|
||||
* Fixed doxygen warnings (`#1163 <https://github.com/ros2/rclcpp/issues/1163>`_) (`#1191 <https://github.com/ros2/rclcpp/issues/1191>`_)
|
||||
* Fix doxygen warnings (`#1163 <https://github.com/ros2/rclcpp/issues/1163>`_)
|
||||
* Contributors: Alejandro Hernández Cordero
|
||||
|
||||
2.0.0 (2020-06-01)
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
<?xml-model href="http://download.ros.org/schema/package_format2.xsd" schematypens="http://www.w3.org/2001/XMLSchema"?>
|
||||
<package format="2">
|
||||
<name>rclcpp_lifecycle</name>
|
||||
<version>2.0.2</version>
|
||||
<version>3.0.0</version>
|
||||
<description>Package containing a prototype for lifecycle implementation</description>
|
||||
<maintainer email="karsten@osrfoundation.org">Karsten Knese</maintainer>
|
||||
<license>Apache License 2.0</license>
|
||||
|
||||
Reference in New Issue
Block a user