in src/http/http_sig.h [240:339]
static SignatureParams parse_signature_params(
std::string_view& auth_header_value)
{
SignatureParams sig_params = {};
auto parsed_params =
parse_delimited_string(auth_header_value, auth::SIGN_PARAMS_DELIMITER);
for (auto& p : parsed_params)
{
auto eq_pos = p.find("=");
if (eq_pos != std::string::npos)
{
auto k = p.substr(0, eq_pos);
auto v = p.substr(eq_pos + 1);
// Remove quotes around value, if present
const bool begins_with_quote = v.front() == '"';
const bool ends_with_quote = v.back() == '"';
if (v.size() >= 2 && (begins_with_quote || ends_with_quote))
{
if (!(begins_with_quote && ends_with_quote))
{
throw std::logic_error(fmt::format(
"Unbalanced quotes in '{}' header: {}",
headers::AUTHORIZATION,
p));
}
v = v.substr(1, v.size() - 2);
}
if (k == auth::SIGN_PARAMS_KEYID)
{
sig_params.key_id = v;
}
else if (k == auth::SIGN_PARAMS_ALGORITHM)
{
sig_params.signature_algorithm = v;
if (
v != auth::SIGN_ALGORITHM_ECDSA_SHA256 &&
v != auth::SIGN_ALGORITHM_HS_2019)
{
throw std::logic_error(
fmt::format("Signature algorithm '{}' is not supported", v));
}
}
else if (k == auth::SIGN_PARAMS_SIGNATURE)
{
sig_params.signature = v;
}
else if (k == auth::SIGN_PARAMS_HEADERS)
{
auto parsed_signed_headers =
parse_delimited_string(v, auth::SIGN_PARAMS_HEADERS_DELIMITER);
if (parsed_signed_headers.size() == 0)
{
throw std::logic_error(fmt::format(
"No headers specified in '{}' field",
auth::SIGN_PARAMS_HEADERS));
}
for (const auto& h : parsed_signed_headers)
{
sig_params.signed_headers.emplace_back(h);
}
}
}
else
{
throw std::logic_error(fmt::format(
"authorization parameter '{}' does not contain \"=\"", p));
}
}
// If any sig params were not found, this is invalid
if (sig_params.key_id.empty())
{
throw std::logic_error(fmt::format(
"Signature params: Missing '{}'", auth::SIGN_PARAMS_KEYID));
}
if (sig_params.signature_algorithm.empty())
{
throw std::logic_error(fmt::format(
"Signature params: Missing '{}'", auth::SIGN_PARAMS_ALGORITHM));
}
if (sig_params.signature.empty())
{
throw std::logic_error(fmt::format(
"Signature params: Missing '{}'", auth::SIGN_PARAMS_SIGNATURE));
}
if (sig_params.signed_headers.empty())
{
throw std::logic_error(fmt::format(
"Signature params: Missing '{}'", auth::SIGN_PARAMS_HEADERS));
}
return sig_params;
}