can specify extra headers
This commit is contained in:
		| @@ -36,6 +36,7 @@ namespace ix | |||||||
|     HttpResponse HttpClient::request( |     HttpResponse HttpClient::request( | ||||||
|         const std::string& url, |         const std::string& url, | ||||||
|         const std::string& verb, |         const std::string& verb, | ||||||
|  |         const WebSocketHttpHeaders& extraHeaders, | ||||||
|         const HttpParameters& httpParameters, |         const HttpParameters& httpParameters, | ||||||
|         bool verbose) |         bool verbose) | ||||||
|     { |     { | ||||||
| @@ -98,6 +99,12 @@ namespace ix | |||||||
|         ss << "Host: " << host << "\r\n"; |         ss << "Host: " << host << "\r\n"; | ||||||
|         ss << "User-Agent: ixwebsocket/1.0.0" << "\r\n"; |         ss << "User-Agent: ixwebsocket/1.0.0" << "\r\n"; | ||||||
|         ss << "Accept: */*" << "\r\n"; |         ss << "Accept: */*" << "\r\n"; | ||||||
|  |  | ||||||
|  |         for (auto&& it : extraHeaders) | ||||||
|  |         { | ||||||
|  |             ss << it.first << ": " << urlEncode(it.second) << "\r\n"; | ||||||
|  |         } | ||||||
|  |  | ||||||
|         if (verb == "POST") |         if (verb == "POST") | ||||||
|         { |         { | ||||||
|             ss << "Content-Length: " << body.size() << "\r\n"; |             ss << "Content-Length: " << body.size() << "\r\n"; | ||||||
| @@ -196,7 +203,7 @@ namespace ix | |||||||
|  |  | ||||||
|         payload.reserve(contentLength); |         payload.reserve(contentLength); | ||||||
|  |  | ||||||
|         // very inefficient way to read bytes, but it works... |         // FIXME: very inefficient way to read bytes, but it works... | ||||||
|         for (int i = 0; i < contentLength; ++i) |         for (int i = 0; i < contentLength; ++i) | ||||||
|         { |         { | ||||||
|             char c; |             char c; | ||||||
| @@ -215,17 +222,19 @@ namespace ix | |||||||
|  |  | ||||||
|     HttpResponse HttpClient::get( |     HttpResponse HttpClient::get( | ||||||
|         const std::string& url, |         const std::string& url, | ||||||
|  |         const WebSocketHttpHeaders& extraHeaders, | ||||||
|         bool verbose) |         bool verbose) | ||||||
|     { |     { | ||||||
|         return request(url, "GET", HttpParameters(), verbose); |         return request(url, "GET", extraHeaders, HttpParameters(), verbose); | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     HttpResponse HttpClient::post( |     HttpResponse HttpClient::post( | ||||||
|         const std::string& url, |         const std::string& url, | ||||||
|  |         const WebSocketHttpHeaders& extraHeaders, | ||||||
|         const HttpParameters& httpParameters, |         const HttpParameters& httpParameters, | ||||||
|         bool verbose) |         bool verbose) | ||||||
|     { |     { | ||||||
|         return request(url, "POST", httpParameters, verbose); |         return request(url, "POST", extraHeaders, httpParameters, verbose); | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     std::string HttpClient::urlEncode(const std::string& value) |     std::string HttpClient::urlEncode(const std::string& value) | ||||||
| @@ -255,48 +264,3 @@ namespace ix | |||||||
|         return escaped.str(); |         return escaped.str(); | ||||||
|     } |     } | ||||||
| } | } | ||||||
|  |  | ||||||
| #if 0 |  | ||||||
|         std::vector<uint8_t> rxbuf; |  | ||||||
|  |  | ||||||
|         while (true) |  | ||||||
|         { |  | ||||||
|             int N = (int) _rxbuf.size(); |  | ||||||
|  |  | ||||||
|             _rxbuf.resize(N + 1500); |  | ||||||
|             ssize_t ret = _socket->recv((char*)&_rxbuf[0] + N, 1500); |  | ||||||
|  |  | ||||||
|             if (ret < 0 && (_socket->getErrno() == EWOULDBLOCK || |  | ||||||
|                             _socket->getErrno() == EAGAIN)) { |  | ||||||
|                 _rxbuf.resize(N); |  | ||||||
|                 break; |  | ||||||
|             } |  | ||||||
|             else if (ret <= 0) |  | ||||||
|             { |  | ||||||
|                 _rxbuf.resize(N); |  | ||||||
|  |  | ||||||
|                 _socket->close(); |  | ||||||
|                 setReadyState(CLOSED); |  | ||||||
|                 break; |  | ||||||
|             } |  | ||||||
|             else |  | ||||||
|             { |  | ||||||
|                 _rxbuf.resize(N + ret); |  | ||||||
|             } |  | ||||||
|         } |  | ||||||
|         ssize_t ret = _socket->recv((char*)&rxbuf[0], contentLength); |  | ||||||
|         payload = std::string(rxbuf.begin(), rxbuf.end()); |  | ||||||
|         std::cerr << "socket->recv: " << ret << std::endl; |  | ||||||
|  |  | ||||||
|         if (ret != contentLength) |  | ||||||
|         { |  | ||||||
|             ss.str(""); |  | ||||||
|             ss << "Cannot retrieve all bytes" |  | ||||||
|                << " want: " << contentLength |  | ||||||
|                << ", got: " << ret; |  | ||||||
|             std::cerr << "adscasdcadcasdc" << std::endl; |  | ||||||
|             std::cerr << ss.str() << std::endl; |  | ||||||
|  |  | ||||||
|             return std::make_tuple(-1, headers, payload, ss.str()); |  | ||||||
|         } |  | ||||||
| #endif |  | ||||||
|   | |||||||
| @@ -28,14 +28,18 @@ namespace ix | |||||||
|         ~HttpClient(); |         ~HttpClient(); | ||||||
|  |  | ||||||
|         // Static methods ? |         // Static methods ? | ||||||
|         HttpResponse get(const std::string& url, bool verbose); |         HttpResponse get(const std::string& url, | ||||||
|  |                          const WebSocketHttpHeaders& extraHeaders, | ||||||
|  |                          bool verbose); | ||||||
|         HttpResponse post(const std::string& url, |         HttpResponse post(const std::string& url, | ||||||
|  |                           const WebSocketHttpHeaders& extraHeaders, | ||||||
|                           const HttpParameters& httpParameters, |                           const HttpParameters& httpParameters, | ||||||
|                           bool verbose); |                           bool verbose); | ||||||
|  |  | ||||||
|     private: |     private: | ||||||
|         HttpResponse request(const std::string& url, |         HttpResponse request(const std::string& url, | ||||||
|                              const std::string& verb, |                              const std::string& verb, | ||||||
|  |                              const WebSocketHttpHeaders& extraHeaders, | ||||||
|                              const HttpParameters& httpParameters, |                              const HttpParameters& httpParameters, | ||||||
|                              bool verbose); |                              bool verbose); | ||||||
|  |  | ||||||
|   | |||||||
| @@ -18,6 +18,7 @@ | |||||||
| namespace ix | namespace ix | ||||||
| { | { | ||||||
|     int ws_http_client_main(const std::string& url, |     int ws_http_client_main(const std::string& url, | ||||||
|  |                             const std::string& headers, | ||||||
|                             const std::string& data); |                             const std::string& data); | ||||||
|  |  | ||||||
|     int ws_ping_pong_main(const std::string& url); |     int ws_ping_pong_main(const std::string& url); | ||||||
| @@ -49,6 +50,7 @@ int main(int argc, char** argv) | |||||||
|     std::string path; |     std::string path; | ||||||
|     std::string user; |     std::string user; | ||||||
|     std::string data; |     std::string data; | ||||||
|  |     std::string headers; | ||||||
|     int port = 8080; |     int port = 8080; | ||||||
|  |  | ||||||
|     CLI::App* sendApp = app.add_subcommand("send", "Send a file"); |     CLI::App* sendApp = app.add_subcommand("send", "Send a file"); | ||||||
| @@ -82,6 +84,7 @@ int main(int argc, char** argv) | |||||||
|     httpClientApp->add_option("url", url, "Connection url")->required(); |     httpClientApp->add_option("url", url, "Connection url")->required(); | ||||||
|     httpClientApp->add_option("-d", data, "Form data")->join(); |     httpClientApp->add_option("-d", data, "Form data")->join(); | ||||||
|     httpClientApp->add_option("-F", data, "Form data")->join(); |     httpClientApp->add_option("-F", data, "Form data")->join(); | ||||||
|  |     httpClientApp->add_option("-H", headers, "Header")->join(); | ||||||
|  |  | ||||||
|     CLI11_PARSE(app, argc, argv); |     CLI11_PARSE(app, argc, argv); | ||||||
|  |  | ||||||
| @@ -123,7 +126,7 @@ int main(int argc, char** argv) | |||||||
|     else if (app.got_subcommand("http_client")) |     else if (app.got_subcommand("http_client")) | ||||||
|     { |     { | ||||||
|         std::cout << "data: " << data << std::endl; |         std::cout << "data: " << data << std::endl; | ||||||
|         return ix::ws_http_client_main(url, data); |         return ix::ws_http_client_main(url, headers, data); | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     return 1; |     return 1; | ||||||
|   | |||||||
| @@ -7,9 +7,35 @@ | |||||||
| #include <iostream> | #include <iostream> | ||||||
| #include <sstream> | #include <sstream> | ||||||
| #include <ixwebsocket/IXHttpClient.h> | #include <ixwebsocket/IXHttpClient.h> | ||||||
|  | #include <ixwebsocket/IXWebSocketHttpHeaders.h> | ||||||
|  |  | ||||||
| namespace ix | namespace ix | ||||||
| { | { | ||||||
|  |     WebSocketHttpHeaders parseHeaders(const std::string& data) | ||||||
|  |     { | ||||||
|  |         WebSocketHttpHeaders headers; | ||||||
|  |  | ||||||
|  |         // Split by \n | ||||||
|  |         std::string token; | ||||||
|  |         std::stringstream tokenStream(data); | ||||||
|  |  | ||||||
|  |         while (std::getline(tokenStream, token)) | ||||||
|  |         { | ||||||
|  |             std::size_t pos = token.rfind(':'); | ||||||
|  |  | ||||||
|  |             // Bail out if last '.' is found | ||||||
|  |             if (pos == std::string::npos) continue; | ||||||
|  |  | ||||||
|  |             auto key = token.substr(0, pos); | ||||||
|  |             auto val = token.substr(pos+2); | ||||||
|  |  | ||||||
|  |             std::cout << key << ": " << val << std::endl; | ||||||
|  |             headers[key] = val; | ||||||
|  |         } | ||||||
|  |  | ||||||
|  |         return headers; | ||||||
|  |     } | ||||||
|  |  | ||||||
|     // |     // | ||||||
|     // Useful endpoint to test HTTP post |     // Useful endpoint to test HTTP post | ||||||
|     // https://postman-echo.com/post |     // https://postman-echo.com/post | ||||||
| @@ -18,7 +44,7 @@ namespace ix | |||||||
|     { |     { | ||||||
|         HttpParameters httpParameters; |         HttpParameters httpParameters; | ||||||
|  |  | ||||||
|         // Split by ; |         // Split by \n | ||||||
|         std::string token; |         std::string token; | ||||||
|         std::stringstream tokenStream(data); |         std::stringstream tokenStream(data); | ||||||
|  |  | ||||||
| @@ -40,27 +66,29 @@ namespace ix | |||||||
|     } |     } | ||||||
|  |  | ||||||
|     int ws_http_client_main(const std::string& url, |     int ws_http_client_main(const std::string& url, | ||||||
|  |                             const std::string& headersData, | ||||||
|                             const std::string& data) |                             const std::string& data) | ||||||
|     { |     { | ||||||
|         HttpParameters httpParameters = parsePostParameters(data); |         HttpParameters httpParameters = parsePostParameters(data); | ||||||
|  |         WebSocketHttpHeaders headers = parseHeaders(headersData); | ||||||
|  |  | ||||||
|         HttpClient httpClient; |         HttpClient httpClient; | ||||||
|         bool verbose = true; |         bool verbose = true; | ||||||
|         HttpResponse out; |         HttpResponse out; | ||||||
|         if (data.empty()) |         if (data.empty()) | ||||||
|         { |         { | ||||||
|             out = httpClient.get(url, verbose); |             out = httpClient.get(url, headers, verbose); | ||||||
|         } |         } | ||||||
|         else |         else | ||||||
|         { |         { | ||||||
|             out = httpClient.post(url, httpParameters, verbose); |             out = httpClient.post(url, headers, httpParameters, verbose); | ||||||
|         } |         } | ||||||
|         auto errorCode = std::get<0>(out); |         auto errorCode = std::get<0>(out); | ||||||
|         auto headers = std::get<1>(out); |         auto responseHeaders = std::get<1>(out); | ||||||
|         auto payload = std::get<2>(out); |         auto payload = std::get<2>(out); | ||||||
|         auto errorMsg = std::get<3>(out); |         auto errorMsg = std::get<3>(out); | ||||||
|  |  | ||||||
|         for (auto it : headers) |         for (auto it : responseHeaders) | ||||||
|         { |         { | ||||||
|             std::cout << it.first << ": " << it.second << std::endl; |             std::cout << it.first << ": " << it.second << std::endl; | ||||||
|         } |         } | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user