15 #ifndef RCLCPP__ANY_SERVICE_CALLBACK_HPP_
16 #define RCLCPP__ANY_SERVICE_CALLBACK_HPP_
22 #include <type_traits>
25 #include "rclcpp/function_traits.hpp"
26 #include "rclcpp/visibility_control.hpp"
27 #include "rmw/types.h"
28 #include "tracetools/tracetools.h"
29 #include "tracetools/utils.hpp"
36 template<
typename T,
typename =
void>
45 decltype(std::declval<T>() == nullptr)>>: std::true_type {};
48 decltype(std::declval<T>() == nullptr), decltype(std::declval<T &>() = nullptr)>>
54 template<
typename ServiceT>
57 template<
typename ServiceT>
62 : callback_(std::monostate{})
67 typename std::enable_if_t<!detail::can_be_nullptr<CallbackT>::value,
int> = 0>
69 set(CallbackT && callback)
78 callback_.template emplace<SharedPtrCallback>(callback);
82 SharedPtrWithRequestHeaderCallback
85 callback_.template emplace<SharedPtrWithRequestHeaderCallback>(callback);
89 SharedPtrDeferResponseCallback
92 callback_.template emplace<SharedPtrDeferResponseCallback>(callback);
96 SharedPtrDeferResponseCallbackWithServiceHandle
99 callback_.template emplace<SharedPtrDeferResponseCallbackWithServiceHandle>(callback);
103 callback_ = std::forward<CallbackT>(callback);
109 typename std::enable_if_t<detail::can_be_nullptr<CallbackT>::value,
int> = 0>
111 set(CallbackT && callback)
114 throw std::invalid_argument(
"AnyServiceCallback::set(): callback cannot be nullptr");
123 callback_.template emplace<SharedPtrCallback>(callback);
124 }
else if constexpr (
127 SharedPtrWithRequestHeaderCallback
130 callback_.template emplace<SharedPtrWithRequestHeaderCallback>(callback);
131 }
else if constexpr (
134 SharedPtrDeferResponseCallback
137 callback_.template emplace<SharedPtrDeferResponseCallback>(callback);
138 }
else if constexpr (
141 SharedPtrDeferResponseCallbackWithServiceHandle
144 callback_.template emplace<SharedPtrDeferResponseCallbackWithServiceHandle>(callback);
148 callback_ = std::forward<CallbackT>(callback);
153 std::shared_ptr<typename ServiceT::Response>
156 const std::shared_ptr<rmw_request_id_t> & request_header,
157 std::shared_ptr<typename ServiceT::Request> request)
159 TRACETOOLS_TRACEPOINT(callback_start,
static_cast<const void *
>(
this),
false);
160 if (std::holds_alternative<std::monostate>(callback_)) {
163 throw std::runtime_error{
"unexpected request without any callback set"};
165 if (std::holds_alternative<SharedPtrDeferResponseCallback>(callback_)) {
166 const auto & cb = std::get<SharedPtrDeferResponseCallback>(callback_);
167 cb(request_header, std::move(request));
170 if (std::holds_alternative<SharedPtrDeferResponseCallbackWithServiceHandle>(callback_)) {
171 const auto & cb = std::get<SharedPtrDeferResponseCallbackWithServiceHandle>(callback_);
172 cb(service_handle, request_header, std::move(request));
176 auto response = std::make_shared<typename ServiceT::Response>();
177 if (std::holds_alternative<SharedPtrCallback>(callback_)) {
178 (void)request_header;
179 const auto & cb = std::get<SharedPtrCallback>(callback_);
180 cb(std::move(request), response);
181 }
else if (std::holds_alternative<SharedPtrWithRequestHeaderCallback>(callback_)) {
182 const auto & cb = std::get<SharedPtrWithRequestHeaderCallback>(callback_);
183 cb(request_header, std::move(request), response);
185 TRACETOOLS_TRACEPOINT(callback_end,
static_cast<const void *
>(
this));
189 void register_callback_for_tracing()
191 #ifndef TRACETOOLS_DISABLED
193 [
this](
auto && arg) {
194 if (TRACETOOLS_TRACEPOINT_ENABLED(rclcpp_callback_register)) {
195 char * symbol = tracetools::get_symbol(arg);
196 TRACETOOLS_DO_TRACEPOINT(
197 rclcpp_callback_register,
198 static_cast<const void *
>(
this),
207 using SharedPtrCallback = std::function<
209 std::shared_ptr<typename ServiceT::Request>,
210 std::shared_ptr<typename ServiceT::Response>
212 using SharedPtrWithRequestHeaderCallback = std::function<
214 std::shared_ptr<rmw_request_id_t>,
215 std::shared_ptr<typename ServiceT::Request>,
216 std::shared_ptr<typename ServiceT::Response>
218 using SharedPtrDeferResponseCallback = std::function<
220 std::shared_ptr<rmw_request_id_t>,
221 std::shared_ptr<typename ServiceT::Request>
223 using SharedPtrDeferResponseCallbackWithServiceHandle = std::function<
226 std::shared_ptr<rmw_request_id_t>,
227 std::shared_ptr<typename ServiceT::Request>
233 SharedPtrWithRequestHeaderCallback,
234 SharedPtrDeferResponseCallback,
235 SharedPtrDeferResponseCallbackWithServiceHandle> callback_;
Versions of rosidl_typesupport_cpp::get_message_type_support_handle that handle adapted types.