diff --git a/README.md b/README.md index 4a89c50..e60d2bd 100644 --- a/README.md +++ b/README.md @@ -23,6 +23,7 @@ Modern, non-blocking and exception free, header-only HTTP Client library for C++ * [POST request with form data](#post-request-with-form-data) * [POST request with JSON data](#post-request-with-json-data) * [What about others? (PUT, DELETE, PATCH)](#what-about-others-put-delete-patch) +* [How to ignore SSL certificate errors?](#how-to-ignore-ssl-certificate-errors) * [Semantic Versioning](#semantic-versioning) * [Full function list](#full-function-list) * [License](#license) @@ -336,6 +337,32 @@ int main() { ``` +## How to ignore SSL certificate errors? + +If you need to ignore SSL certificate errors for any valid reason, you can continue +working by passing **"true"** value to the **"ignoreSslErrors"** variable of the +HttpClient class. + +```cpp +#include +#include "libcpp-http-client.hpp" + +using namespace lklibs; + +int main() { + + HttpClient httpClient; + + // If you need to ignore SSL errors, you can set the "ignoreSslErrors" field to true + httpClient.ignoreSslErrors = true; + + auto response = httpClient.getRequest("https://api.myinvalidssl.com").get(); + + return 0; +} +``` + + ## Semantic Versioning Versioning of the library is done using conventional semantic versioning. Accordingly, @@ -363,49 +390,49 @@ overloaded versions of 5 functions in total. ```cpp - getRequest - std::future getRequest(const std::string &url) - - std::future getRequest(const std::string &url, bool returnAsBinary) - - std::future getRequest(const std::string &url, const std::map &headers) - - std::future getRequest(const std::string &url, bool returnAsBinary, const std::map &headers) + - std::future getRequest(const std::string &url, bool returnAsBinary, bool ignoreSslErrors = false) + - std::future getRequest(const std::string &url, const std::map &headers, bool ignoreSslErrors = false) + - std::future getRequest(const std::string &url, bool returnAsBinary, const std::map &headers, bool ignoreSslErrors = false) - postRequest - std::future postRequest(const std::string &url) - - std::future postRequest(const std::string &url, const std::string &payload) - - std::future postRequest(const std::string &url, bool returnAsBinary) - - std::future postRequest(const std::string &url, const std::map &headers) - - std::future postRequest(const std::string &url, const std::string &payload, bool returnAsBinary) - - std::future postRequest(const std::string &url, const std::string &payload, const std::map &headers) - - std::future postRequest(const std::string &url, bool returnAsBinary, const std::map &headers) - - std::future postRequest(const std::string &url, const std::string &payload, bool returnAsBinary, const std::map &headers) + - std::future postRequest(const std::string &url, const std::string &payload, bool ignoreSslErrors = false) + - std::future postRequest(const std::string &url, bool returnAsBinary, bool ignoreSslErrors = false) + - std::future postRequest(const std::string &url, const std::map &headers, bool ignoreSslErrors = false) + - std::future postRequest(const std::string &url, const std::string &payload, bool returnAsBinary, bool ignoreSslErrors = false) + - std::future postRequest(const std::string &url, const std::string &payload, const std::map &headers, bool ignoreSslErrors = false) + - std::future postRequest(const std::string &url, bool returnAsBinary, const std::map &headers, bool ignoreSslErrors = false) + - std::future postRequest(const std::string &url, const std::string &payload, bool returnAsBinary, const std::map &headers, bool ignoreSslErrors = false) - putRequest - std::future putRequest(const std::string &url) - - std::future putRequest(const std::string &url, const std::string &payload) - - std::future putRequest(const std::string &url, bool returnAsBinary) - - std::future putRequest(const std::string &url, const std::map &headers) - - std::future putRequest(const std::string &url, const std::string &payload, bool returnAsBinary) - - std::future putRequest(const std::string &url, const std::string &payload, const std::map &headers) - - std::future putRequest(const std::string &url, bool returnAsBinary, const std::map &headers) - - std::future putRequest(const std::string &url, const std::string &payload, bool returnAsBinary, const std::map &headers) + - std::future putRequest(const std::string &url, const std::string &payload, bool ignoreSslErrors = false) + - std::future putRequest(const std::string &url, bool returnAsBinary, bool ignoreSslErrors = false) + - std::future putRequest(const std::string &url, const std::map &headers, bool ignoreSslErrors = false) + - std::future putRequest(const std::string &url, const std::string &payload, bool returnAsBinary, bool ignoreSslErrors = false) + - std::future putRequest(const std::string &url, const std::string &payload, const std::map &headers, bool ignoreSslErrors = false) + - std::future putRequest(const std::string &url, bool returnAsBinary, const std::map &headers, bool ignoreSslErrors = false) + - std::future putRequest(const std::string &url, const std::string &payload, bool returnAsBinary, const std::map &headers, bool ignoreSslErrors = false) - deleteRequest - std::future deleteRequest(const std::string &url) - - std::future deleteRequest(const std::string &url, const std::string &payload) - - std::future deleteRequest(const std::string &url, bool returnAsBinary) - - std::future deleteRequest(const std::string &url, const std::map &headers) - - std::future deleteRequest(const std::string &url, const std::string &payload, bool returnAsBinary) - - std::future deleteRequest(const std::string &url, const std::string &payload, const std::map &headers) - - std::future deleteRequest(const std::string &url, bool returnAsBinary, const std::map &headers) - - std::future deleteRequest(const std::string &url, const std::string &payload, bool returnAsBinary, const std::map &headers) + - std::future deleteRequest(const std::string &url, const std::string &payload, bool ignoreSslErrors = false) + - std::future deleteRequest(const std::string &url, bool returnAsBinary, bool ignoreSslErrors = false) + - std::future deleteRequest(const std::string &url, const std::map &headers, bool ignoreSslErrors = false) + - std::future deleteRequest(const std::string &url, const std::string &payload, bool returnAsBinary, bool ignoreSslErrors = false) + - std::future deleteRequest(const std::string &url, const std::string &payload, const std::map &headers, bool ignoreSslErrors = false) + - std::future deleteRequest(const std::string &url, bool returnAsBinary, const std::map &headers, bool ignoreSslErrors = false) + - std::future deleteRequest(const std::string &url, const std::string &payload, bool returnAsBinary, const std::map &headers, bool ignoreSslErrors = false) - patchRequest - std::future patchRequest(const std::string &url) - - std::future patchRequest(const std::string &url, bool returnAsBinary) - - std::future patchRequest(const std::string &url, const std::map &headers) - - std::future patchRequest(const std::string &url, bool returnAsBinary, const std::map &headers) + - std::future patchRequest(const std::string &url, bool returnAsBinary, bool ignoreSslErrors = false) + - std::future patchRequest(const std::string &url, const std::map &headers, bool ignoreSslErrors = false) + - std::future patchRequest(const std::string &url, bool returnAsBinary, const std::map &headers, bool ignoreSslErrors = false) ``` diff --git a/examples/main.cpp b/examples/main.cpp index fa524f4..b00272c 100644 --- a/examples/main.cpp +++ b/examples/main.cpp @@ -160,6 +160,20 @@ void simplePatch() { std::cout << "Data: " << response.textData << std::endl; } +void ignoreSslErrors() { + + HttpClient httpClient; + + // If you need to ignore SSL errors, you can set the "ignoreSslErrors" field to true + httpClient.ignoreSslErrors = true; + + auto response = httpClient.getRequest("https://self-signed-cert.httpbun.com").get(); + + std::cout << "Succeed: " << response.succeed << std::endl; + std::cout << "Http Status Code: " << response.statusCode << std::endl; + std::cout << "Data: " << response.textData << std::endl; +} + int main() { @@ -183,5 +197,7 @@ int main() { simplePatch(); + ignoreSslErrors(); + return 0; } \ No newline at end of file diff --git a/src/libcpp-http-client.hpp b/src/libcpp-http-client.hpp index a4b9e90..f2799df 100644 --- a/src/libcpp-http-client.hpp +++ b/src/libcpp-http-client.hpp @@ -1,7 +1,7 @@ /* Modern non-blocking HTTP Client library for C++ (17+) -version 1.0.0 +version 1.1.0 https://github.com/lk-libs/libcpp-http-client If you encounter any issues, please submit a ticket at https://github.com/lk-libs/libcpp-http-client/issues @@ -91,6 +91,11 @@ namespace lklibs { curl_global_cleanup(); } + /** + * @brief Ignore SSL errors when making HTTP requests + */ + bool ignoreSslErrors = false; + /** * @brief Makes an HTTP GET request for the given URL and returns the result * @@ -106,7 +111,7 @@ namespace lklibs { * @brief Makes an HTTP GET request for the given URL and returns the result * * @param url: Request URL - * @param returnAsBinary: Return result as binary instead of string (Optional) + * @param returnAsBinary: Return result as binary instead of string * @return Result of the request (see HttpResult object for details) */ std::future getRequest(const std::string &url, bool returnAsBinary) noexcept { @@ -118,7 +123,7 @@ namespace lklibs { * @brief Makes an HTTP GET request for the given URL and returns the result * * @param url: Request URL - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future getRequest(const std::string &url, const std::map &headers) noexcept { @@ -130,8 +135,8 @@ namespace lklibs { * @brief Makes an HTTP GET request for the given URL and returns the result * * @param url: Request URL - * @param returnAsBinary: Return result as binary instead of string (Optional) - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param returnAsBinary: Return result as binary instead of string + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future getRequest(const std::string &url, bool returnAsBinary, const std::map &headers) noexcept { @@ -155,7 +160,7 @@ namespace lklibs { * @brief Makes an HTTP POST request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) + * @param payload: Payload to be sent with the request * @return Result of the request (see HttpResult object for details) */ std::future postRequest(const std::string &url, const std::string &payload) noexcept { @@ -167,7 +172,7 @@ namespace lklibs { * @brief Makes an HTTP POST request for the given URL and returns the result * * @param url: Request URL - * @param returnAsBinary: Return result as binary instead of string (Optional) + * @param returnAsBinary: Return result as binary instead of string * @return Result of the request (see HttpResult object for details) */ std::future postRequest(const std::string &url, bool returnAsBinary) noexcept { @@ -179,7 +184,7 @@ namespace lklibs { * @brief Makes an HTTP POST request for the given URL and returns the result * * @param url: Request URL - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future postRequest(const std::string &url, const std::map &headers) noexcept { @@ -191,8 +196,8 @@ namespace lklibs { * @brief Makes an HTTP POST request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) - * @param returnAsBinary: Return result as binary instead of string (Optional) + * @param payload: Payload to be sent with the request + * @param returnAsBinary: Return result as binary instead of string * @return Result of the request (see HttpResult object for details) */ std::future postRequest(const std::string &url, const std::string &payload, bool returnAsBinary) noexcept { @@ -204,8 +209,8 @@ namespace lklibs { * @brief Makes an HTTP POST request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param payload: Payload to be sent with the request + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future postRequest(const std::string &url, const std::string &payload, const std::map &headers) noexcept { @@ -217,8 +222,8 @@ namespace lklibs { * @brief Makes an HTTP POST request for the given URL and returns the result * * @param url: Request URL - * @param returnAsBinary: Return result as binary instead of string (Optional) - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param returnAsBinary: Return result as binary instead of string + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future postRequest(const std::string &url, bool returnAsBinary, const std::map &headers) noexcept { @@ -230,9 +235,9 @@ namespace lklibs { * @brief Makes an HTTP POST request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) - * @param returnAsBinary: Return result as binary instead of string (Optional) - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param payload: Payload to be sent with the request + * @param returnAsBinary: Return result as binary instead of string + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future postRequest(const std::string &url, const std::string &payload, bool returnAsBinary, const std::map &headers) noexcept { @@ -256,7 +261,7 @@ namespace lklibs { * @brief Makes an HTTP PUT request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) + * @param payload: Payload to be sent with the request * @return Result of the request (see HttpResult object for details) */ std::future putRequest(const std::string &url, const std::string &payload) noexcept { @@ -268,7 +273,7 @@ namespace lklibs { * @brief Makes an HTTP PUT request for the given URL and returns the result * * @param url: Request URL - * @param returnAsBinary: Return result as binary instead of string (Optional) + * @param returnAsBinary: Return result as binary instead of string * @return Result of the request (see HttpResult object for details) */ std::future putRequest(const std::string &url, bool returnAsBinary) noexcept { @@ -280,7 +285,7 @@ namespace lklibs { * @brief Makes an HTTP PUT request for the given URL and returns the result * * @param url: Request URL - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future putRequest(const std::string &url, const std::map &headers) noexcept { @@ -292,8 +297,8 @@ namespace lklibs { * @brief Makes an HTTP PUT request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) - * @param returnAsBinary: Return result as binary instead of string (Optional) + * @param payload: Payload to be sent with the request + * @param returnAsBinary: Return result as binary instead of string * @return Result of the request (see HttpResult object for details) */ std::future putRequest(const std::string &url, const std::string &payload, bool returnAsBinary) noexcept { @@ -305,8 +310,8 @@ namespace lklibs { * @brief Makes an HTTP PUT request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param payload: Payload to be sent with the request + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future putRequest(const std::string &url, const std::string &payload, const std::map &headers) noexcept { @@ -318,8 +323,8 @@ namespace lklibs { * @brief Makes an HTTP PUT request for the given URL and returns the result * * @param url: Request URL - * @param returnAsBinary: Return result as binary instead of string (Optional) - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param returnAsBinary: Return result as binary instead of string + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future putRequest(const std::string &url, bool returnAsBinary, const std::map &headers) noexcept { @@ -331,9 +336,9 @@ namespace lklibs { * @brief Makes an HTTP PUT request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) - * @param returnAsBinary: Return result as binary instead of string (Optional) - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param payload: Payload to be sent with the request + * @param returnAsBinary: Return result as binary instead of string + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future putRequest(const std::string &url, const std::string &payload, bool returnAsBinary, const std::map &headers) noexcept { @@ -357,7 +362,7 @@ namespace lklibs { * @brief Makes an HTTP DELETE request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) + * @param payload: Payload to be sent with the request * @return Result of the request (see HttpResult object for details) */ std::future deleteRequest(const std::string &url, const std::string &payload) noexcept { @@ -369,7 +374,7 @@ namespace lklibs { * @brief Makes an HTTP DELETE request for the given URL and returns the result * * @param url: Request URL - * @param returnAsBinary: Return result as binary instead of string (Optional) + * @param returnAsBinary: Return result as binary instead of string * @return Result of the request (see HttpResult object for details) */ std::future deleteRequest(const std::string &url, bool returnAsBinary) noexcept { @@ -381,7 +386,7 @@ namespace lklibs { * @brief Makes an HTTP DELETE request for the given URL and returns the result * * @param url: Request URL - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future deleteRequest(const std::string &url, const std::map &headers) noexcept { @@ -393,8 +398,8 @@ namespace lklibs { * @brief Makes an HTTP DELETE request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) - * @param returnAsBinary: Return result as binary instead of string (Optional) + * @param payload: Payload to be sent with the request + * @param returnAsBinary: Return result as binary instead of string * @return Result of the request (see HttpResult object for details) */ std::future deleteRequest(const std::string &url, const std::string &payload, bool returnAsBinary) noexcept { @@ -406,8 +411,8 @@ namespace lklibs { * @brief Makes an HTTP DELETE request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param payload: Payload to be sent with the request + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future deleteRequest(const std::string &url, const std::string &payload, const std::map &headers) noexcept { @@ -419,8 +424,8 @@ namespace lklibs { * @brief Makes an HTTP DELETE request for the given URL and returns the result * * @param url: Request URL - * @param returnAsBinary: Return result as binary instead of string (Optional) - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param returnAsBinary: Return result as binary instead of string + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future deleteRequest(const std::string &url, bool returnAsBinary, const std::map &headers) noexcept { @@ -432,9 +437,9 @@ namespace lklibs { * @brief Makes an HTTP DELETE request for the given URL and returns the result * * @param url: Request URL - * @param payload: Payload to be sent with the request (Optional) - * @param returnAsBinary: Return result as binary instead of string (Optional) - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param payload: Payload to be sent with the request + * @param returnAsBinary: Return result as binary instead of string + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future deleteRequest(const std::string &url, const std::string &payload, bool returnAsBinary, const std::map &headers) noexcept { @@ -458,7 +463,7 @@ namespace lklibs { * @brief Makes an HTTP PATCH request for the given URL and returns the result * * @param url: Request URL - * @param returnAsBinary: Return result as binary instead of string (Optional) + * @param returnAsBinary: Return result as binary instead of string * @return Result of the request (see HttpResult object for details) */ std::future patchRequest(const std::string &url, bool returnAsBinary) noexcept { @@ -470,7 +475,7 @@ namespace lklibs { * @brief Makes an HTTP PATCH request for the given URL and returns the result * * @param url: Request URL - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future patchRequest(const std::string &url, const std::map &headers) noexcept { @@ -482,8 +487,8 @@ namespace lklibs { * @brief Makes an HTTP PATCH request for the given URL and returns the result * * @param url: Request URL - * @param returnAsBinary: Return result as binary instead of string (Optional) - * @param headers: HTTP Header information to be sent when making the request (Optional) + * @param returnAsBinary: Return result as binary instead of string + * @param headers: HTTP Header information to be sent when making the request * @return Result of the request (see HttpResult object for details) */ std::future patchRequest(const std::string &url, bool returnAsBinary, const std::map &headers) noexcept { @@ -517,7 +522,7 @@ namespace lklibs { std::future request(const std::string &url, const std::string &method, const std::string &payload, bool returnAsBinary, const std::map &headers) { - return std::async(std::launch::async, [url, method, payload, returnAsBinary, headers]() -> HttpResult { + return std::async(std::launch::async, [this, url, method, payload, returnAsBinary, headers]() -> HttpResult { std::unique_ptr curl(curl_easy_init()); @@ -542,6 +547,8 @@ namespace lklibs { curl_easy_setopt(curl.get(), CURLOPT_HTTPHEADER, headerList.get()); curl_easy_setopt(curl.get(), CURLOPT_URL, url.c_str()); curl_easy_setopt(curl.get(), CURLOPT_CUSTOMREQUEST, method.c_str()); + curl_easy_setopt(curl.get(), CURLOPT_SSL_VERIFYPEER, this->ignoreSslErrors ? 0L : 1L); + curl_easy_setopt(curl.get(), CURLOPT_SSL_VERIFYHOST, this->ignoreSslErrors ? 0L : 1L); if (!payload.empty()) { diff --git a/test/test.cpp b/test/test.cpp index b948912..bbc9823 100644 --- a/test/test.cpp +++ b/test/test.cpp @@ -677,6 +677,32 @@ TEST(HttpPatchTest, HttpHeadersCanBeSentWithTheHttpPatchRequest) { ASSERT_EQ(data["headers"]["Custom-Header2"], "value2") << "Custom-Header2 is invalid"; } +TEST(InvalidSSLTest, HttpGetRequestMustReturnErrorForAnInvalidSsl) { + + HttpClient httpClient; + + auto response = httpClient.getRequest("https://self-signed-cert.httpbun.com").get(); + + ASSERT_FALSE(response.succeed) << "HTTP Request failed"; + ASSERT_EQ(response.statusCode, 0) << "HTTP Status Code is not 0"; + ASSERT_EQ(response.errorMessage, "SSL peer certificate or SSH remote key was not OK") << "HTTP Error Message is invalid"; +} + +TEST(InvalidSSLTest, HttpGetRequestMustBeCompletedSuccessfullyForAnInvalidSslIfIgnoreSslErrorsFieldSetTrue) { + + HttpClient httpClient; + + httpClient.ignoreSslErrors = true; + + auto response = httpClient.getRequest("https://self-signed-cert.httpbun.com").get(); + + ASSERT_TRUE(response.succeed) << "HTTP Request failed"; + ASSERT_EQ(response.statusCode, 200) << "HTTP Status Code is not 200"; + ASSERT_FALSE(response.textData.empty()) << "HTTP Response is empty"; + ASSERT_TRUE(response.binaryData.empty()) << "Binary data is not empty"; + ASSERT_TRUE(response.errorMessage.empty()) << "HTTP Error Message is not empty"; +} + int main(int argc, char** argv) { testing::InitGoogleTest(&argc, argv);