updates
This commit is contained in:
		| @@ -1,235 +1,235 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_COMM_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_COMM_HPP_ | ||||
|  | ||||
| #include "comm/curl/multi_request.hpp" | ||||
| #include "comm/i_http_comm.hpp" | ||||
| #include "utils/encryption.hpp" | ||||
| #include "utils/utils.hpp" | ||||
|  | ||||
| namespace repertory { | ||||
| class curl_comm final : public i_http_comm { | ||||
| public: | ||||
|   curl_comm() = delete; | ||||
|  | ||||
|   explicit curl_comm(host_config cfg); | ||||
|  | ||||
|   explicit curl_comm(s3_config cfg); | ||||
|  | ||||
| private: | ||||
|   using write_callback = size_t (*)(char *, size_t, size_t, void *); | ||||
|  | ||||
|   struct read_write_info final { | ||||
|     repertory::data_buffer data{}; | ||||
|     repertory::stop_type &stop_requested; | ||||
|   }; | ||||
|  | ||||
|   static const write_callback write_data; | ||||
|   static const write_callback write_headers; | ||||
|  | ||||
| private: | ||||
|   std::optional<host_config> host_config_; | ||||
|   std::optional<s3_config> s3_config_; | ||||
|  | ||||
| private: | ||||
|   bool use_s3_path_style_{false}; | ||||
|  | ||||
| public: | ||||
|   [[nodiscard]] static auto construct_url(CURL *curl, | ||||
|                                           const std::string &relative_path, | ||||
|                                           const host_config &cfg) | ||||
|       -> std::string; | ||||
|  | ||||
|   [[nodiscard]] static auto create_host_config(const s3_config &cfg, | ||||
|                                                bool use_s3_path_style) | ||||
|       -> host_config; | ||||
|  | ||||
|   [[nodiscard]] static auto url_encode(CURL *curl, const std::string &data, | ||||
|                                        bool allow_slash) -> std::string; | ||||
|  | ||||
|   template <typename request_type> | ||||
|   [[nodiscard]] static auto | ||||
|   make_encrypted_request(const host_config &cfg, const request_type &request, | ||||
|                          long &response_code, stop_type &stop_requested) | ||||
|       -> bool { | ||||
|     response_code = 0; | ||||
|  | ||||
|     if (not request.decryption_token.has_value() || | ||||
|         request.decryption_token.value().empty()) { | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     if (not request.range.has_value()) { | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     if (not request.total_size.has_value()) { | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     data_buffer data{}; | ||||
|     const auto key = | ||||
|         utils::encryption::generate_key(request.decryption_token.value()); | ||||
|     const auto result = utils::encryption::read_encrypted_range( | ||||
|         request.range.value(), key, | ||||
|         [&](std::vector<char> &ct, std::uint64_t start_offset, | ||||
|             std::uint64_t end_offset) -> api_error { | ||||
|           auto encrypted_request = request; | ||||
|           encrypted_request.decryption_token = std::nullopt; | ||||
|           encrypted_request.range = {{start_offset, end_offset}}; | ||||
|           encrypted_request.response_handler = [&ct](const auto &encrypted_data, | ||||
|                                                      long /*response_code*/) { | ||||
|             ct = encrypted_data; | ||||
|           }; | ||||
|           encrypted_request.total_size = std::nullopt; | ||||
|  | ||||
|           if (not make_request(cfg, encrypted_request, response_code, | ||||
|                                stop_requested)) { | ||||
|             return api_error::comm_error; | ||||
|           } | ||||
|  | ||||
|           if (response_code != 200) { | ||||
|             return api_error::comm_error; | ||||
|           } | ||||
|  | ||||
|           return api_error::success; | ||||
|         }, | ||||
|         request.total_size.value(), data); | ||||
|     if (result != api_error::success) { | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     if (request.response_handler.has_value()) { | ||||
|       request.response_handler.value()(data, response_code); | ||||
|     } | ||||
|  | ||||
|     return true; | ||||
|   } | ||||
|  | ||||
|   template <typename request_type> | ||||
|   [[nodiscard]] static auto | ||||
|   make_request(const host_config &cfg, const request_type &request, | ||||
|                long &response_code, stop_type &stop_requested) -> bool { | ||||
|     if (request.decryption_token.has_value() && | ||||
|         not request.decryption_token.value().empty()) { | ||||
|       return make_encrypted_request(cfg, request, response_code, | ||||
|                                     stop_requested); | ||||
|     } | ||||
|  | ||||
|     response_code = 0; | ||||
|  | ||||
|     auto *curl = utils::create_curl(); | ||||
|     if (not request.set_method(curl, stop_requested)) { | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     if (not cfg.agent_string.empty()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_USERAGENT, cfg.agent_string.c_str()); | ||||
|     } | ||||
|  | ||||
|     if (request.allow_timeout && cfg.timeout_ms) { | ||||
|       curl_easy_setopt(curl, CURLOPT_TIMEOUT_MS, cfg.timeout_ms); | ||||
|     } | ||||
|  | ||||
|     std::string range_list{}; | ||||
|     if (request.range.has_value()) { | ||||
|       range_list = std::to_string(request.range.value().begin) + '-' + | ||||
|                    std::to_string(request.range.value().end); | ||||
|       curl_easy_setopt(curl, CURLOPT_RANGE, range_list.c_str()); | ||||
|     } | ||||
|  | ||||
|     if (request.response_headers.has_value()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_HEADERDATA, | ||||
|                        &request.response_headers.value()); | ||||
|       curl_easy_setopt(curl, CURLOPT_HEADERFUNCTION, write_headers); | ||||
|     } | ||||
|  | ||||
|     read_write_info write_info{{}, stop_requested}; | ||||
|     if (request.response_handler.has_value()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_WRITEDATA, &write_info); | ||||
|       curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, write_data); | ||||
|     } | ||||
|  | ||||
|     std::string parameters{}; | ||||
|     for (const auto ¶m : request.query) { | ||||
|       parameters += (parameters.empty() ? '?' : '&') + param.first + '=' + | ||||
|                     url_encode(curl, param.second, false); | ||||
|     } | ||||
|  | ||||
|     if (not cfg.api_password.empty()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_USERNAME, cfg.api_user.c_str()); | ||||
|       curl_easy_setopt(curl, CURLOPT_PASSWORD, cfg.api_password.c_str()); | ||||
|     } else if (not cfg.api_user.empty()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_USERNAME, cfg.api_user.c_str()); | ||||
|     } | ||||
|  | ||||
|     if (request.aws_service.has_value()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_AWS_SIGV4, | ||||
|                        request.aws_service.value().c_str()); | ||||
|     } | ||||
|  | ||||
|     auto url = construct_url(curl, request.get_path(), cfg) + parameters; | ||||
|     curl_easy_setopt(curl, CURLOPT_URL, url.c_str()); | ||||
|  | ||||
|     multi_request curl_request(curl, stop_requested); | ||||
|  | ||||
|     CURLcode curl_code{}; | ||||
|     curl_request.get_result(curl_code, response_code); | ||||
|     if (curl_code != CURLE_OK) { | ||||
|       std::cout << curl_easy_strerror(curl_code) << std::endl; | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     if (request.response_handler.has_value()) { | ||||
|       request.response_handler.value()(write_info.data, response_code); | ||||
|     } | ||||
|  | ||||
|     return true; | ||||
|   } | ||||
|  | ||||
| public: | ||||
|   void enable_s3_path_style(bool enable) override; | ||||
|  | ||||
|   [[nodiscard]] auto make_request(const curl::requests::http_delete &del, | ||||
|                                   long &response_code, | ||||
|                                   stop_type &stop_requested) const | ||||
|       -> bool override; | ||||
|  | ||||
|   [[nodiscard]] auto make_request(const curl::requests::http_get &get, | ||||
|                                   long &response_code, | ||||
|                                   stop_type &stop_requested) const | ||||
|       -> bool override; | ||||
|  | ||||
|   [[nodiscard]] auto make_request(const curl::requests::http_head &head, | ||||
|                                   long &response_code, | ||||
|                                   stop_type &stop_requested) const | ||||
|       -> bool override; | ||||
|  | ||||
|   [[nodiscard]] auto make_request(const curl::requests::http_put_file &put_file, | ||||
|                                   long &response_code, | ||||
|                                   stop_type &stop_requested) const | ||||
|       -> bool override; | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_COMM_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_COMM_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_COMM_HPP_ | ||||
|  | ||||
| #include "comm/curl/multi_request.hpp" | ||||
| #include "comm/i_http_comm.hpp" | ||||
| #include "utils/encryption.hpp" | ||||
| #include "utils/utils.hpp" | ||||
|  | ||||
| namespace repertory { | ||||
| class curl_comm final : public i_http_comm { | ||||
| public: | ||||
|   curl_comm() = delete; | ||||
|  | ||||
|   explicit curl_comm(host_config cfg); | ||||
|  | ||||
|   explicit curl_comm(s3_config cfg); | ||||
|  | ||||
| private: | ||||
|   using write_callback = size_t (*)(char *, size_t, size_t, void *); | ||||
|  | ||||
|   struct read_write_info final { | ||||
|     repertory::data_buffer data{}; | ||||
|     repertory::stop_type &stop_requested; | ||||
|   }; | ||||
|  | ||||
|   static const write_callback write_data; | ||||
|   static const write_callback write_headers; | ||||
|  | ||||
| private: | ||||
|   std::optional<host_config> host_config_; | ||||
|   std::optional<s3_config> s3_config_; | ||||
|  | ||||
| private: | ||||
|   bool use_s3_path_style_{false}; | ||||
|  | ||||
| public: | ||||
|   [[nodiscard]] static auto construct_url(CURL *curl, | ||||
|                                           const std::string &relative_path, | ||||
|                                           const host_config &cfg) | ||||
|       -> std::string; | ||||
|  | ||||
|   [[nodiscard]] static auto create_host_config(const s3_config &cfg, | ||||
|                                                bool use_s3_path_style) | ||||
|       -> host_config; | ||||
|  | ||||
|   [[nodiscard]] static auto url_encode(CURL *curl, const std::string &data, | ||||
|                                        bool allow_slash) -> std::string; | ||||
|  | ||||
|   template <typename request_type> | ||||
|   [[nodiscard]] static auto | ||||
|   make_encrypted_request(const host_config &cfg, const request_type &request, | ||||
|                          long &response_code, stop_type &stop_requested) | ||||
|       -> bool { | ||||
|     response_code = 0; | ||||
|  | ||||
|     if (not request.decryption_token.has_value() || | ||||
|         request.decryption_token.value().empty()) { | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     if (not request.range.has_value()) { | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     if (not request.total_size.has_value()) { | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     data_buffer data{}; | ||||
|     const auto key = | ||||
|         utils::encryption::generate_key(request.decryption_token.value()); | ||||
|     const auto result = utils::encryption::read_encrypted_range( | ||||
|         request.range.value(), key, | ||||
|         [&](std::vector<char> &ct, std::uint64_t start_offset, | ||||
|             std::uint64_t end_offset) -> api_error { | ||||
|           auto encrypted_request = request; | ||||
|           encrypted_request.decryption_token = std::nullopt; | ||||
|           encrypted_request.range = {{start_offset, end_offset}}; | ||||
|           encrypted_request.response_handler = [&ct](const auto &encrypted_data, | ||||
|                                                      long /*response_code*/) { | ||||
|             ct = encrypted_data; | ||||
|           }; | ||||
|           encrypted_request.total_size = std::nullopt; | ||||
|  | ||||
|           if (not make_request(cfg, encrypted_request, response_code, | ||||
|                                stop_requested)) { | ||||
|             return api_error::comm_error; | ||||
|           } | ||||
|  | ||||
|           if (response_code != 200) { | ||||
|             return api_error::comm_error; | ||||
|           } | ||||
|  | ||||
|           return api_error::success; | ||||
|         }, | ||||
|         request.total_size.value(), data); | ||||
|     if (result != api_error::success) { | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     if (request.response_handler.has_value()) { | ||||
|       request.response_handler.value()(data, response_code); | ||||
|     } | ||||
|  | ||||
|     return true; | ||||
|   } | ||||
|  | ||||
|   template <typename request_type> | ||||
|   [[nodiscard]] static auto | ||||
|   make_request(const host_config &cfg, const request_type &request, | ||||
|                long &response_code, stop_type &stop_requested) -> bool { | ||||
|     if (request.decryption_token.has_value() && | ||||
|         not request.decryption_token.value().empty()) { | ||||
|       return make_encrypted_request(cfg, request, response_code, | ||||
|                                     stop_requested); | ||||
|     } | ||||
|  | ||||
|     response_code = 0; | ||||
|  | ||||
|     auto *curl = utils::create_curl(); | ||||
|     if (not request.set_method(curl, stop_requested)) { | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     if (not cfg.agent_string.empty()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_USERAGENT, cfg.agent_string.c_str()); | ||||
|     } | ||||
|  | ||||
|     if (request.allow_timeout && cfg.timeout_ms) { | ||||
|       curl_easy_setopt(curl, CURLOPT_TIMEOUT_MS, cfg.timeout_ms); | ||||
|     } | ||||
|  | ||||
|     std::string range_list{}; | ||||
|     if (request.range.has_value()) { | ||||
|       range_list = std::to_string(request.range.value().begin) + '-' + | ||||
|                    std::to_string(request.range.value().end); | ||||
|       curl_easy_setopt(curl, CURLOPT_RANGE, range_list.c_str()); | ||||
|     } | ||||
|  | ||||
|     if (request.response_headers.has_value()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_HEADERDATA, | ||||
|                        &request.response_headers.value()); | ||||
|       curl_easy_setopt(curl, CURLOPT_HEADERFUNCTION, write_headers); | ||||
|     } | ||||
|  | ||||
|     read_write_info write_info{{}, stop_requested}; | ||||
|     if (request.response_handler.has_value()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_WRITEDATA, &write_info); | ||||
|       curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, write_data); | ||||
|     } | ||||
|  | ||||
|     std::string parameters{}; | ||||
|     for (const auto ¶m : request.query) { | ||||
|       parameters += (parameters.empty() ? '?' : '&') + param.first + '=' + | ||||
|                     url_encode(curl, param.second, false); | ||||
|     } | ||||
|  | ||||
|     if (not cfg.api_password.empty()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_USERNAME, cfg.api_user.c_str()); | ||||
|       curl_easy_setopt(curl, CURLOPT_PASSWORD, cfg.api_password.c_str()); | ||||
|     } else if (not cfg.api_user.empty()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_USERNAME, cfg.api_user.c_str()); | ||||
|     } | ||||
|  | ||||
|     if (request.aws_service.has_value()) { | ||||
|       curl_easy_setopt(curl, CURLOPT_AWS_SIGV4, | ||||
|                        request.aws_service.value().c_str()); | ||||
|     } | ||||
|  | ||||
|     auto url = construct_url(curl, request.get_path(), cfg) + parameters; | ||||
|     curl_easy_setopt(curl, CURLOPT_URL, url.c_str()); | ||||
|  | ||||
|     multi_request curl_request(curl, stop_requested); | ||||
|  | ||||
|     CURLcode curl_code{}; | ||||
|     curl_request.get_result(curl_code, response_code); | ||||
|     if (curl_code != CURLE_OK) { | ||||
|       std::cout << curl_easy_strerror(curl_code) << std::endl; | ||||
|       return false; | ||||
|     } | ||||
|  | ||||
|     if (request.response_handler.has_value()) { | ||||
|       request.response_handler.value()(write_info.data, response_code); | ||||
|     } | ||||
|  | ||||
|     return true; | ||||
|   } | ||||
|  | ||||
| public: | ||||
|   void enable_s3_path_style(bool enable) override; | ||||
|  | ||||
|   [[nodiscard]] auto make_request(const curl::requests::http_delete &del, | ||||
|                                   long &response_code, | ||||
|                                   stop_type &stop_requested) const | ||||
|       -> bool override; | ||||
|  | ||||
|   [[nodiscard]] auto make_request(const curl::requests::http_get &get, | ||||
|                                   long &response_code, | ||||
|                                   stop_type &stop_requested) const | ||||
|       -> bool override; | ||||
|  | ||||
|   [[nodiscard]] auto make_request(const curl::requests::http_head &head, | ||||
|                                   long &response_code, | ||||
|                                   stop_type &stop_requested) const | ||||
|       -> bool override; | ||||
|  | ||||
|   [[nodiscard]] auto make_request(const curl::requests::http_put_file &put_file, | ||||
|                                   long &response_code, | ||||
|                                   stop_type &stop_requested) const | ||||
|       -> bool override; | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_COMM_HPP_ | ||||
|   | ||||
| @@ -1,44 +1,44 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_MULTI_REQUEST_HPP_ | ||||
| #define INCLUDE_COMM_CURL_MULTI_REQUEST_HPP_ | ||||
|  | ||||
| #include "types/repertory.hpp" | ||||
|  | ||||
| namespace repertory { | ||||
| class multi_request final { | ||||
| public: | ||||
|   multi_request(CURL *curl_handle, stop_type &stop_requested); | ||||
|  | ||||
|   ~multi_request(); | ||||
|  | ||||
| private: | ||||
|   CURL *curl_handle_; | ||||
|   stop_type &stop_requested_; | ||||
|   CURLM *multi_handle_; | ||||
|  | ||||
| public: | ||||
|   void get_result(CURLcode &curl_code, long &http_code); | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_MULTI_REQUEST_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_MULTI_REQUEST_HPP_ | ||||
| #define INCLUDE_COMM_CURL_MULTI_REQUEST_HPP_ | ||||
|  | ||||
| #include "types/repertory.hpp" | ||||
|  | ||||
| namespace repertory { | ||||
| class multi_request final { | ||||
| public: | ||||
|   multi_request(CURL *curl_handle, stop_type &stop_requested); | ||||
|  | ||||
|   ~multi_request(); | ||||
|  | ||||
| private: | ||||
|   CURL *curl_handle_; | ||||
|   stop_type &stop_requested_; | ||||
|   CURLM *multi_handle_; | ||||
|  | ||||
| public: | ||||
|   void get_result(CURLcode &curl_code, long &http_code); | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_MULTI_REQUEST_HPP_ | ||||
|   | ||||
| @@ -1,40 +1,40 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_DELETE_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_DELETE_HPP_ | ||||
|  | ||||
| #include "comm/curl/requests/http_request_base.hpp" | ||||
|  | ||||
| namespace repertory::curl::requests { | ||||
| struct http_delete final : http_request_base { | ||||
|   ~http_delete() override = default; | ||||
|  | ||||
|   [[nodiscard]] auto set_method(CURL *curl, | ||||
|                                 stop_type & /* stop_requested */) const | ||||
|       -> bool override { | ||||
|     curl_easy_setopt(curl, CURLOPT_CUSTOMREQUEST, "DELETE"); | ||||
|     return true; | ||||
|   } | ||||
| }; | ||||
| } // namespace repertory::curl::requests | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_DELETE_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_DELETE_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_DELETE_HPP_ | ||||
|  | ||||
| #include "comm/curl/requests/http_request_base.hpp" | ||||
|  | ||||
| namespace repertory::curl::requests { | ||||
| struct http_delete final : http_request_base { | ||||
|   ~http_delete() override = default; | ||||
|  | ||||
|   [[nodiscard]] auto set_method(CURL *curl, | ||||
|                                 stop_type & /* stop_requested */) const | ||||
|       -> bool override { | ||||
|     curl_easy_setopt(curl, CURLOPT_CUSTOMREQUEST, "DELETE"); | ||||
|     return true; | ||||
|   } | ||||
| }; | ||||
| } // namespace repertory::curl::requests | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_DELETE_HPP_ | ||||
|   | ||||
| @@ -1,45 +1,45 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_GET_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_GET_HPP_ | ||||
|  | ||||
| #include "comm/curl/requests/http_request_base.hpp" | ||||
|  | ||||
| namespace repertory::curl::requests { | ||||
| struct http_get final : http_request_base { | ||||
|   http_get() = default; | ||||
|   http_get(const http_get &) = default; | ||||
|   http_get(http_get &&) = default; | ||||
|   auto operator=(const http_get &) -> http_get & = default; | ||||
|   auto operator=(http_get &&) -> http_get & = default; | ||||
|   ~http_get() override = default; | ||||
|  | ||||
|   [[nodiscard]] auto set_method(CURL *curl, | ||||
|                                 stop_type & /*stop_requested*/) const | ||||
|       -> bool override { | ||||
|     curl_easy_setopt(curl, CURLOPT_HTTPGET, 1L); | ||||
|     return true; | ||||
|   } | ||||
| }; | ||||
| } // namespace repertory::curl::requests | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_GET_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_GET_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_GET_HPP_ | ||||
|  | ||||
| #include "comm/curl/requests/http_request_base.hpp" | ||||
|  | ||||
| namespace repertory::curl::requests { | ||||
| struct http_get final : http_request_base { | ||||
|   http_get() = default; | ||||
|   http_get(const http_get &) = default; | ||||
|   http_get(http_get &&) = default; | ||||
|   auto operator=(const http_get &) -> http_get & = default; | ||||
|   auto operator=(http_get &&) -> http_get & = default; | ||||
|   ~http_get() override = default; | ||||
|  | ||||
|   [[nodiscard]] auto set_method(CURL *curl, | ||||
|                                 stop_type & /*stop_requested*/) const | ||||
|       -> bool override { | ||||
|     curl_easy_setopt(curl, CURLOPT_HTTPGET, 1L); | ||||
|     return true; | ||||
|   } | ||||
| }; | ||||
| } // namespace repertory::curl::requests | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_GET_HPP_ | ||||
|   | ||||
| @@ -1,41 +1,41 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_HEAD_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_HEAD_HPP_ | ||||
|  | ||||
| #include "comm/curl/requests/http_request_base.hpp" | ||||
|  | ||||
| namespace repertory::curl::requests { | ||||
| struct http_head final : http_request_base { | ||||
|   ~http_head() override = default; | ||||
|  | ||||
|   [[nodiscard]] auto set_method(CURL *curl, | ||||
|                                 stop_type & /* stop_requested */) const | ||||
|       -> bool override { | ||||
|     curl_easy_setopt(curl, CURLOPT_CUSTOMREQUEST, "HEAD"); | ||||
|     curl_easy_setopt(curl, CURLOPT_NOBODY, 1L); | ||||
|     return true; | ||||
|   } | ||||
| }; | ||||
| } // namespace repertory::curl::requests | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_HEAD_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_HEAD_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_HEAD_HPP_ | ||||
|  | ||||
| #include "comm/curl/requests/http_request_base.hpp" | ||||
|  | ||||
| namespace repertory::curl::requests { | ||||
| struct http_head final : http_request_base { | ||||
|   ~http_head() override = default; | ||||
|  | ||||
|   [[nodiscard]] auto set_method(CURL *curl, | ||||
|                                 stop_type & /* stop_requested */) const | ||||
|       -> bool override { | ||||
|     curl_easy_setopt(curl, CURLOPT_CUSTOMREQUEST, "HEAD"); | ||||
|     curl_easy_setopt(curl, CURLOPT_NOBODY, 1L); | ||||
|     return true; | ||||
|   } | ||||
| }; | ||||
| } // namespace repertory::curl::requests | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_HEAD_HPP_ | ||||
|   | ||||
| @@ -1,50 +1,50 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_PUT_FILE_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_PUT_FILE_HPP_ | ||||
|  | ||||
| #include "comm/curl/requests/http_request_base.hpp" | ||||
| #include "utils/encrypting_reader.hpp" | ||||
|  | ||||
| namespace repertory::curl::requests { | ||||
| struct http_put_file final : http_request_base { | ||||
|   http_put_file() = default; | ||||
|   http_put_file(const http_put_file &) = default; | ||||
|   http_put_file(http_put_file &&) = default; | ||||
|  | ||||
|   auto operator=(const http_put_file &) -> http_put_file & = default; | ||||
|   auto operator=(http_put_file &&) -> http_put_file & = default; | ||||
|  | ||||
|   ~http_put_file() override = default; | ||||
|  | ||||
|   std::shared_ptr<utils::encryption::encrypting_reader> reader; | ||||
|   std::string source_path; | ||||
|  | ||||
|   [[nodiscard]] auto set_method(CURL *curl, stop_type &stop_requested) const | ||||
|       -> bool override; | ||||
|  | ||||
| private: | ||||
|   mutable std::shared_ptr<read_file_info> read_info{}; | ||||
| }; | ||||
| } // namespace repertory::curl::requests | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_PUT_FILE_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_PUT_FILE_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_PUT_FILE_HPP_ | ||||
|  | ||||
| #include "comm/curl/requests/http_request_base.hpp" | ||||
| #include "utils/encrypting_reader.hpp" | ||||
|  | ||||
| namespace repertory::curl::requests { | ||||
| struct http_put_file final : http_request_base { | ||||
|   http_put_file() = default; | ||||
|   http_put_file(const http_put_file &) = default; | ||||
|   http_put_file(http_put_file &&) = default; | ||||
|  | ||||
|   auto operator=(const http_put_file &) -> http_put_file & = default; | ||||
|   auto operator=(http_put_file &&) -> http_put_file & = default; | ||||
|  | ||||
|   ~http_put_file() override = default; | ||||
|  | ||||
|   std::shared_ptr<utils::encryption::encrypting_reader> reader; | ||||
|   std::string source_path; | ||||
|  | ||||
|   [[nodiscard]] auto set_method(CURL *curl, stop_type &stop_requested) const | ||||
|       -> bool override; | ||||
|  | ||||
| private: | ||||
|   mutable std::shared_ptr<read_file_info> read_info{}; | ||||
| }; | ||||
| } // namespace repertory::curl::requests | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_PUT_FILE_HPP_ | ||||
|   | ||||
| @@ -1,82 +1,82 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_REQUEST_BASE_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_REQUEST_BASE_HPP_ | ||||
|  | ||||
| #include "types/repertory.hpp" | ||||
| #include "utils/native_file.hpp" | ||||
|  | ||||
| namespace repertory::curl::requests { | ||||
| using read_callback = size_t (*)(char *, size_t, size_t, void *); | ||||
|  | ||||
| using response_callback = | ||||
|     std::function<void(const data_buffer &data, long response_code)>; | ||||
|  | ||||
| struct read_file_info final { | ||||
|   stop_type &stop_requested; | ||||
|   native_file::native_file_ptr nf{}; | ||||
|   std::uint64_t offset{}; | ||||
| }; | ||||
|  | ||||
| inline const auto read_file_data = static_cast<read_callback>( | ||||
|     [](char *buffer, size_t size, size_t nitems, void *instream) -> size_t { | ||||
|       auto *read_info = reinterpret_cast<read_file_info *>(instream); | ||||
|       std::size_t bytes_read{}; | ||||
|       auto ret = read_info->nf->read_bytes(buffer, size * nitems, | ||||
|                                            read_info->offset, bytes_read); | ||||
|       if (ret) { | ||||
|         read_info->offset += bytes_read; | ||||
|       } | ||||
|       return ret && not read_info->stop_requested ? bytes_read | ||||
|                                                   : CURL_READFUNC_ABORT; | ||||
|     }); | ||||
|  | ||||
| struct http_request_base { | ||||
|   http_request_base() = default; | ||||
|   http_request_base(const http_request_base &) = default; | ||||
|   http_request_base(http_request_base &&) = default; | ||||
|  | ||||
|   auto operator=(const http_request_base &) -> http_request_base & = default; | ||||
|   auto operator=(http_request_base &&) -> http_request_base & = default; | ||||
|  | ||||
|   virtual ~http_request_base() = default; | ||||
|  | ||||
|   bool allow_timeout{}; | ||||
|   std::optional<std::string> aws_service; | ||||
|   std::optional<std::string> decryption_token{}; | ||||
|   http_headers headers{}; | ||||
|   std::string path{}; | ||||
|   query_parameters query{}; | ||||
|   std::optional<http_range> range{}; | ||||
|   std::optional<response_callback> response_handler; | ||||
|   std::optional<http_headers> response_headers; | ||||
|   std::optional<std::uint64_t> total_size{}; | ||||
|  | ||||
|   [[nodiscard]] virtual auto get_path() const -> std::string { return path; } | ||||
|  | ||||
|   [[nodiscard]] virtual auto set_method(CURL *curl, | ||||
|                                         stop_type &stop_requested) const | ||||
|       -> bool = 0; | ||||
| }; | ||||
| } // namespace repertory::curl::requests | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_REQUEST_BASE_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_REQUEST_BASE_HPP_ | ||||
| #define INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_REQUEST_BASE_HPP_ | ||||
|  | ||||
| #include "types/repertory.hpp" | ||||
| #include "utils/native_file.hpp" | ||||
|  | ||||
| namespace repertory::curl::requests { | ||||
| using read_callback = size_t (*)(char *, size_t, size_t, void *); | ||||
|  | ||||
| using response_callback = | ||||
|     std::function<void(const data_buffer &data, long response_code)>; | ||||
|  | ||||
| struct read_file_info final { | ||||
|   stop_type &stop_requested; | ||||
|   native_file::native_file_ptr nf{}; | ||||
|   std::uint64_t offset{}; | ||||
| }; | ||||
|  | ||||
| inline const auto read_file_data = static_cast<read_callback>( | ||||
|     [](char *buffer, size_t size, size_t nitems, void *instream) -> size_t { | ||||
|       auto *read_info = reinterpret_cast<read_file_info *>(instream); | ||||
|       std::size_t bytes_read{}; | ||||
|       auto ret = read_info->nf->read_bytes(buffer, size * nitems, | ||||
|                                            read_info->offset, bytes_read); | ||||
|       if (ret) { | ||||
|         read_info->offset += bytes_read; | ||||
|       } | ||||
|       return ret && not read_info->stop_requested ? bytes_read | ||||
|                                                   : CURL_READFUNC_ABORT; | ||||
|     }); | ||||
|  | ||||
| struct http_request_base { | ||||
|   http_request_base() = default; | ||||
|   http_request_base(const http_request_base &) = default; | ||||
|   http_request_base(http_request_base &&) = default; | ||||
|  | ||||
|   auto operator=(const http_request_base &) -> http_request_base & = default; | ||||
|   auto operator=(http_request_base &&) -> http_request_base & = default; | ||||
|  | ||||
|   virtual ~http_request_base() = default; | ||||
|  | ||||
|   bool allow_timeout{}; | ||||
|   std::optional<std::string> aws_service; | ||||
|   std::optional<std::string> decryption_token{}; | ||||
|   http_headers headers{}; | ||||
|   std::string path{}; | ||||
|   query_parameters query{}; | ||||
|   std::optional<http_range> range{}; | ||||
|   std::optional<response_callback> response_handler; | ||||
|   std::optional<http_headers> response_headers; | ||||
|   std::optional<std::uint64_t> total_size{}; | ||||
|  | ||||
|   [[nodiscard]] virtual auto get_path() const -> std::string { return path; } | ||||
|  | ||||
|   [[nodiscard]] virtual auto set_method(CURL *curl, | ||||
|                                         stop_type &stop_requested) const | ||||
|       -> bool = 0; | ||||
| }; | ||||
| } // namespace repertory::curl::requests | ||||
|  | ||||
| #endif // INCLUDE_COMM_CURL_CURL_REQUESTS_HTTP_REQUEST_BASE_HPP_ | ||||
|   | ||||
| @@ -1,59 +1,59 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_I_HTTP_COMM_HPP_ | ||||
| #define INCLUDE_COMM_I_HTTP_COMM_HPP_ | ||||
|  | ||||
| #include "comm/curl/requests/http_delete.hpp" | ||||
| #include "comm/curl/requests/http_get.hpp" | ||||
| #include "comm/curl/requests/http_head.hpp" | ||||
| #include "comm/curl/requests/http_put_file.hpp" | ||||
| #include "types/repertory.hpp" | ||||
|  | ||||
| namespace repertory { | ||||
| struct i_http_comm { | ||||
|   INTERFACE_SETUP(i_http_comm); | ||||
|  | ||||
| public: | ||||
|   virtual void enable_s3_path_style(bool enable) = 0; | ||||
|  | ||||
|   [[nodiscard]] virtual auto | ||||
|   make_request(const curl::requests::http_delete &del, long &response_code, | ||||
|                stop_type &stop_requested) const -> bool = 0; | ||||
|  | ||||
|   [[nodiscard]] virtual auto make_request(const curl::requests::http_get &get, | ||||
|                                           long &response_code, | ||||
|                                           stop_type &stop_requested) const | ||||
|       -> bool = 0; | ||||
|  | ||||
|   [[nodiscard]] virtual auto make_request(const curl::requests::http_head &head, | ||||
|                                           long &response_code, | ||||
|                                           stop_type &stop_requested) const | ||||
|       -> bool = 0; | ||||
|  | ||||
|   [[nodiscard]] virtual auto | ||||
|   make_request(const curl::requests::http_put_file &put_file, | ||||
|                long &response_code, stop_type &stop_requested) const | ||||
|       -> bool = 0; | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_I_HTTP_COMM_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_I_HTTP_COMM_HPP_ | ||||
| #define INCLUDE_COMM_I_HTTP_COMM_HPP_ | ||||
|  | ||||
| #include "comm/curl/requests/http_delete.hpp" | ||||
| #include "comm/curl/requests/http_get.hpp" | ||||
| #include "comm/curl/requests/http_head.hpp" | ||||
| #include "comm/curl/requests/http_put_file.hpp" | ||||
| #include "types/repertory.hpp" | ||||
|  | ||||
| namespace repertory { | ||||
| struct i_http_comm { | ||||
|   INTERFACE_SETUP(i_http_comm); | ||||
|  | ||||
| public: | ||||
|   virtual void enable_s3_path_style(bool enable) = 0; | ||||
|  | ||||
|   [[nodiscard]] virtual auto | ||||
|   make_request(const curl::requests::http_delete &del, long &response_code, | ||||
|                stop_type &stop_requested) const -> bool = 0; | ||||
|  | ||||
|   [[nodiscard]] virtual auto make_request(const curl::requests::http_get &get, | ||||
|                                           long &response_code, | ||||
|                                           stop_type &stop_requested) const | ||||
|       -> bool = 0; | ||||
|  | ||||
|   [[nodiscard]] virtual auto make_request(const curl::requests::http_head &head, | ||||
|                                           long &response_code, | ||||
|                                           stop_type &stop_requested) const | ||||
|       -> bool = 0; | ||||
|  | ||||
|   [[nodiscard]] virtual auto | ||||
|   make_request(const curl::requests::http_put_file &put_file, | ||||
|                long &response_code, stop_type &stop_requested) const | ||||
|       -> bool = 0; | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_I_HTTP_COMM_HPP_ | ||||
|   | ||||
| @@ -1,110 +1,110 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_PACKET_CLIENT_POOL_HPP_ | ||||
| #define INCLUDE_COMM_PACKET_CLIENT_POOL_HPP_ | ||||
|  | ||||
| #include "comm/packet/packet.hpp" | ||||
| #include "types/repertory.hpp" | ||||
|  | ||||
| namespace repertory { | ||||
| class client_pool final { | ||||
| public: | ||||
|   using worker_callback = std::function<packet::error_type()>; | ||||
|   using worker_complete_callback = | ||||
|       std::function<void(const packet::error_type &)>; | ||||
|  | ||||
| private: | ||||
|   class pool final { | ||||
|   private: | ||||
|     struct work_item final { | ||||
|       work_item(worker_callback worker, | ||||
|                 worker_complete_callback worker_complete) | ||||
|           : work(std::move(worker)), | ||||
|             work_complete(std::move(worker_complete)) {} | ||||
|  | ||||
|       worker_callback work; | ||||
|       worker_complete_callback work_complete; | ||||
|     }; | ||||
|  | ||||
|     struct work_queue final { | ||||
|       std::mutex mutex; | ||||
|       std::condition_variable notify; | ||||
|       std::deque<std::shared_ptr<work_item>> queue; | ||||
|     }; | ||||
|  | ||||
|   public: | ||||
|     explicit pool(std::uint8_t pool_size); | ||||
|  | ||||
|     ~pool() { shutdown(); } | ||||
|  | ||||
|   public: | ||||
|     pool(const pool &) = delete; | ||||
|     pool(pool &&) = delete; | ||||
|     auto operator=(const pool &) -> pool & = delete; | ||||
|     auto operator=(pool &&) -> pool & = delete; | ||||
|  | ||||
|   private: | ||||
|     std::vector<std::unique_ptr<work_queue>> pool_queues_; | ||||
|     std::vector<std::thread> pool_threads_; | ||||
|     bool shutdown_{false}; | ||||
|     std::atomic<std::uint8_t> thread_index_{}; | ||||
|  | ||||
|   public: | ||||
|     void execute(std::uint64_t thread_id, const worker_callback &worker, | ||||
|                  const worker_complete_callback &worker_complete); | ||||
|  | ||||
|     void shutdown(); | ||||
|   }; | ||||
|  | ||||
| public: | ||||
|   explicit client_pool(std::uint8_t pool_size = min_pool_size) | ||||
|       : pool_size_(pool_size == 0U ? min_pool_size : pool_size) {} | ||||
|  | ||||
|   ~client_pool() { shutdown(); } | ||||
|  | ||||
| public: | ||||
|   client_pool(const client_pool &) = delete; | ||||
|   client_pool(client_pool &&) = delete; | ||||
|   auto operator=(const client_pool &) -> client_pool & = delete; | ||||
|   auto operator=(client_pool &&) -> client_pool & = delete; | ||||
|  | ||||
| private: | ||||
|   std::uint8_t pool_size_; | ||||
|   std::unordered_map<std::string, std::shared_ptr<pool>> pool_lookup_; | ||||
|   std::mutex pool_mutex_; | ||||
|   bool shutdown_ = false; | ||||
|  | ||||
| private: | ||||
|   static constexpr const auto min_pool_size = 10U; | ||||
|  | ||||
| public: | ||||
|   void execute(const std::string &client_id, std::uint64_t thread_id, | ||||
|                const worker_callback &worker, | ||||
|                const worker_complete_callback &worker_complete); | ||||
|  | ||||
|   void remove_client(const std::string &client_id); | ||||
|  | ||||
|   void shutdown(); | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_PACKET_CLIENT_POOL_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_PACKET_CLIENT_POOL_HPP_ | ||||
| #define INCLUDE_COMM_PACKET_CLIENT_POOL_HPP_ | ||||
|  | ||||
| #include "comm/packet/packet.hpp" | ||||
| #include "types/repertory.hpp" | ||||
|  | ||||
| namespace repertory { | ||||
| class client_pool final { | ||||
| public: | ||||
|   using worker_callback = std::function<packet::error_type()>; | ||||
|   using worker_complete_callback = | ||||
|       std::function<void(const packet::error_type &)>; | ||||
|  | ||||
| private: | ||||
|   class pool final { | ||||
|   private: | ||||
|     struct work_item final { | ||||
|       work_item(worker_callback worker, | ||||
|                 worker_complete_callback worker_complete) | ||||
|           : work(std::move(worker)), | ||||
|             work_complete(std::move(worker_complete)) {} | ||||
|  | ||||
|       worker_callback work; | ||||
|       worker_complete_callback work_complete; | ||||
|     }; | ||||
|  | ||||
|     struct work_queue final { | ||||
|       std::mutex mutex; | ||||
|       std::condition_variable notify; | ||||
|       std::deque<std::shared_ptr<work_item>> queue; | ||||
|     }; | ||||
|  | ||||
|   public: | ||||
|     explicit pool(std::uint8_t pool_size); | ||||
|  | ||||
|     ~pool() { shutdown(); } | ||||
|  | ||||
|   public: | ||||
|     pool(const pool &) = delete; | ||||
|     pool(pool &&) = delete; | ||||
|     auto operator=(const pool &) -> pool & = delete; | ||||
|     auto operator=(pool &&) -> pool & = delete; | ||||
|  | ||||
|   private: | ||||
|     std::vector<std::unique_ptr<work_queue>> pool_queues_; | ||||
|     std::vector<std::thread> pool_threads_; | ||||
|     bool shutdown_{false}; | ||||
|     std::atomic<std::uint8_t> thread_index_{}; | ||||
|  | ||||
|   public: | ||||
|     void execute(std::uint64_t thread_id, const worker_callback &worker, | ||||
|                  const worker_complete_callback &worker_complete); | ||||
|  | ||||
|     void shutdown(); | ||||
|   }; | ||||
|  | ||||
| public: | ||||
|   explicit client_pool(std::uint8_t pool_size = min_pool_size) | ||||
|       : pool_size_(pool_size == 0U ? min_pool_size : pool_size) {} | ||||
|  | ||||
|   ~client_pool() { shutdown(); } | ||||
|  | ||||
| public: | ||||
|   client_pool(const client_pool &) = delete; | ||||
|   client_pool(client_pool &&) = delete; | ||||
|   auto operator=(const client_pool &) -> client_pool & = delete; | ||||
|   auto operator=(client_pool &&) -> client_pool & = delete; | ||||
|  | ||||
| private: | ||||
|   std::uint8_t pool_size_; | ||||
|   std::unordered_map<std::string, std::shared_ptr<pool>> pool_lookup_; | ||||
|   std::mutex pool_mutex_; | ||||
|   bool shutdown_ = false; | ||||
|  | ||||
| private: | ||||
|   static constexpr const auto min_pool_size = 10U; | ||||
|  | ||||
| public: | ||||
|   void execute(const std::string &client_id, std::uint64_t thread_id, | ||||
|                const worker_callback &worker, | ||||
|                const worker_complete_callback &worker_complete); | ||||
|  | ||||
|   void remove_client(const std::string &client_id); | ||||
|  | ||||
|   void shutdown(); | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_PACKET_CLIENT_POOL_HPP_ | ||||
|   | ||||
| @@ -1,232 +1,232 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_PACKET_PACKET_HPP_ | ||||
| #define INCLUDE_COMM_PACKET_PACKET_HPP_ | ||||
|  | ||||
| #include "types/remote.hpp" | ||||
| #include "types/repertory.hpp" | ||||
|  | ||||
| namespace repertory { | ||||
| #define DECODE_OR_RETURN(p, value)                                             \ | ||||
|   if ((ret = (p)->decode(value)) != 0)                                         \ | ||||
|   return ret | ||||
| #define DECODE_OR_IGNORE(p, value)                                             \ | ||||
|   if (ret == 0)                                                                \ | ||||
|   ret = (p)->decode(value) | ||||
|  | ||||
| class packet final { | ||||
| public: | ||||
|   using error_type = std::int32_t; | ||||
|  | ||||
| public: | ||||
|   packet() = default; | ||||
|  | ||||
|   explicit packet(data_buffer buffer) : buffer_(std::move(buffer)) {} | ||||
|  | ||||
|   explicit packet(data_buffer &&buffer) : buffer_(std::move(buffer)) {} | ||||
|  | ||||
|   packet(const packet &pkt) noexcept = default; | ||||
|  | ||||
|   packet(packet &&pkt) noexcept | ||||
|       : buffer_(std::move(pkt.buffer_)), decode_offset_(pkt.decode_offset_) {} | ||||
|  | ||||
|   ~packet() = default; | ||||
|  | ||||
| private: | ||||
|   data_buffer buffer_; | ||||
|   std::size_t decode_offset_ = 0U; | ||||
|  | ||||
| public: | ||||
|   [[nodiscard]] static auto decode_json(packet &response, json &json_data) | ||||
|       -> int; | ||||
|  | ||||
| public: | ||||
|   void clear(); | ||||
|  | ||||
|   [[nodiscard]] auto current_pointer() -> char * { | ||||
|     return (decode_offset_ < buffer_.size()) ? &buffer_[decode_offset_] | ||||
|                                              : nullptr; | ||||
|   } | ||||
|  | ||||
|   [[nodiscard]] auto current_pointer() const -> const char * { | ||||
|     return (decode_offset_ < buffer_.size()) ? &buffer_[decode_offset_] | ||||
|                                              : nullptr; | ||||
|   } | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::string &data) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::wstring &data) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(void *buffer, std::size_t size) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(void *&ptr) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::int8_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::uint8_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::int16_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::uint16_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::int32_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::uint32_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::int64_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::uint64_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::open_flags &val) -> error_type { | ||||
|     return decode(reinterpret_cast<std::uint32_t &>(val)); | ||||
|   } | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::setattr_x &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::stat &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::statfs &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::statfs_x &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::file_info &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decrypt(const std::string &token) -> error_type; | ||||
|  | ||||
|   void encode(const void *buffer, std::size_t size, bool should_reserve = true); | ||||
|  | ||||
|   void encode(const char *str) { | ||||
|     encode(std::string(str == nullptr ? "" : str)); | ||||
|   } | ||||
|  | ||||
|   void encode(const std::string &str); | ||||
|  | ||||
|   void encode(const wchar_t *str); | ||||
|  | ||||
|   void encode(const std::wstring &str); | ||||
|  | ||||
|   void encode(void *ptr) { | ||||
|     encode(static_cast<std::uint64_t>(reinterpret_cast<std::uintptr_t>(ptr))); | ||||
|   } | ||||
|  | ||||
|   void encode(std::int8_t val); | ||||
|  | ||||
|   void encode(std::uint8_t val); | ||||
|  | ||||
|   void encode(std::int16_t val); | ||||
|  | ||||
|   void encode(std::uint16_t val); | ||||
|  | ||||
|   void encode(std::int32_t val); | ||||
|  | ||||
|   void encode(std::uint32_t val); | ||||
|  | ||||
|   void encode(std::int64_t val); | ||||
|  | ||||
|   void encode(std::uint64_t val); | ||||
|  | ||||
|   void encode(remote::open_flags val) { | ||||
|     encode(static_cast<std::uint32_t>(val)); | ||||
|   } | ||||
|  | ||||
|   void encode(remote::setattr_x val); | ||||
|  | ||||
|   void encode(remote::stat val); | ||||
|  | ||||
|   void encode(remote::statfs val, bool should_reserve = true); | ||||
|  | ||||
|   void encode(remote::statfs_x val); | ||||
|  | ||||
|   void encode(remote::file_info val); | ||||
|  | ||||
|   void encode_top(const void *buffer, std::size_t size, | ||||
|                   bool should_reserve = true); | ||||
|  | ||||
|   void encode_top(const std::string &str); | ||||
|  | ||||
|   void encode_top(const std::wstring &str); | ||||
|  | ||||
|   void encode_top(void *ptr) { | ||||
|     encode_top( | ||||
|         static_cast<std::uint64_t>(reinterpret_cast<std::uintptr_t>(ptr))); | ||||
|   } | ||||
|  | ||||
|   void encode_top(std::int8_t val); | ||||
|  | ||||
|   void encode_top(std::uint8_t val); | ||||
|  | ||||
|   void encode_top(std::int16_t val); | ||||
|  | ||||
|   void encode_top(std::uint16_t val); | ||||
|  | ||||
|   void encode_top(std::int32_t val); | ||||
|  | ||||
|   void encode_top(std::uint32_t val); | ||||
|  | ||||
|   void encode_top(std::int64_t val); | ||||
|  | ||||
|   void encode_top(std::uint64_t val); | ||||
|  | ||||
|   void encode_top(remote::open_flags val) { | ||||
|     encode_top(static_cast<std::uint32_t>(val)); | ||||
|   } | ||||
|  | ||||
|   void encode_top(remote::setattr_x val); | ||||
|  | ||||
|   void encode_top(remote::stat val); | ||||
|  | ||||
|   void encode_top(remote::statfs val, bool should_reserve = true); | ||||
|  | ||||
|   void encode_top(remote::statfs_x val); | ||||
|  | ||||
|   void encode_top(remote::file_info val); | ||||
|  | ||||
|   void encrypt(const std::string &token); | ||||
|  | ||||
|   [[nodiscard]] auto get_size() const -> std::uint32_t { | ||||
|     return static_cast<std::uint32_t>(buffer_.size()); | ||||
|   } | ||||
|  | ||||
|   void transfer_into(data_buffer &buffer); | ||||
|  | ||||
| public: | ||||
|   auto operator=(const data_buffer &buffer) noexcept -> packet &; | ||||
|  | ||||
|   auto operator=(data_buffer &&buffer) noexcept -> packet &; | ||||
|  | ||||
|   auto operator=(const packet &pkt) noexcept -> packet &; | ||||
|  | ||||
|   auto operator=(packet &&pkt) noexcept -> packet &; | ||||
|  | ||||
|   [[nodiscard]] auto operator[](std::size_t index) -> char & { | ||||
|     return buffer_[index]; | ||||
|   } | ||||
|  | ||||
|   [[nodiscard]] auto operator[](std::size_t index) const -> const char & { | ||||
|     return buffer_.at(index); | ||||
|   } | ||||
| }; | ||||
|  | ||||
| using packet = packet; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_PACKET_PACKET_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_PACKET_PACKET_HPP_ | ||||
| #define INCLUDE_COMM_PACKET_PACKET_HPP_ | ||||
|  | ||||
| #include "types/remote.hpp" | ||||
| #include "types/repertory.hpp" | ||||
|  | ||||
| namespace repertory { | ||||
| #define DECODE_OR_RETURN(p, value)                                             \ | ||||
|   if ((ret = (p)->decode(value)) != 0)                                         \ | ||||
|   return ret | ||||
| #define DECODE_OR_IGNORE(p, value)                                             \ | ||||
|   if (ret == 0)                                                                \ | ||||
|   ret = (p)->decode(value) | ||||
|  | ||||
| class packet final { | ||||
| public: | ||||
|   using error_type = std::int32_t; | ||||
|  | ||||
| public: | ||||
|   packet() = default; | ||||
|  | ||||
|   explicit packet(data_buffer buffer) : buffer_(std::move(buffer)) {} | ||||
|  | ||||
|   explicit packet(data_buffer &&buffer) : buffer_(std::move(buffer)) {} | ||||
|  | ||||
|   packet(const packet &pkt) noexcept = default; | ||||
|  | ||||
|   packet(packet &&pkt) noexcept | ||||
|       : buffer_(std::move(pkt.buffer_)), decode_offset_(pkt.decode_offset_) {} | ||||
|  | ||||
|   ~packet() = default; | ||||
|  | ||||
| private: | ||||
|   data_buffer buffer_; | ||||
|   std::size_t decode_offset_ = 0U; | ||||
|  | ||||
| public: | ||||
|   [[nodiscard]] static auto decode_json(packet &response, json &json_data) | ||||
|       -> int; | ||||
|  | ||||
| public: | ||||
|   void clear(); | ||||
|  | ||||
|   [[nodiscard]] auto current_pointer() -> char * { | ||||
|     return (decode_offset_ < buffer_.size()) ? &buffer_[decode_offset_] | ||||
|                                              : nullptr; | ||||
|   } | ||||
|  | ||||
|   [[nodiscard]] auto current_pointer() const -> const char * { | ||||
|     return (decode_offset_ < buffer_.size()) ? &buffer_[decode_offset_] | ||||
|                                              : nullptr; | ||||
|   } | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::string &data) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::wstring &data) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(void *buffer, std::size_t size) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(void *&ptr) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::int8_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::uint8_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::int16_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::uint16_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::int32_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::uint32_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::int64_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(std::uint64_t &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::open_flags &val) -> error_type { | ||||
|     return decode(reinterpret_cast<std::uint32_t &>(val)); | ||||
|   } | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::setattr_x &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::stat &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::statfs &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::statfs_x &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decode(remote::file_info &val) -> error_type; | ||||
|  | ||||
|   [[nodiscard]] auto decrypt(const std::string &token) -> error_type; | ||||
|  | ||||
|   void encode(const void *buffer, std::size_t size, bool should_reserve = true); | ||||
|  | ||||
|   void encode(const char *str) { | ||||
|     encode(std::string(str == nullptr ? "" : str)); | ||||
|   } | ||||
|  | ||||
|   void encode(const std::string &str); | ||||
|  | ||||
|   void encode(const wchar_t *str); | ||||
|  | ||||
|   void encode(const std::wstring &str); | ||||
|  | ||||
|   void encode(void *ptr) { | ||||
|     encode(static_cast<std::uint64_t>(reinterpret_cast<std::uintptr_t>(ptr))); | ||||
|   } | ||||
|  | ||||
|   void encode(std::int8_t val); | ||||
|  | ||||
|   void encode(std::uint8_t val); | ||||
|  | ||||
|   void encode(std::int16_t val); | ||||
|  | ||||
|   void encode(std::uint16_t val); | ||||
|  | ||||
|   void encode(std::int32_t val); | ||||
|  | ||||
|   void encode(std::uint32_t val); | ||||
|  | ||||
|   void encode(std::int64_t val); | ||||
|  | ||||
|   void encode(std::uint64_t val); | ||||
|  | ||||
|   void encode(remote::open_flags val) { | ||||
|     encode(static_cast<std::uint32_t>(val)); | ||||
|   } | ||||
|  | ||||
|   void encode(remote::setattr_x val); | ||||
|  | ||||
|   void encode(remote::stat val); | ||||
|  | ||||
|   void encode(remote::statfs val, bool should_reserve = true); | ||||
|  | ||||
|   void encode(remote::statfs_x val); | ||||
|  | ||||
|   void encode(remote::file_info val); | ||||
|  | ||||
|   void encode_top(const void *buffer, std::size_t size, | ||||
|                   bool should_reserve = true); | ||||
|  | ||||
|   void encode_top(const std::string &str); | ||||
|  | ||||
|   void encode_top(const std::wstring &str); | ||||
|  | ||||
|   void encode_top(void *ptr) { | ||||
|     encode_top( | ||||
|         static_cast<std::uint64_t>(reinterpret_cast<std::uintptr_t>(ptr))); | ||||
|   } | ||||
|  | ||||
|   void encode_top(std::int8_t val); | ||||
|  | ||||
|   void encode_top(std::uint8_t val); | ||||
|  | ||||
|   void encode_top(std::int16_t val); | ||||
|  | ||||
|   void encode_top(std::uint16_t val); | ||||
|  | ||||
|   void encode_top(std::int32_t val); | ||||
|  | ||||
|   void encode_top(std::uint32_t val); | ||||
|  | ||||
|   void encode_top(std::int64_t val); | ||||
|  | ||||
|   void encode_top(std::uint64_t val); | ||||
|  | ||||
|   void encode_top(remote::open_flags val) { | ||||
|     encode_top(static_cast<std::uint32_t>(val)); | ||||
|   } | ||||
|  | ||||
|   void encode_top(remote::setattr_x val); | ||||
|  | ||||
|   void encode_top(remote::stat val); | ||||
|  | ||||
|   void encode_top(remote::statfs val, bool should_reserve = true); | ||||
|  | ||||
|   void encode_top(remote::statfs_x val); | ||||
|  | ||||
|   void encode_top(remote::file_info val); | ||||
|  | ||||
|   void encrypt(const std::string &token); | ||||
|  | ||||
|   [[nodiscard]] auto get_size() const -> std::uint32_t { | ||||
|     return static_cast<std::uint32_t>(buffer_.size()); | ||||
|   } | ||||
|  | ||||
|   void transfer_into(data_buffer &buffer); | ||||
|  | ||||
| public: | ||||
|   auto operator=(const data_buffer &buffer) noexcept -> packet &; | ||||
|  | ||||
|   auto operator=(data_buffer &&buffer) noexcept -> packet &; | ||||
|  | ||||
|   auto operator=(const packet &pkt) noexcept -> packet &; | ||||
|  | ||||
|   auto operator=(packet &&pkt) noexcept -> packet &; | ||||
|  | ||||
|   [[nodiscard]] auto operator[](std::size_t index) -> char & { | ||||
|     return buffer_[index]; | ||||
|   } | ||||
|  | ||||
|   [[nodiscard]] auto operator[](std::size_t index) const -> const char & { | ||||
|     return buffer_.at(index); | ||||
|   } | ||||
| }; | ||||
|  | ||||
| using packet = packet; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_PACKET_PACKET_HPP_ | ||||
|   | ||||
| @@ -1,91 +1,91 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_PACKET_PACKET_CLIENT_HPP_ | ||||
| #define INCLUDE_COMM_PACKET_PACKET_CLIENT_HPP_ | ||||
|  | ||||
| #include "comm/packet/packet.hpp" | ||||
|  | ||||
| using boost::asio::ip::tcp; | ||||
|  | ||||
| namespace repertory { | ||||
| class packet_client final { | ||||
| private: | ||||
|   struct client final { | ||||
|     explicit client(boost::asio::io_context &ctx) : nonce(""), socket(ctx) {} | ||||
|  | ||||
|     std::string nonce; | ||||
|     tcp::socket socket; | ||||
|   }; | ||||
|  | ||||
| public: | ||||
|   packet_client(std::string host_name_or_ip, std::uint8_t max_connections, | ||||
|                 std::uint16_t port, std::uint16_t receive_timeout, | ||||
|                 std::uint16_t send_timeout, std::string encryption_token); | ||||
|  | ||||
|   ~packet_client(); | ||||
|  | ||||
| private: | ||||
|   boost::asio::io_context io_context_; | ||||
|   const std::string host_name_or_ip_; | ||||
|   const std::uint8_t max_connections_; | ||||
|   const std::uint16_t port_; | ||||
|   const std::uint16_t receive_timeout_; | ||||
|   const std::uint16_t send_timeout_; | ||||
|   const std::string encryption_token_; | ||||
|   std::string unique_id_; | ||||
|  | ||||
|   bool allow_connections_ = true; | ||||
|   boost::asio::ip::basic_resolver<boost::asio::ip::tcp>::results_type | ||||
|       resolve_results_; | ||||
|   std::mutex clients_mutex_; | ||||
|   std::vector<std::shared_ptr<client>> clients_; | ||||
|  | ||||
| private: | ||||
|   void close(client &c) const; | ||||
|  | ||||
|   void close_all(); | ||||
|  | ||||
|   void connect(client &c); | ||||
|  | ||||
|   [[nodiscard]] auto get_client() -> std::shared_ptr<client>; | ||||
|  | ||||
|   void put_client(std::shared_ptr<client> &c); | ||||
|  | ||||
|   [[nodiscard]] auto read_packet(client &c, packet &response) | ||||
|       -> packet::error_type; | ||||
|  | ||||
|   void resolve(); | ||||
|  | ||||
| public: | ||||
|   [[nodiscard]] auto send(const std::string &method, | ||||
|                           std::uint32_t &service_flags) -> packet::error_type; | ||||
|  | ||||
|   [[nodiscard]] auto send(const std::string &method, packet &request, | ||||
|                           std::uint32_t &service_flags) -> packet::error_type; | ||||
|  | ||||
|   [[nodiscard]] auto send(const std::string &method, packet &request, | ||||
|                           packet &response, std::uint32_t &service_flags) | ||||
|       -> packet::error_type; | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_PACKET_PACKET_CLIENT_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_PACKET_PACKET_CLIENT_HPP_ | ||||
| #define INCLUDE_COMM_PACKET_PACKET_CLIENT_HPP_ | ||||
|  | ||||
| #include "comm/packet/packet.hpp" | ||||
|  | ||||
| using boost::asio::ip::tcp; | ||||
|  | ||||
| namespace repertory { | ||||
| class packet_client final { | ||||
| private: | ||||
|   struct client final { | ||||
|     explicit client(boost::asio::io_context &ctx) : nonce(""), socket(ctx) {} | ||||
|  | ||||
|     std::string nonce; | ||||
|     tcp::socket socket; | ||||
|   }; | ||||
|  | ||||
| public: | ||||
|   packet_client(std::string host_name_or_ip, std::uint8_t max_connections, | ||||
|                 std::uint16_t port, std::uint16_t receive_timeout, | ||||
|                 std::uint16_t send_timeout, std::string encryption_token); | ||||
|  | ||||
|   ~packet_client(); | ||||
|  | ||||
| private: | ||||
|   boost::asio::io_context io_context_; | ||||
|   const std::string host_name_or_ip_; | ||||
|   const std::uint8_t max_connections_; | ||||
|   const std::uint16_t port_; | ||||
|   const std::uint16_t receive_timeout_; | ||||
|   const std::uint16_t send_timeout_; | ||||
|   const std::string encryption_token_; | ||||
|   std::string unique_id_; | ||||
|  | ||||
|   bool allow_connections_ = true; | ||||
|   boost::asio::ip::basic_resolver<boost::asio::ip::tcp>::results_type | ||||
|       resolve_results_; | ||||
|   std::mutex clients_mutex_; | ||||
|   std::vector<std::shared_ptr<client>> clients_; | ||||
|  | ||||
| private: | ||||
|   void close(client &c) const; | ||||
|  | ||||
|   void close_all(); | ||||
|  | ||||
|   void connect(client &c); | ||||
|  | ||||
|   [[nodiscard]] auto get_client() -> std::shared_ptr<client>; | ||||
|  | ||||
|   void put_client(std::shared_ptr<client> &c); | ||||
|  | ||||
|   [[nodiscard]] auto read_packet(client &c, packet &response) | ||||
|       -> packet::error_type; | ||||
|  | ||||
|   void resolve(); | ||||
|  | ||||
| public: | ||||
|   [[nodiscard]] auto send(const std::string &method, | ||||
|                           std::uint32_t &service_flags) -> packet::error_type; | ||||
|  | ||||
|   [[nodiscard]] auto send(const std::string &method, packet &request, | ||||
|                           std::uint32_t &service_flags) -> packet::error_type; | ||||
|  | ||||
|   [[nodiscard]] auto send(const std::string &method, packet &request, | ||||
|                           packet &response, std::uint32_t &service_flags) | ||||
|       -> packet::error_type; | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_PACKET_PACKET_CLIENT_HPP_ | ||||
|   | ||||
| @@ -1,92 +1,92 @@ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_PACKET_PACKET_SERVER_HPP_ | ||||
| #define INCLUDE_COMM_PACKET_PACKET_SERVER_HPP_ | ||||
|  | ||||
| #include "comm/packet/client_pool.hpp" | ||||
| #include "types/repertory.hpp" | ||||
| #include "utils/utils.hpp" | ||||
|  | ||||
| using namespace boost::asio; | ||||
| using boost::asio::ip::tcp; | ||||
|  | ||||
| namespace repertory { | ||||
| class packet_server final { | ||||
| public: | ||||
|   using closed_callback = std::function<void(const std::string &)>; | ||||
|   using message_complete_callback = client_pool::worker_complete_callback; | ||||
|   using message_handler_callback = std::function<void( | ||||
|       std::uint32_t, const std::string &, std::uint64_t, const std::string &, | ||||
|       packet *, packet &, message_complete_callback)>; | ||||
|  | ||||
| public: | ||||
|   packet_server(std::uint16_t port, std::string token, std::uint8_t pool_size, | ||||
|                 closed_callback closed, | ||||
|                 message_handler_callback message_handler); | ||||
|  | ||||
|   ~packet_server(); | ||||
|  | ||||
| private: | ||||
|   struct connection { | ||||
|     connection(boost::asio::io_service &io_service, tcp::acceptor &acceptor_) | ||||
|         : socket(io_service), acceptor(acceptor_) {} | ||||
|  | ||||
|     tcp::socket socket; | ||||
|     tcp::acceptor &acceptor; | ||||
|     data_buffer buffer; | ||||
|     std::string client_id; | ||||
|     std::string nonce; | ||||
|  | ||||
|     void generate_nonce() { nonce = utils::generate_random_string(256u); } | ||||
|   }; | ||||
|  | ||||
| private: | ||||
|   const std::string encryption_token_; | ||||
|   closed_callback closed_; | ||||
|   message_handler_callback message_handler_; | ||||
|   boost::asio::io_context io_context_; | ||||
|   std::unique_ptr<std::thread> server_thread_; | ||||
|   std::vector<std::thread> service_threads_; | ||||
|   std::recursive_mutex connection_mutex_; | ||||
|   std::unordered_map<std::string, std::uint32_t> connection_lookup_; | ||||
|  | ||||
| private: | ||||
|   void add_client(connection &c, const std::string &client_id); | ||||
|  | ||||
|   void initialize(const uint16_t &port, uint8_t pool_size); | ||||
|  | ||||
|   void listen_for_connection(tcp::acceptor &acceptor); | ||||
|  | ||||
|   void on_accept(std::shared_ptr<connection> c, boost::system::error_code ec); | ||||
|  | ||||
|   void read_header(std::shared_ptr<connection> c); | ||||
|  | ||||
|   void read_packet(std::shared_ptr<connection> c, std::uint32_t data_size); | ||||
|  | ||||
|   void remove_client(connection &c); | ||||
|  | ||||
|   void send_response(std::shared_ptr<connection> c, | ||||
|                      const packet::error_type &result, packet &response); | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_PACKET_PACKET_SERVER_HPP_ | ||||
| /* | ||||
|   Copyright <2018-2023> <scott.e.graves@protonmail.com> | ||||
|  | ||||
|   Permission is hereby granted, free of charge, to any person obtaining a copy | ||||
|   of this software and associated documentation files (the "Software"), to deal | ||||
|   in the Software without restriction, including without limitation the rights | ||||
|   to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
|   copies of the Software, and to permit persons to whom the Software is | ||||
|   furnished to do so, subject to the following conditions: | ||||
|  | ||||
|   The above copyright notice and this permission notice shall be included in all | ||||
|   copies or substantial portions of the Software. | ||||
|  | ||||
|   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||||
|   IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||||
|   FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||||
|   AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||||
|   LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||||
|   OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE | ||||
|   SOFTWARE. | ||||
| */ | ||||
| #ifndef INCLUDE_COMM_PACKET_PACKET_SERVER_HPP_ | ||||
| #define INCLUDE_COMM_PACKET_PACKET_SERVER_HPP_ | ||||
|  | ||||
| #include "comm/packet/client_pool.hpp" | ||||
| #include "types/repertory.hpp" | ||||
| #include "utils/utils.hpp" | ||||
|  | ||||
| using namespace boost::asio; | ||||
| using boost::asio::ip::tcp; | ||||
|  | ||||
| namespace repertory { | ||||
| class packet_server final { | ||||
| public: | ||||
|   using closed_callback = std::function<void(const std::string &)>; | ||||
|   using message_complete_callback = client_pool::worker_complete_callback; | ||||
|   using message_handler_callback = std::function<void( | ||||
|       std::uint32_t, const std::string &, std::uint64_t, const std::string &, | ||||
|       packet *, packet &, message_complete_callback)>; | ||||
|  | ||||
| public: | ||||
|   packet_server(std::uint16_t port, std::string token, std::uint8_t pool_size, | ||||
|                 closed_callback closed, | ||||
|                 message_handler_callback message_handler); | ||||
|  | ||||
|   ~packet_server(); | ||||
|  | ||||
| private: | ||||
|   struct connection { | ||||
|     connection(boost::asio::io_service &io_service, tcp::acceptor &acceptor_) | ||||
|         : socket(io_service), acceptor(acceptor_) {} | ||||
|  | ||||
|     tcp::socket socket; | ||||
|     tcp::acceptor &acceptor; | ||||
|     data_buffer buffer; | ||||
|     std::string client_id; | ||||
|     std::string nonce; | ||||
|  | ||||
|     void generate_nonce() { nonce = utils::generate_random_string(256u); } | ||||
|   }; | ||||
|  | ||||
| private: | ||||
|   const std::string encryption_token_; | ||||
|   closed_callback closed_; | ||||
|   message_handler_callback message_handler_; | ||||
|   boost::asio::io_context io_context_; | ||||
|   std::unique_ptr<std::thread> server_thread_; | ||||
|   std::vector<std::thread> service_threads_; | ||||
|   std::recursive_mutex connection_mutex_; | ||||
|   std::unordered_map<std::string, std::uint32_t> connection_lookup_; | ||||
|  | ||||
| private: | ||||
|   void add_client(connection &c, const std::string &client_id); | ||||
|  | ||||
|   void initialize(const uint16_t &port, uint8_t pool_size); | ||||
|  | ||||
|   void listen_for_connection(tcp::acceptor &acceptor); | ||||
|  | ||||
|   void on_accept(std::shared_ptr<connection> c, boost::system::error_code ec); | ||||
|  | ||||
|   void read_header(std::shared_ptr<connection> c); | ||||
|  | ||||
|   void read_packet(std::shared_ptr<connection> c, std::uint32_t data_size); | ||||
|  | ||||
|   void remove_client(connection &c); | ||||
|  | ||||
|   void send_response(std::shared_ptr<connection> c, | ||||
|                      const packet::error_type &result, packet &response); | ||||
| }; | ||||
| } // namespace repertory | ||||
|  | ||||
| #endif // INCLUDE_COMM_PACKET_PACKET_SERVER_HPP_ | ||||
|   | ||||
		Reference in New Issue
	
	Block a user