2#ifndef _KURLYK_UTILS_HTTP_PARSER_HPP_INCLUDED
3#define _KURLYK_UTILS_HTTP_PARSER_HPP_INCLUDED
20 std::string header(buffer, size);
21 if (header.size() < 3)
return;
22 std::size_t colon_pos = header.find_first_of(
":");
23 std::size_t start_pos = colon_pos + 1;
24 if (colon_pos == std::string::npos || colon_pos == 0)
return;
25 key = header.substr(0, colon_pos);
26 std::size_t end_pos = header.find_first_not_of(
" ", start_pos);
27 value = (end_pos != std::string::npos) ? header.substr(end_pos) : std::string();
30 while (!value.empty() && (value.back() ==
'\r' || value.back() ==
'\n')) {
35# ifdef KURLYK_USE_CURL
43 const std::string &prefix = std::string()) noexcept {
44 if (query.empty())
return std::string();
45 std::string query_string(prefix);
46 CURL *curl = curl_easy_init();
47 if (!curl)
return query_string;
50 const size_t index_end = query.size() - 1;
51 for(
const auto& pair : query) {
52 char *escaped_key = curl_easy_escape(curl, pair.first.c_str(), pair.first.size());
54 query_string += std::string(escaped_key);
55 curl_free(escaped_key);
58 char *escaped_value = curl_easy_escape(curl, pair.second.c_str(), pair.second.size());
60 query_string += std::string(escaped_value);
61 curl_free(escaped_value);
63 if (index != index_end) query_string +=
"&";
66 curl_easy_cleanup(curl);
78 const std::string &prefix = std::string()) noexcept {
79 std::string result(prefix);
82 for (
const auto &field : query) {
101 for (
auto it = cookies.begin(); it != cookies.end(); ++it) {
102 if (it != cookies.begin()) {
105 result += it->first +
"=" + it->second;
117 for (
auto it = cookies.begin(); it != cookies.end(); ++it) {
118 if (it != cookies.begin()) {
121 result += it->second.name +
"=" + it->second.value;
123 if (!it->second.path.empty()) {
124 result +=
"; Path=" + it->second.path;
127 if (it->second.expiration_date != 0) {
128 result +=
"; Expires=" + std::to_string(it->second.expiration_date);
140 std::vector<std::string> list_fragment;
142 const std::string secure_prefix(
"__Secure-");
143 const std::string host_prefix(
"__Host-");
144 std::size_t start_pos = 0;
147 bool is_option =
false;
148 std::size_t separator_pos = cookie.find_first_of(
"=;", start_pos);
149 if (separator_pos != std::string::npos) {
150 std::string name = cookie.substr(start_pos, (separator_pos - start_pos));
152 if (name.size() > host_prefix.size() && name.substr(0, 2) ==
"__") {
153 std::size_t prefix_pos = name.find_first_of(
"-");
154 if(prefix_pos != std::string::npos) {
155 name = name.substr(prefix_pos + 1, name.size() - prefix_pos - 1);
166 start_pos = (cookie[separator_pos] ==
';') ? separator_pos + 2 : separator_pos + 1;
171 std::size_t end_pos = cookie.find(
"; ", separator_pos + 1);
172 if (end_pos == std::string::npos) {
173 std::string value = cookie.substr(separator_pos + 1, cookie.size() - separator_pos - 2);
174 Cookie cookie_obj{name, value};
175 if (!is_option) cookies.emplace(cookie_obj.name, cookie_obj);
178 std::string value = cookie.substr(separator_pos + 1, end_pos - separator_pos - 1);
179 start_pos = end_pos + 2;
180 Cookie cookie_obj{name, value};
181 if (!is_option) cookies.emplace(cookie_obj.name, cookie_obj);
Represents an HTTP cookie.
std::unordered_multimap< std::string, std::string, CaseInsensitiveHash, CaseInsensitiveEqual > CaseInsensitiveMultimap
A case-insensitive unordered multimap for storing HTTP headers.
bool case_insensitive_equal(const std::string &str1, const std::string &str2) noexcept
Compares two strings case-insensitively.
std::string to_cookie_string(const CaseInsensitiveMultimap &cookies)
Converts a CaseInsensitiveMultimap to a string format suitable for HTTP Cookie headers.
void parse_http_header_pair(const char *buffer, const size_t &size, std::string &key, std::string &value)
Parses a header pair from a buffer.
std::string to_query_string(const QueryParams &query, const std::string &prefix=std::string()) noexcept
Converts a map of query parameters into a URL query string.
Cookies parse_cookie(std::string cookie)
Parses a cookie string into a Cookies object.
std::string percent_encode(const std::string &value) noexcept
Encodes a string using Percent Encoding according to RFC 3986.
utils::CaseInsensitiveCookieMultimap Cookies
Alias for HTTP cookies, stored case-insensitively.
utils::CaseInsensitiveMultimap QueryParams
Alias for query parameters in HTTP requests, stored case-insensitively.