static SignatureParams parse_signature_params()

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;
    }