diff options
Diffstat (limited to 'src/httpclient.cpp')
-rw-r--r-- | src/httpclient.cpp | 129 |
1 files changed, 129 insertions, 0 deletions
diff --git a/src/httpclient.cpp b/src/httpclient.cpp new file mode 100644 index 0000000..730b310 --- /dev/null +++ b/src/httpclient.cpp @@ -0,0 +1,129 @@ +/* Copyright (C) 2022 The Qt Company Ltd. + * + * SPDX-License-Identifier: GPL-3.0-only WITH Qt-GPL-exception-1.0 +*/ + +#include "httpclient.h" + +size_t WriteCallback(char *contents, size_t size, size_t nmemb, void *userp) +{ + std::cout << "Reading data\n"; + ((std::string *)userp)->append(contents, size * nmemb); + return size * nmemb; +} + +HttpClient::HttpClient( const std::string &serverUrl, + const std::string &requestAccessPoint, + const std::string &longtermAccessPoint, + const std::string &versionAccessPoint) : + m_serverUrl(serverUrl), + m_requestAccessPoint(requestAccessPoint), + m_longtermAccessPoint(longtermAccessPoint), + m_versionAccessPoint(versionAccessPoint) +{ + m_userAgent += DAEMON_VERSION; +} + +int HttpClient::sendRequest(std::string &reply, const std::string &payload, + const std::string &server, const std::string &authKey) +{ + HttpRequest request; + m_lastError = "No errors"; + + /* specify URL to POST */ + request.url = server; + if (server.empty()) { + // If server URL is not given as param, we use the default + request.url = m_serverUrl; + } + if (!authKey.empty()) { + // normal request + request.url += m_requestAccessPoint; + } else { + if (payload.empty()) { + // version query + request.url += m_versionAccessPoint; + } else { + // long-term request + request.url += m_longtermAccessPoint; + } + } + request.authKey = authKey; + request.payload = payload; + + if (!request.authKey.empty()) { + // Set authorization only if applicable + std::string auth = "Authorization: " + request.authKey; + request.headers = curl_slist_append(request.headers, auth.c_str()); + } + std::string agent = "User-Agent: " + m_userAgent; + request.headers = curl_slist_append(request.headers, agent.c_str()); + request.headers = curl_slist_append(request.headers, "Accept: */*"); + request.headers = curl_slist_append(request.headers, "Content-Type: application/json"); + request.headers = curl_slist_append(request.headers, "charset: utf-8"); + + std::cout << "HTTPClient() -- server URL " << request.url << std::endl; + + int retVal = 0; + + /* init the curl session */ + curl_global_init(CURL_GLOBAL_ALL); + CURL *curl = curl_easy_init(); + try { + if (doRequest(curl, request) != 0) { + retVal = 1; + } + } catch(...) { + m_lastError = "Connection failed"; + retVal = 1; + } + if (retVal == 0) { + std::cout << request.reply.length() << " bytes retrieved from license server:\n"; + std::cout << request.reply << std::endl; + } else { + std::cout << m_lastError << std::endl; + } + + /* cleanup curl stuff */ + + curl_easy_cleanup(curl); + curl_global_cleanup(); + curl_slist_free_all(request.headers); + reply = request.reply; + return retVal; +} + +int HttpClient::doRequest(CURL *curl, HttpRequest &request) +{ + // Set all received data to be send to our callback function + curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, WriteCallback); + + std::string readBuffer; + // Pass the buffer to a callback + curl_easy_setopt(curl, CURLOPT_WRITEDATA, &readBuffer); + + // Set the URL / headers + curl_easy_setopt(curl, CURLOPT_URL, request.url.c_str()); + curl_easy_setopt(curl, CURLOPT_HTTPHEADER, request.headers); + if (!request.payload.empty()) { + curl_easy_setopt(curl, CURLOPT_POST, 1); + curl_easy_setopt(curl, CURLOPT_POSTFIELDS, request.payload.c_str()); + } + else { + curl_easy_setopt(curl, CURLOPT_HTTPGET, 1); + } + curl_easy_setopt(curl, CURLOPT_TIMEOUT, SERVER_CONN_TIMEOUT); + + // get it + CURLcode res; + res = curl_easy_perform(curl); + + // check for errors + if (res != CURLE_OK) { + std::cout << "HTTP transfer failed, URL: " << request.url << std::endl; + m_lastError = curl_easy_strerror(res); + return 1; + } + request.reply = readBuffer; + return 0; +} |