add support for better error messages
This includes extended error messages which show the original format string. It works for 'char' type with wchar_t returning only the message. The thrown exception class now has a format() method to retrieve the pointer to the original format.
This commit is contained in:
parent
225d4f7032
commit
62466cc3d9
27
format.cc
27
format.cc
@ -409,12 +409,14 @@ void fmt::BasicFormatter<Char>::CheckSign(const Char *&s, const Arg &arg) {
|
|||||||
|
|
||||||
template <typename Char>
|
template <typename Char>
|
||||||
void fmt::BasicFormatter<Char>::DoFormat() {
|
void fmt::BasicFormatter<Char>::DoFormat() {
|
||||||
const Char *start = format_;
|
const Char *start = format_; // capture the format string before it is reset
|
||||||
|
const Char *original = format_;
|
||||||
format_ = 0;
|
format_ = 0;
|
||||||
next_arg_index_ = 0;
|
next_arg_index_ = 0;
|
||||||
const Char *s = start;
|
const Char *s = start;
|
||||||
typedef internal::Array<Char, BasicWriter<Char>::INLINE_BUFFER_SIZE> Buffer;
|
typedef internal::Array<Char, BasicWriter<Char>::INLINE_BUFFER_SIZE> Buffer;
|
||||||
BasicWriter<Char> &writer = *writer_;
|
BasicWriter<Char> &writer = *writer_;
|
||||||
|
try {
|
||||||
while (*s) {
|
while (*s) {
|
||||||
Char c = *s++;
|
Char c = *s++;
|
||||||
if (c != '{' && c != '}') continue;
|
if (c != '{' && c != '}') continue;
|
||||||
@ -644,6 +646,11 @@ void fmt::BasicFormatter<Char>::DoFormat() {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
} catch (const FormatError &e) {
|
||||||
|
// rethrow FormatError with the format string pointed to by start
|
||||||
|
throw BasicFormatError<Char>(e.what(), original);
|
||||||
|
}
|
||||||
|
|
||||||
writer.buffer_.append(start, s);
|
writer.buffer_.append(start, s);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -679,6 +686,17 @@ template void fmt::BasicFormatter<char>::CheckSign(
|
|||||||
|
|
||||||
template void fmt::BasicFormatter<char>::DoFormat();
|
template void fmt::BasicFormatter<char>::DoFormat();
|
||||||
|
|
||||||
|
const char* FormatErrorMessage(const std::string &message, const char* format) {
|
||||||
|
return fmt::c_str(fmt::Format("error: {} while parsing {}") << message << format);
|
||||||
|
}
|
||||||
|
|
||||||
|
template<> fmt::BasicFormatError<char>::BasicFormatError(const std::string &message, const char *format)
|
||||||
|
: std::runtime_error(FormatErrorMessage(message, format)), format_(format) {}
|
||||||
|
|
||||||
|
template<> fmt::BasicFormatError<char>::~BasicFormatError() {
|
||||||
|
std::runtime_error::~runtime_error();
|
||||||
|
}
|
||||||
|
|
||||||
// Explicit instantiations for wchar_t.
|
// Explicit instantiations for wchar_t.
|
||||||
|
|
||||||
template void fmt::BasicWriter<wchar_t>::FormatDouble<double>(
|
template void fmt::BasicWriter<wchar_t>::FormatDouble<double>(
|
||||||
@ -711,3 +729,10 @@ template void fmt::BasicFormatter<wchar_t>::CheckSign(
|
|||||||
const wchar_t *&s, const Arg &arg);
|
const wchar_t *&s, const Arg &arg);
|
||||||
|
|
||||||
template void fmt::BasicFormatter<wchar_t>::DoFormat();
|
template void fmt::BasicFormatter<wchar_t>::DoFormat();
|
||||||
|
|
||||||
|
template<> fmt::BasicFormatError<wchar_t>::BasicFormatError(const std::string &message, const wchar_t *format)
|
||||||
|
: std::runtime_error(message), format_(format){}
|
||||||
|
|
||||||
|
template<> fmt::BasicFormatError<wchar_t>::~BasicFormatError() {
|
||||||
|
std::runtime_error::~runtime_error();
|
||||||
|
}
|
||||||
|
|||||||
10
format.h
10
format.h
@ -292,6 +292,16 @@ class FormatError : public std::runtime_error {
|
|||||||
: std::runtime_error(message) {}
|
: std::runtime_error(message) {}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
template <typename Char>
|
||||||
|
class BasicFormatError : public std::runtime_error {
|
||||||
|
private:
|
||||||
|
std::basic_string<Char> format_;
|
||||||
|
public:
|
||||||
|
explicit BasicFormatError(const std::string &message, const Char *format);
|
||||||
|
virtual ~BasicFormatError() throw();
|
||||||
|
const Char *format() const { return format_.c_str(); }
|
||||||
|
};
|
||||||
|
|
||||||
enum Alignment {
|
enum Alignment {
|
||||||
ALIGN_DEFAULT, ALIGN_LEFT, ALIGN_RIGHT, ALIGN_CENTER, ALIGN_NUMERIC
|
ALIGN_DEFAULT, ALIGN_LEFT, ALIGN_RIGHT, ALIGN_CENTER, ALIGN_NUMERIC
|
||||||
};
|
};
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user