[JSON] Facility to track position within an object and report errors.
This error model should be rich enough for most applications. It comprises:
- a name for the root object, so the user knows what we're parsing
- a path from the root object to the JSON node most associated with the error
- a local error message
This can be presented as an llvm::Error e.g.
"expected string at ConfigFile.credentials[0].username"
It's designed to be cheap: Paths are a linked list of lightweight
objects on the stack. No heap allocations unless errors are encountered.
A subsequent commit will make use of this in the JSON-to-object
translation facilities: fromJSON and ObjectMapper.
However it's independent of these and can be used for e.g. validation alone.
Another subsequent commit will support showing the error in its context
within the parsed value.
Differential Revision: https://reviews.llvm.org/D88103
diff --git a/llvm/unittests/Support/JSONTest.cpp b/llvm/unittests/Support/JSONTest.cpp
index 986cf5e..8c7b470 100644
--- a/llvm/unittests/Support/JSONTest.cpp
+++ b/llvm/unittests/Support/JSONTest.cpp
@@ -8,6 +8,7 @@
#include "llvm/Support/JSON.h"
#include "llvm/Support/raw_ostream.h"
+#include "llvm/Testing/Support/Error.h"
#include "gmock/gmock.h"
#include "gtest/gtest.h"
@@ -461,6 +462,17 @@
EXPECT_EQ(Pretty, StreamStuff(2));
}
+TEST(JSONTest, Path) {
+ Path::Root R("foo");
+ Path P = R, A = P.field("a"), B = P.field("b");
+ A.index(1).field("c").index(2).report("boom");
+ EXPECT_THAT_ERROR(R.getError(), FailedWithMessage("boom at foo.a[1].c[2]"));
+ B.field("d").field("e").report("bam");
+ EXPECT_THAT_ERROR(R.getError(), FailedWithMessage("bam at foo.b.d.e"));
+ P.report("oh no");
+ EXPECT_THAT_ERROR(R.getError(), FailedWithMessage("oh no when parsing foo"));
+}
+
} // namespace
} // namespace json
} // namespace llvm