mirror of
https://github.com/matrix-construct/construct
synced 2024-06-02 18:18:56 +02:00
ircd::http: Elaborate the query string interface with indexing.
This commit is contained in:
parent
654901d7df
commit
6af4782922
|
@ -142,10 +142,17 @@ struct ircd::http::query::string
|
|||
using closure = std::function<bool (const query &)>;
|
||||
|
||||
bool for_each(const closure &) const;
|
||||
string_view at(const string_view &key) const;
|
||||
bool for_each(const string_view &key, const closure &) const;
|
||||
|
||||
string_view _get(const string_view &key, size_t idx = 0) const;
|
||||
template<class T = string_view> T get(const string_view &key, const T &def = {}, const size_t &idx = 0) const;
|
||||
string_view operator[](const string_view &key) const;
|
||||
template<class T> T at(const string_view &key) const;
|
||||
template<class T = string_view> T get(const string_view &key, const T &def = {}) const;
|
||||
|
||||
string_view at(const string_view &key, const size_t &idx = 0) const;
|
||||
template<class T> T at(const string_view &key, const size_t &idx = 0) const;
|
||||
|
||||
size_t count(const string_view &key) const;
|
||||
bool has(const string_view &key) const;
|
||||
|
||||
using string_view::string_view;
|
||||
};
|
||||
|
@ -336,10 +343,11 @@ enum ircd::http::code
|
|||
template<class T>
|
||||
T
|
||||
ircd::http::query::string::get(const string_view &key,
|
||||
const T &def)
|
||||
const T &def,
|
||||
const size_t &idx)
|
||||
const try
|
||||
{
|
||||
const auto val(operator[](key));
|
||||
const auto val(_get(key, idx));
|
||||
return val? lex_cast<T>(val) : def;
|
||||
}
|
||||
catch(const bad_lex_cast &)
|
||||
|
@ -349,10 +357,11 @@ catch(const bad_lex_cast &)
|
|||
|
||||
template<class T>
|
||||
T
|
||||
ircd::http::query::string::at(const string_view &key)
|
||||
ircd::http::query::string::at(const string_view &key,
|
||||
const size_t &idx)
|
||||
const
|
||||
{
|
||||
return lex_cast<T>(at(key));
|
||||
return lex_cast<T>(at(key, idx));
|
||||
}
|
||||
|
||||
template<size_t BUFSIZE,
|
||||
|
|
98
ircd/http.cc
98
ircd/http.cc
|
@ -698,17 +698,58 @@ ircd::http::line::line(parse::capstan &pc)
|
|||
{
|
||||
}
|
||||
|
||||
ircd::string_view
|
||||
ircd::http::query::string::at(const string_view &key)
|
||||
//
|
||||
// query::string
|
||||
//
|
||||
|
||||
bool
|
||||
ircd::http::query::string::has(const string_view &key)
|
||||
const
|
||||
{
|
||||
const auto ret(operator[](key));
|
||||
if(ret.empty())
|
||||
bool ret{false};
|
||||
for_each(key, [&ret]
|
||||
(const auto &)
|
||||
{
|
||||
ret = true;
|
||||
return false;
|
||||
});
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
size_t
|
||||
ircd::http::query::string::count(const string_view &key)
|
||||
const
|
||||
{
|
||||
size_t ret{0};
|
||||
for_each(key, [&ret]
|
||||
(const auto &)
|
||||
{
|
||||
++ret;
|
||||
return true;
|
||||
});
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
ircd::string_view
|
||||
ircd::http::query::string::at(const string_view &key,
|
||||
const size_t &idx)
|
||||
const
|
||||
{
|
||||
const string_view &ret
|
||||
{
|
||||
_get(key, idx)
|
||||
};
|
||||
|
||||
if(!ret)
|
||||
{
|
||||
thread_local char buf[1024];
|
||||
const string_view msg{fmt::sprintf
|
||||
{
|
||||
buf, "Failed to find value for required query string key '%s'", key
|
||||
buf, "Failed to find value for required query string key '%s' #%zu.",
|
||||
key,
|
||||
idx
|
||||
}};
|
||||
|
||||
throw std::out_of_range
|
||||
|
@ -723,20 +764,43 @@ const
|
|||
ircd::string_view
|
||||
ircd::http::query::string::operator[](const string_view &key)
|
||||
const
|
||||
{
|
||||
return _get(key, 0);
|
||||
}
|
||||
|
||||
ircd::string_view
|
||||
ircd::http::query::string::_get(const string_view &key,
|
||||
size_t idx)
|
||||
const
|
||||
{
|
||||
string_view ret;
|
||||
const auto match{[&key, &ret]
|
||||
(const query &query) -> bool
|
||||
for_each(key, [&idx, &ret]
|
||||
(const auto &query)
|
||||
{
|
||||
if(!idx--)
|
||||
{
|
||||
ret = query.second;
|
||||
return false;
|
||||
}
|
||||
else return true;
|
||||
});
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
bool
|
||||
ircd::http::query::string::for_each(const string_view &key,
|
||||
const closure &closure)
|
||||
const
|
||||
{
|
||||
return for_each([&key, &closure]
|
||||
(const auto &query)
|
||||
{
|
||||
if(query.first != key)
|
||||
return true;
|
||||
|
||||
ret = query.second;
|
||||
return false; // false to break out of for_each()
|
||||
}};
|
||||
|
||||
for_each(match);
|
||||
return ret;
|
||||
return closure(query);
|
||||
});
|
||||
}
|
||||
|
||||
bool
|
||||
|
@ -759,6 +823,10 @@ const
|
|||
return qi::parse(start, stop, grammar);
|
||||
}
|
||||
|
||||
//
|
||||
// parser util
|
||||
//
|
||||
|
||||
size_t
|
||||
ircd::http::parser::content_length(const string_view &str)
|
||||
{
|
||||
|
@ -779,6 +847,10 @@ ircd::http::parser::content_length(const string_view &str)
|
|||
return ret;
|
||||
}
|
||||
|
||||
//
|
||||
// util
|
||||
//
|
||||
|
||||
ircd::const_buffer
|
||||
ircd::http::writechunk(const mutable_buffer &buf,
|
||||
const uint32_t &chunk_size)
|
||||
|
|
Loading…
Reference in a new issue