From b4e949a8dda2fd5ac7561f9e40c086bbe67dec45 Mon Sep 17 00:00:00 2001 From: Brennan Conroy Date: Wed, 30 Nov 2022 13:23:27 -0800 Subject: [PATCH] templates --- include/signalrclient/converters.h | 92 ++++++++++++++++++++++++++ include/signalrclient/hub_connection.h | 33 ++++++++- 2 files changed, 124 insertions(+), 1 deletion(-) create mode 100644 include/signalrclient/converters.h diff --git a/include/signalrclient/converters.h b/include/signalrclient/converters.h new file mode 100644 index 00000000..e825b992 --- /dev/null +++ b/include/signalrclient/converters.h @@ -0,0 +1,92 @@ +#pragma once + +#include "signalr_value.h" +#include + +namespace signalr +{ + template + class is_map + { + public: + static const bool value = false; + }; + + template + class is_map> + { + public: + static const bool value = true; + }; + + template + class is_vector + { + public: + static const bool value = false; + }; + + template + class is_vector> + { + public: + static const bool value = true; + }; + + template ::value, T>>::value, int> = 0> + T convert_value(const signalr::value& value) + { + static_assert(false, "type conversion not defined"); + throw std::runtime_error("failed"); + } + + template <> + inline int convert_value(const signalr::value& value) + { + if (value.is_double()) + { + return (int)value.as_double(); + } + throw std::runtime_error("not type"); + } + + template <> + inline std::string convert_value(const signalr::value& value) + { + if (value.is_string()) + { + return value.as_string(); + } + throw std::runtime_error("not type"); + } + + template + typename std::enable_if_t::value, T> convert_value(const signalr::value& value) + { + if (value.is_map()) + { + T map{}; + for (auto& v : value.as_map()) + { + map.insert(std::make_pair(v.first, convert_value(v.second))); + } + return map; + } + throw std::runtime_error("not type"); + } + + template + typename std::enable_if_t::value, T> convert_value(const signalr::value& value) + { + if (value.is_array()) + { + T vec{}; + for (auto& v : value.as_array()) + { + vec.push_back(convert_value(v)); + } + return vec; + } + throw std::runtime_error("not type"); + } +} \ No newline at end of file diff --git a/include/signalrclient/hub_connection.h b/include/signalrclient/hub_connection.h index c6a04ca2..db0014f5 100644 --- a/include/signalrclient/hub_connection.h +++ b/include/signalrclient/hub_connection.h @@ -12,6 +12,7 @@ #include "log_writer.h" #include "signalr_client_config.h" #include "signalr_value.h" +#include "converters.h" namespace signalr { @@ -21,6 +22,24 @@ namespace signalr class hub_connection_builder; class hub_protocol; + /*template + T convert_value(const signalr::value& value);*/ + + /*template ::value, T>>::value, int> = 0> + T convert_value(const signalr::value& value); + + template <> + int convert_value(const signalr::value& value); + + template <> + std::string convert_value(const signalr::value& value); + + template + typename std::enable_if_t::value, T> convert_value(const signalr::value& value); + + template + typename std::enable_if_t::value, T> convert_value(const signalr::value& value);*/ + class hub_connection { public: @@ -48,6 +67,18 @@ namespace signalr SIGNALRCLIENT_API void __cdecl on(const std::string& event_name, const method_invoked_handler& handler); + template + SIGNALRCLIENT_API void on(const std::string& event_name, std::function handler) + { + return on(event_name, [handler](const std::vector& args) + { + handler(convert_value(args[0])); + }); + } + + /*template + SIGNALRCLIENT_API void on(const std::string& event_name, std::function handler);*/ + SIGNALRCLIENT_API void invoke(const std::string& method_name, const std::vector& arguments = std::vector(), std::function callback = [](const signalr::value&, std::exception_ptr) {}) noexcept; SIGNALRCLIENT_API void send(const std::string& method_name, const std::vector& arguments = std::vector(), std::function callback = [](std::exception_ptr) {}) noexcept; @@ -63,4 +94,4 @@ namespace signalr std::shared_ptr m_pImpl; }; -} +} \ No newline at end of file