From af77c78dd36d339a2bd388aa19ef45211abe4313 Mon Sep 17 00:00:00 2001 From: Barry Xu Date: Wed, 19 Feb 2025 13:46:46 +0800 Subject: [PATCH] Support action typesupport helper Signed-off-by: Barry Xu --- rclcpp/include/rclcpp/typesupport_helpers.hpp | 19 +++++++++ rclcpp/src/rclcpp/typesupport_helpers.cpp | 15 +++++++ .../test/rclcpp/test_typesupport_helpers.cpp | 40 +++++++++++++++++-- 3 files changed, 71 insertions(+), 3 deletions(-) diff --git a/rclcpp/include/rclcpp/typesupport_helpers.hpp b/rclcpp/include/rclcpp/typesupport_helpers.hpp index 7f75a8052b..1fc7715d7d 100644 --- a/rclcpp/include/rclcpp/typesupport_helpers.hpp +++ b/rclcpp/include/rclcpp/typesupport_helpers.hpp @@ -21,6 +21,7 @@ #include #include "rcpputils/shared_library.hpp" +#include "rosidl_runtime_cpp/action_type_support_decl.hpp" #include "rosidl_runtime_cpp/message_type_support_decl.hpp" #include "rosidl_runtime_cpp/service_type_support_decl.hpp" @@ -72,6 +73,24 @@ get_service_typesupport_handle( const std::string & typesupport_identifier, rcpputils::SharedLibrary & library); +/// Extract the action type support handle from the library. +/** + * The library needs to match the action type. The shared library must stay loaded for the lifetime + * of the result. + * + * \param[in] type The action type, e.g. "example_interfaces/action/Fibonacci" + * \param[in] typesupport_identifier Type support identifier, typically "rosidl_typesupport_cpp" + * \param[in] library The shared type support library + * \throws std::runtime_error if the symbol of type not found in the library. + * \return A action type support handle + */ +RCLCPP_PUBLIC +const rosidl_action_type_support_t * +get_action_typesupport_handle( + const std::string & type, + const std::string & typesupport_identifier, + rcpputils::SharedLibrary & library); + } // namespace rclcpp #endif // RCLCPP__TYPESUPPORT_HELPERS_HPP_ diff --git a/rclcpp/src/rclcpp/typesupport_helpers.cpp b/rclcpp/src/rclcpp/typesupport_helpers.cpp index 04dd8c4c9f..8f3c1a2817 100644 --- a/rclcpp/src/rclcpp/typesupport_helpers.cpp +++ b/rclcpp/src/rclcpp/typesupport_helpers.cpp @@ -177,4 +177,19 @@ const rosidl_service_type_support_t * get_service_typesupport_handle( )); } +const rosidl_action_type_support_t * get_action_typesupport_handle( + const std::string & type, + const std::string & typesupport_identifier, + rcpputils::SharedLibrary & library) +{ + static const std::string typesupport_name = "action"; + static const std::string symbol_part_name = "__get_action_type_support_handle__"; + static const std::string middle_module_additional = "action"; + + return static_cast(get_typesupport_handle_impl( + type, typesupport_identifier, typesupport_name, symbol_part_name, + middle_module_additional, library + )); +} + } // namespace rclcpp diff --git a/rclcpp/test/rclcpp/test_typesupport_helpers.cpp b/rclcpp/test/rclcpp/test_typesupport_helpers.cpp index 2117b89455..bbd45772f7 100644 --- a/rclcpp/test/rclcpp/test_typesupport_helpers.cpp +++ b/rclcpp/test/rclcpp/test_typesupport_helpers.cpp @@ -106,6 +106,36 @@ TEST(TypesupportHelpersTest, returns_service_type_info_for_valid_library) { } } +TEST(TypesupportHelpersTest, returns_action_type_info_for_valid_legacy_library) { + try { + auto library = rclcpp::get_typesupport_library( + "test_msgs/NestedMessage", "rosidl_typesupport_cpp"); + auto nestedmessage_typesupport = rclcpp::get_action_typesupport_handle( + "test_msgs/NestedMessage", "rosidl_typesupport_cpp", *library); + + EXPECT_THAT( + std::string(nestedmessage_typesupport->goal_service_type_support->typesupport_identifier), + ContainsRegex("rosidl_typesupport")); + } catch (const std::runtime_error & e) { + FAIL() << e.what(); + } +} + +TEST(TypesupportHelpersTest, returns_action_type_info_for_valid_library) { + try { + auto library = rclcpp::get_typesupport_library( + "test_msgs/action/NestedMessage", "rosidl_typesupport_cpp"); + auto nestedmessage_typesupport = rclcpp::get_action_typesupport_handle( + "test_msgs/action/NestedMessage", "rosidl_typesupport_cpp", *library); + + EXPECT_THAT( + std::string(nestedmessage_typesupport->goal_service_type_support->typesupport_identifier), + ContainsRegex("rosidl_typesupport")); + } catch (const std::runtime_error & e) { + FAIL() << e.what(); + } +} + TEST(TypesupportHelpersTest, test_throw_exception_with_invalid_type) { // message std::string invalid_type = "test_msgs/msg/InvalidType"; @@ -113,9 +143,6 @@ TEST(TypesupportHelpersTest, test_throw_exception_with_invalid_type) { EXPECT_THROW( rclcpp::get_message_typesupport_handle(invalid_type, "rosidl_typesupport_cpp", *library), std::runtime_error); - EXPECT_THROW( - rclcpp::get_service_typesupport_handle(invalid_type, "rosidl_typesupport_cpp", *library), - std::runtime_error); // service invalid_type = "test_msgs/srv/InvalidType"; @@ -123,4 +150,11 @@ TEST(TypesupportHelpersTest, test_throw_exception_with_invalid_type) { EXPECT_THROW( rclcpp::get_service_typesupport_handle(invalid_type, "rosidl_typesupport_cpp", *library), std::runtime_error); + + // action + invalid_type = "test_msgs/action/InvalidType"; + library = rclcpp::get_typesupport_library(invalid_type, "rosidl_typesupport_cpp"); + EXPECT_THROW( + rclcpp::get_action_typesupport_handle(invalid_type, "rosidl_typesupport_cpp", *library), + std::runtime_error); }