#ifndef CPR_MULTIPERFORM_H #define CPR_MULTIPERFORM_H #include "cpr/curlmultiholder.h" #include "cpr/response.h" #include "cpr/session.h" #include #include #include #include #include namespace cpr { class InterceptorMulti; class MultiPerform { public: enum class HttpMethod { UNDEFINED = 0, GET_REQUEST, POST_REQUEST, PUT_REQUEST, DELETE_REQUEST, PATCH_REQUEST, HEAD_REQUEST, OPTIONS_REQUEST, DOWNLOAD_REQUEST, }; MultiPerform(); MultiPerform(const MultiPerform& other) = delete; MultiPerform(MultiPerform&& old) = default; ~MultiPerform(); MultiPerform& operator=(const MultiPerform& other) = delete; MultiPerform& operator=(MultiPerform&& old) noexcept = default; std::vector Get(); std::vector Delete(); template std::vector Download(DownloadArgTypes... args); std::vector Put(); std::vector Head(); std::vector Options(); std::vector Patch(); std::vector Post(); std::vector Perform(); template std::vector PerformDownload(DownloadArgTypes... args); void AddSession(std::shared_ptr& session, HttpMethod method = HttpMethod::UNDEFINED); void RemoveSession(const std::shared_ptr& session); std::vector, HttpMethod>>& GetSessions(); [[nodiscard]] const std::vector, HttpMethod>>& GetSessions() const; void AddInterceptor(const std::shared_ptr& pinterceptor); private: // Interceptors should be able to call the private proceed() and PrepareDownloadSessions() functions friend InterceptorMulti; void SetHttpMethod(HttpMethod method); void PrepareSessions(); template void PrepareDownloadSessions(size_t sessions_index, CurrentDownloadArgType current_arg, DownloadArgTypes... args); template void PrepareDownloadSessions(size_t sessions_index, CurrentDownloadArgType current_arg); void PrepareDownloadSession(size_t sessions_index, std::ofstream& file); void PrepareDownloadSession(size_t sessions_index, const WriteCallback& write); void PrepareGet(); void PrepareDelete(); void PreparePut(); void PreparePatch(); void PrepareHead(); void PrepareOptions(); void PreparePost(); template void PrepareDownload(DownloadArgTypes... args); std::vector intercept(); std::vector proceed(); std::vector MakeRequest(); std::vector MakeDownloadRequest(); void DoMultiPerform(); std::vector ReadMultiInfo(std::function&& complete_function); std::vector, HttpMethod>> sessions_; std::unique_ptr multicurl_; bool is_download_multi_perform{false}; std::queue> interceptors_; }; template void MultiPerform::PrepareDownloadSessions(size_t sessions_index, CurrentDownloadArgType current_arg) { PrepareDownloadSession(sessions_index, current_arg); } template void MultiPerform::PrepareDownloadSessions(size_t sessions_index, CurrentDownloadArgType current_arg, DownloadArgTypes... args) { PrepareDownloadSession(sessions_index, current_arg); PrepareDownloadSessions(sessions_index + 1, args...); } template void MultiPerform::PrepareDownload(DownloadArgTypes... args) { SetHttpMethod(HttpMethod::DOWNLOAD_REQUEST); PrepareDownloadSessions(0, args...); } template std::vector MultiPerform::Download(DownloadArgTypes... args) { if (sizeof...(args) != sessions_.size()) { throw std::invalid_argument("Number of download arguments has to match the number of sessions added to the multiperform!"); } PrepareDownload(args...); return MakeDownloadRequest(); } template std::vector MultiPerform::PerformDownload(DownloadArgTypes... args) { if (sizeof...(args) != sessions_.size()) { throw std::invalid_argument("Number of download arguments has to match the number of sessions added to the multiperform!"); } PrepareDownloadSessions(0, args...); return MakeDownloadRequest(); } } // namespace cpr #endif