feat: formatting error messages improved

This commit is contained in:
Mateusz Pusz
2024-01-23 21:19:45 +01:00
parent dbd3bd07f1
commit 4e88298ce3
2 changed files with 19 additions and 12 deletions

View File

@@ -256,19 +256,24 @@ template<typename Char, typename Handler>
[[nodiscard]] constexpr const Char* parse_subentity_replacement_field(const Char* begin, const Char* end,
Handler&& handler)
{
if (end - begin++ < 4) return MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("invalid format string")), end;
if (*begin++ != '%') MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("invalid format"));
if (*begin == '}') MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("invalid format"));
if (end - begin++ < 4)
return MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("`subentity-replacement-field` too short")), end;
if (*begin++ != '%')
MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("`subentity-replacement-field` should start with '%'"));
if (*begin == '}')
MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("`subentity-replacement-field` should have an identifier"));
auto it = begin;
for (; it != end; ++it) {
if (*it == '{' || *it == '%') MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("invalid format"));
if (*it == '{' || *it == '%')
MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("invalid `subentity-replacement-field` format"));
if (*it == '}' || *it == ':') break;
}
if (it == end) MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("invalid format"));
if (it == end) MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("`subentity-replacement-field` too short"));
std::string_view id{begin, it};
if (*it == ':') ++it;
it = handler.on_replacement_field(id, it);
if (it == end || *it != '}') MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("invalid format"));
if (it == end || *it != '}')
MP_UNITS_THROW(MP_UNITS_STD_FMT::format_error("`subentity-replacement-field` should end with '}'"));
return ++it;
}

View File

@@ -265,7 +265,7 @@ class MP_UNITS_STD_FMT::formatter<mp_units::quantity<Reference, Rep>, Char> {
return begin;
// on_replacement_field<dimension_t>(begin);
} else
throw MP_UNITS_STD_FMT::format_error("invalid format");
throw MP_UNITS_STD_FMT::format_error("unknown replacement field '" + std::string(id) + "'");
}
private:
@@ -275,7 +275,7 @@ class MP_UNITS_STD_FMT::formatter<mp_units::quantity<Reference, Rep>, Char> {
MP_UNITS_STD_FMT::formatter<T> sf;
ctx.advance_to(begin);
auto ptr = sf.parse(ctx);
if (*ptr != '}') throw MP_UNITS_STD_FMT::format_error("invalid format");
if (*ptr != '}') throw MP_UNITS_STD_FMT::format_error("unmatched '}' in format string");
format_str_lengths.push_back(mp_units::detail::to_unsigned(ptr - begin));
return ptr;
}
@@ -314,7 +314,7 @@ class MP_UNITS_STD_FMT::formatter<mp_units::quantity<Reference, Rep>, Char> {
else if (id == "D")
on_dimension(format_str());
else
throw MP_UNITS_STD_FMT::format_error("invalid format");
throw MP_UNITS_STD_FMT::format_error("unknown replacement field '" + std::string(id) + "'");
return begin + *format_str_lengths_it++;
}
};
@@ -325,7 +325,9 @@ class MP_UNITS_STD_FMT::formatter<mp_units::quantity<Reference, Rep>, Char> {
constexpr const Char* parse_quantity_specs(const Char* begin, const Char* end, Handler&& handler) const
{
if (begin == end || *begin == '}') return begin;
if (*begin != '%' && *begin != '{') throw MP_UNITS_STD_FMT::format_error("invalid format");
if (*begin != '%' && *begin != '{')
throw MP_UNITS_STD_FMT::format_error(
"`quantity-specs` should start with a `conversion-spec` ('%' or '{' characters expected)})");
auto ptr = begin;
while (ptr != end) {
auto c = *ptr;
@@ -341,7 +343,7 @@ class MP_UNITS_STD_FMT::formatter<mp_units::quantity<Reference, Rep>, Char> {
}
if (begin != ptr) handler.on_text(begin, ptr);
++ptr; // consume '%'
if (ptr == end) throw MP_UNITS_STD_FMT::format_error("invalid format");
if (ptr == end) throw MP_UNITS_STD_FMT::format_error("invalid `placement-spec` format");
c = *ptr++;
switch (c) {
@@ -361,7 +363,7 @@ class MP_UNITS_STD_FMT::formatter<mp_units::quantity<Reference, Rep>, Char> {
handler.on_text(ptr - 1, ptr);
break;
default:
throw MP_UNITS_STD_FMT::format_error("invalid format");
throw MP_UNITS_STD_FMT::format_error(std::string("unknown `placement-spec` token '") + c + "'");
}
begin = ptr;
}