diff --git a/rclcpp/include/rclcpp/create_client.hpp b/rclcpp/include/rclcpp/create_client.hpp new file mode 100644 index 0000000000..94f6b212fa --- /dev/null +++ b/rclcpp/include/rclcpp/create_client.hpp @@ -0,0 +1,56 @@ +// 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. + +#ifndef RCLCPP__CREATE_CLIENT_HPP_ +#define RCLCPP__CREATE_CLIENT_HPP_ + +#include +#include + +#include "rclcpp/node_interfaces/node_base_interface.hpp" +#include "rclcpp/node_interfaces/node_services_interface.hpp" +#include "rmw/rmw.h" + +namespace rclcpp +{ + +/// Create a service client with a given type. +/// \internal +template +typename rclcpp::Client::SharedPtr +create_client( + std::shared_ptr node_base, + std::shared_ptr node_graph, + std::shared_ptr node_services, + const std::string & service_name, + const rmw_qos_profile_t & qos_profile, + rclcpp::callback_group::CallbackGroup::SharedPtr group) +{ + rcl_client_options_t options = rcl_client_get_default_options(); + options.qos = qos_profile; + + auto cli = rclcpp::Client::make_shared( + node_base.get(), + node_graph, + service_name, + options); + + auto cli_base_ptr = std::dynamic_pointer_cast(cli); + node_services->add_client(cli_base_ptr, group); + return cli; +} + +} // namespace rclcpp + +#endif // RCLCPP__CREATE_CLIENT_HPP_ diff --git a/rclcpp/include/rclcpp/node_impl.hpp b/rclcpp/include/rclcpp/node_impl.hpp index 850ea0c90b..55afcbc3d2 100644 --- a/rclcpp/include/rclcpp/node_impl.hpp +++ b/rclcpp/include/rclcpp/node_impl.hpp @@ -36,6 +36,7 @@ #include "rcl_interfaces/msg/intra_process_message.hpp" #include "rclcpp/contexts/default_context.hpp" +#include "rclcpp/create_client.hpp" #include "rclcpp/create_publisher.hpp" #include "rclcpp/create_service.hpp" #include "rclcpp/create_subscription.hpp" @@ -211,21 +212,13 @@ Node::create_client( const rmw_qos_profile_t & qos_profile, rclcpp::callback_group::CallbackGroup::SharedPtr group) { - rcl_client_options_t options = rcl_client_get_default_options(); - options.qos = qos_profile; - - using rclcpp::Client; - using rclcpp::ClientBase; - - auto cli = Client::make_shared( - node_base_.get(), + return rclcpp::create_client( + node_base_, node_graph_, + node_services_, extend_name_with_sub_namespace(service_name, this->get_sub_namespace()), - options); - - auto cli_base_ptr = std::dynamic_pointer_cast(cli); - node_services_->add_client(cli_base_ptr, group); - return cli; + qos_profile, + group); } template diff --git a/rclcpp/test/test_client.cpp b/rclcpp/test/test_client.cpp index d7fbb8c7ec..8fd1b5657b 100644 --- a/rclcpp/test/test_client.cpp +++ b/rclcpp/test/test_client.cpp @@ -81,6 +81,29 @@ TEST_F(TestClient, construction_and_destruction) { } } +TEST_F(TestClient, construction_with_free_function) { + { + auto client = rclcpp::create_client( + node->get_node_base_interface(), + node->get_node_graph_interface(), + node->get_node_services_interface(), + "service", + rmw_qos_profile_services_default, + nullptr); + } + { + ASSERT_THROW({ + auto client = rclcpp::create_client( + node->get_node_base_interface(), + node->get_node_graph_interface(), + node->get_node_services_interface(), + "invalid_?service", + rmw_qos_profile_services_default, + nullptr); + }, rclcpp::exceptions::InvalidServiceNameError); + } +} + /* Testing client construction and destruction for subnodes. */