Skip to content

Commit

Permalink
Namespace JSON-related errors
Browse files Browse the repository at this point in the history
Signed-off-by: Juan Cruz Viotti <jv@jviotti.com>
  • Loading branch information
jviotti committed Jan 28, 2025
1 parent d1039b8 commit 4048343
Show file tree
Hide file tree
Showing 13 changed files with 56 additions and 51 deletions.
8 changes: 4 additions & 4 deletions src/core/json/include/sourcemeta/core/json.h
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ namespace sourcemeta::core {
/// assert(document.is_array());
/// ```
///
/// If parsing fails, sourcemeta::core::ParseError will be thrown.
/// If parsing fails, sourcemeta::core::JSONParseError will be thrown.
SOURCEMETA_CORE_JSON_EXPORT
auto parse_json(std::basic_istream<JSON::Char, JSON::CharTraits> &stream,
const JSON::ParseCallback &callback = nullptr) -> JSON;
Expand All @@ -63,7 +63,7 @@ auto parse_json(std::basic_istream<JSON::Char, JSON::CharTraits> &stream,
/// assert(document.is_array());
/// ```
///
/// If parsing fails, sourcemeta::core::ParseError will be thrown.
/// If parsing fails, sourcemeta::core::JSONParseError will be thrown.
SOURCEMETA_CORE_JSON_EXPORT
auto parse_json(const std::basic_string<JSON::Char, JSON::CharTraits> &input,
const JSON::ParseCallback &callback = nullptr) -> JSON;
Expand Down Expand Up @@ -125,7 +125,7 @@ auto parse_json(const std::basic_string<JSON::Char, JSON::CharTraits> &input,
/// std::cout << std::endl;
/// ```
///
/// If parsing fails, sourcemeta::core::ParseError will be thrown.
/// If parsing fails, sourcemeta::core::JSONParseError will be thrown.
SOURCEMETA_CORE_JSON_EXPORT
auto read_json(const std::filesystem::path &path) -> JSON;

Expand All @@ -147,7 +147,7 @@ auto read_json(const std::filesystem::path &path) -> JSON;
/// std::cout << std::endl;
/// ```
///
/// If parsing fails, sourcemeta::core::ParseError will be thrown.
/// If parsing fails, sourcemeta::core::JSONParseError will be thrown.
SOURCEMETA_CORE_JSON_EXPORT
auto read_file(const std::filesystem::path &path)
-> std::basic_ifstream<JSON::Char, JSON::CharTraits>;
Expand Down
17 changes: 9 additions & 8 deletions src/core/json/include/sourcemeta/core/json_error.h
Original file line number Diff line number Diff line change
Expand Up @@ -20,10 +20,10 @@ namespace sourcemeta::core {

/// @ingroup json
/// This class represents a parsing error
class SOURCEMETA_CORE_JSON_EXPORT ParseError : public std::exception {
class SOURCEMETA_CORE_JSON_EXPORT JSONParseError : public std::exception {
public:
/// Create a parsing error
ParseError(const std::uint64_t line, const std::uint64_t column)
JSONParseError(const std::uint64_t line, const std::uint64_t column)
: line_{line}, column_{column} {}

[[nodiscard]] auto what() const noexcept -> const char * override {
Expand All @@ -45,16 +45,17 @@ class SOURCEMETA_CORE_JSON_EXPORT ParseError : public std::exception {

/// @ingroup json
/// This class represents a parsing error occurring from parsing a file
class SOURCEMETA_CORE_JSON_EXPORT FileParseError : public ParseError {
class SOURCEMETA_CORE_JSON_EXPORT JSONFileParseError : public JSONParseError {
public:
/// Create a file parsing error
FileParseError(const std::filesystem::path &path, const std::uint64_t line,
const std::uint64_t column)
: ParseError{line, column}, path_{path} {}
JSONFileParseError(const std::filesystem::path &path,
const std::uint64_t line, const std::uint64_t column)
: JSONParseError{line, column}, path_{path} {}

/// Create a file parsing error from a parse error
FileParseError(const std::filesystem::path &path, const ParseError &parent)
: ParseError{parent.line(), parent.column()}, path_{path} {}
JSONFileParseError(const std::filesystem::path &path,
const JSONParseError &parent)
: JSONParseError{parent.line(), parent.column()}, path_{path} {}

/// Get the fiel path of the error
[[nodiscard]] auto path() const noexcept -> const std::filesystem::path {
Expand Down
4 changes: 2 additions & 2 deletions src/core/json/json.cc
Original file line number Diff line number Diff line change
Expand Up @@ -54,9 +54,9 @@ auto read_json(const std::filesystem::path &path) -> JSON {
auto stream{read_file(path)};
try {
return parse_json(stream);
} catch (const ParseError &error) {
} catch (const JSONParseError &error) {
// For producing better error messages
throw FileParseError(path, error);
throw JSONFileParseError(path, error);
}
}

Expand Down
46 changes: 23 additions & 23 deletions src/core/json/parser.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ inline auto parse_null(
1)) {
column += 1;
if (stream.get() != character) {
throw ParseError(line, column);
throw JSONParseError(line, column);
}
}

Expand All @@ -45,7 +45,7 @@ inline auto parse_boolean_true(
1)) {
column += 1;
if (stream.get() != character) {
throw ParseError(line, column);
throw JSONParseError(line, column);
}
}

Expand All @@ -62,7 +62,7 @@ inline auto parse_boolean_false(
1)) {
column += 1;
if (stream.get() != character) {
throw ParseError(line, column);
throw JSONParseError(line, column);
}
}

Expand Down Expand Up @@ -97,7 +97,7 @@ auto parse_string_unicode_code_point(
if (std::isxdigit(code_point[code_point_size])) {
code_point_size += 1;
} else {
throw ParseError(line, column);
throw JSONParseError(line, column);
}
}

Expand Down Expand Up @@ -127,13 +127,13 @@ auto parse_string_unicode(
// Next, we expect "\"
column += 1;
if (stream.get() != internal::token_string_escape<CharT>) {
throw ParseError(line, column);
throw JSONParseError(line, column);
}

// Next, we expect "u"
column += 1;
if (stream.get() != internal::token_string_escape_unicode<CharT>) {
throw ParseError(line, column);
throw JSONParseError(line, column);
}

// Finally, get the low code point of the surrogate and calculate
Expand All @@ -147,7 +147,7 @@ auto parse_string_unicode(
code_point =
0x10000 + ((code_point - 0xD800) << 10) + (low_code_point - 0xDC00);
} else {
throw ParseError(line, column);
throw JSONParseError(line, column);
}
}

Expand Down Expand Up @@ -218,7 +218,7 @@ auto parse_string_escape(
return;

default:
throw ParseError(line, column);
throw JSONParseError(line, column);
}
}

Expand Down Expand Up @@ -276,14 +276,14 @@ auto parse_string(
case '\u001E':
case '\u001F':
case static_cast<typename JSON::Char>(JSON::CharTraits::eof()):
throw ParseError(line, column);
throw JSONParseError(line, column);
default:
result.put(character);
break;
}
}

throw ParseError(line, column);
throw JSONParseError(line, column);
}

template <typename CharT, typename Traits>
Expand All @@ -293,7 +293,7 @@ auto parse_number_integer(const std::uint64_t line, const std::uint64_t column,
try {
return std::stoll(string);
} catch (const std::out_of_range &) {
throw ParseError(line, column);
throw JSONParseError(line, column);
}
}

Expand All @@ -304,7 +304,7 @@ auto parse_number_real(const std::uint64_t line, const std::uint64_t column,
try {
return std::stod(string);
} catch (const std::out_of_range &) {
throw ParseError(line, column);
throw JSONParseError(line, column);
}
}

Expand Down Expand Up @@ -338,7 +338,7 @@ auto parse_number_exponent_rest(
}
}

throw ParseError(line, column);
throw JSONParseError(line, column);
}

auto parse_number_exponent(
Expand Down Expand Up @@ -366,7 +366,7 @@ auto parse_number_exponent(
return parse_number_exponent_rest(line, column, original_column, stream,
result);
default:
throw ParseError(line, column);
throw JSONParseError(line, column);
}
}

Expand Down Expand Up @@ -405,7 +405,7 @@ auto parse_number_exponent_first(
return parse_number_exponent_rest(line, column, original_column, stream,
result);
default:
throw ParseError(line, column);
throw JSONParseError(line, column);
}
}

Expand Down Expand Up @@ -450,7 +450,7 @@ auto parse_number_fractional(
}
}

throw ParseError(line, column);
throw JSONParseError(line, column);
}

auto parse_number_fractional_first(
Expand All @@ -469,7 +469,7 @@ auto parse_number_fractional_first(
case internal::token_number_decimal_point<typename JSON::Char>:
case static_cast<typename JSON::Char>(JSON::CharTraits::eof()):
column += 1;
throw ParseError(line, column);
throw JSONParseError(line, column);
case internal::token_number_zero<typename JSON::Char>:
case internal::token_number_one<typename JSON::Char>:
case internal::token_number_two<typename JSON::Char>:
Expand Down Expand Up @@ -526,7 +526,7 @@ auto parse_number_maybe_fractional(
case internal::token_number_eight<typename JSON::Char>:
case internal::token_number_nine<typename JSON::Char>:
column += 1;
throw ParseError(line, column);
throw JSONParseError(line, column);
default:
return JSON{parse_number_integer(line, original_column, result.str())};
}
Expand Down Expand Up @@ -578,7 +578,7 @@ auto parse_number_any_rest(
}
}

throw ParseError(line, column);
throw JSONParseError(line, column);
}

auto parse_number_any_negative_first(
Expand Down Expand Up @@ -612,7 +612,7 @@ auto parse_number_any_negative_first(
return parse_number_any_rest(line, column, original_column, stream,
result);
default:
throw ParseError(line, column);
throw JSONParseError(line, column);
}
}

Expand Down Expand Up @@ -783,7 +783,7 @@ auto internal_parse_json(
case internal::token_whitespace_space<typename JSON::Char>:
goto do_parse;
default:
throw ParseError(line, column);
throw JSONParseError(line, column);
}

/*
Expand Down Expand Up @@ -828,7 +828,7 @@ auto internal_parse_json(
CALLBACK_POST(Array, frames.top().get());
goto do_parse_container_end;
} else {
throw ParseError(line, column);
throw JSONParseError(line, column);
}

// Values
Expand Down Expand Up @@ -1172,7 +1172,7 @@ auto internal_parse_json(
frames.pop();
}

throw ParseError(line, column);
throw JSONParseError(line, column);

do_parse_container_end:
assert(!levels.empty());
Expand Down
2 changes: 1 addition & 1 deletion src/core/jsonl/include/sourcemeta/core/jsonl.h
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ class SOURCEMETA_CORE_JSONL_EXPORT JSONL {
/// }
/// ```
///
/// If parsing fails, sourcemeta::core::ParseError will be thrown.
/// If parsing fails, sourcemeta::core::JSONParseError will be thrown.
JSONL(std::basic_istream<JSON::Char, JSON::CharTraits> &stream);

using const_iterator = ConstJSONLIterator;
Expand Down
2 changes: 1 addition & 1 deletion src/core/jsonl/iterator.cc
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ auto ConstJSONLIterator::operator++() -> ConstJSONLIterator & {
goto end;
default:
this->column += 1;
throw ParseError(this->line, this->column);
throw JSONParseError(this->line, this->column);
}

element:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,10 +13,13 @@ namespace sourcemeta::core {

/// @ingroup jsonpointer
/// This class represents a parsing error.
class SOURCEMETA_CORE_JSONPOINTER_EXPORT PointerParseError : public ParseError {
class SOURCEMETA_CORE_JSONPOINTER_EXPORT PointerParseError
// TODO: It makes no sense for a JSON Pointer error to inherit from a JSON
// error. Make them independent
: public JSONParseError {
public:
/// Create a parsing error
PointerParseError(const std::uint64_t column) : ParseError{1, column} {}
PointerParseError(const std::uint64_t column) : JSONParseError{1, column} {}

[[nodiscard]] auto what() const noexcept -> const char * override {
return "The input is not a valid JSON Pointer";
Expand Down
2 changes: 1 addition & 1 deletion src/core/yaml/yaml.cc
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ static auto yaml_node_to_json(yaml_node_t *const node,
// Looks like it is very hard in YAML, given a scalar value, to
// determine whether it is a string or something else without attempting
// to parsing it and potentially failing to do so
} catch (const sourcemeta::core::ParseError &) {
} catch (const sourcemeta::core::JSONParseError &) {
return sourcemeta::core::JSON{input};
}
}
Expand Down
9 changes: 5 additions & 4 deletions test/json/json_error_test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,11 @@
#include <type_traits> // std::is_base_of_v

TEST(JSON_error, parse_error) {
static_assert(std::is_base_of_v<std::exception, sourcemeta::core::ParseError>,
"Must subclass std::exception");
auto exception{sourcemeta::core::ParseError(5, 6)};
EXPECT_THROW(throw exception, sourcemeta::core::ParseError);
static_assert(
std::is_base_of_v<std::exception, sourcemeta::core::JSONParseError>,
"Must subclass std::exception");
auto exception{sourcemeta::core::JSONParseError(5, 6)};
EXPECT_THROW(throw exception, sourcemeta::core::JSONParseError);
EXPECT_EQ(std::string{exception.what()}, "Failed to parse the JSON document");
EXPECT_EQ(exception.line(), 5);
EXPECT_EQ(exception.column(), 6);
Expand Down
4 changes: 2 additions & 2 deletions test/json/json_parse_error_test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
try { \
sourcemeta::core::parse_json((input)); \
FAIL() << "The parse function was expected to throw"; \
} catch (const sourcemeta::core::ParseError &error) { \
} catch (const sourcemeta::core::JSONParseError &error) { \
EXPECT_EQ(error.line(), expected_line); \
EXPECT_EQ(error.column(), expected_column); \
SUCCEED(); \
Expand Down Expand Up @@ -633,7 +633,7 @@ TEST(JSON_parse_error, read_json_invalid) {
try {
sourcemeta::core::read_json(std::filesystem::path{TEST_DIRECTORY} /
"stub_invalid.json");
} catch (const sourcemeta::core::FileParseError &error) {
} catch (const sourcemeta::core::JSONFileParseError &error) {
EXPECT_EQ(error.path(),
std::filesystem::path{TEST_DIRECTORY} / "stub_invalid.json");
EXPECT_EQ(error.line(), 3);
Expand Down
2 changes: 1 addition & 1 deletion test/json/jsontestsuite.cc
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ class JSONTest : public testing::Test {
while (!stream.eof()) {
sourcemeta::core::parse_json(stream);
}
} catch (const sourcemeta::core::ParseError &) {
} catch (const sourcemeta::core::JSONParseError &) {
SUCCEED();
} catch (const std::exception &) {
FAIL() << "The parse function threw an unexpected error";
Expand Down
2 changes: 1 addition & 1 deletion test/jsonl/jsonl_parse_error_test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
while (iterator != parser.cend()) \
++iterator; \
FAIL() << "The JSONL parser was expected to throw"; \
} catch (const sourcemeta::core::ParseError &error) { \
} catch (const sourcemeta::core::JSONParseError &error) { \
EXPECT_EQ(error.line(), expected_line); \
EXPECT_EQ(error.column(), expected_column); \
SUCCEED(); \
Expand Down
2 changes: 1 addition & 1 deletion test/jsonpointer/jsonpointer_parse_error_test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
stream << "\"" << (input) << "\""; \
sourcemeta::core::parse_json(stream.str()); \
FAIL() << "The parse function was expected to throw"; \
} catch (const sourcemeta::core::ParseError &) { \
} catch (const sourcemeta::core::JSONParseError &) { \
SUCCEED(); \
} catch (const std::exception &) { \
FAIL() << "The parse operation threw an unexpected error"; \
Expand Down

0 comments on commit 4048343

Please sign in to comment.