Skip to content

Commit

Permalink
Merge pull request #1018 from miloyip/issue1017_allOfHandler
Browse files Browse the repository at this point in the history
Fix #1017 allOf keyword fail with Writer handler
  • Loading branch information
miloyip committed Jul 13, 2017
2 parents 1a77513 + fcd2e1f commit c34e3df
Show file tree
Hide file tree
Showing 2 changed files with 27 additions and 18 deletions.
26 changes: 8 additions & 18 deletions include/rapidjson/schema.h
Original file line number Diff line number Diff line change
Expand Up @@ -1594,7 +1594,7 @@ class GenericSchemaValidator :
ownStateAllocator_(0),
schemaStack_(allocator, schemaStackCapacity),
documentStack_(allocator, documentStackCapacity),
outputHandler_(CreateNullHandler()),
outputHandler_(0),
valid_(true)
#if RAPIDJSON_SCHEMA_VERBOSE
, depth_(0)
Expand Down Expand Up @@ -1622,8 +1622,7 @@ class GenericSchemaValidator :
ownStateAllocator_(0),
schemaStack_(allocator, schemaStackCapacity),
documentStack_(allocator, documentStackCapacity),
outputHandler_(outputHandler),
nullHandler_(0),
outputHandler_(&outputHandler),
valid_(true)
#if RAPIDJSON_SCHEMA_VERBOSE
, depth_(0)
Expand All @@ -1634,10 +1633,6 @@ class GenericSchemaValidator :
//! Destructor.
~GenericSchemaValidator() {
Reset();
if (nullHandler_) {
nullHandler_->~OutputHandler();
StateAllocator::Free(nullHandler_);
}
RAPIDJSON_DELETE(ownStateAllocator_);
}

Expand Down Expand Up @@ -1699,7 +1694,7 @@ RAPIDJSON_MULTILINEMACRO_END
}

#define RAPIDJSON_SCHEMA_HANDLE_END_(method, arg2)\
return valid_ = EndValue() && outputHandler_.method arg2
return valid_ = EndValue() && (!outputHandler_ || outputHandler_->method arg2)

#define RAPIDJSON_SCHEMA_HANDLE_VALUE_(method, arg1, arg2) \
RAPIDJSON_SCHEMA_HANDLE_BEGIN_ (method, arg1);\
Expand All @@ -1721,15 +1716,15 @@ RAPIDJSON_MULTILINEMACRO_END
bool StartObject() {
RAPIDJSON_SCHEMA_HANDLE_BEGIN_(StartObject, (CurrentContext()));
RAPIDJSON_SCHEMA_HANDLE_PARALLEL_(StartObject, ());
return valid_ = outputHandler_.StartObject();
return valid_ = !outputHandler_ || outputHandler_->StartObject();
}

bool Key(const Ch* str, SizeType len, bool copy) {
if (!valid_) return false;
AppendToken(str, len);
if (!CurrentSchema().Key(CurrentContext(), str, len, copy)) return valid_ = false;
RAPIDJSON_SCHEMA_HANDLE_PARALLEL_(Key, (str, len, copy));
return valid_ = outputHandler_.Key(str, len, copy);
return valid_ = !outputHandler_ || outputHandler_->Key(str, len, copy);
}

bool EndObject(SizeType memberCount) {
Expand All @@ -1742,7 +1737,7 @@ RAPIDJSON_MULTILINEMACRO_END
bool StartArray() {
RAPIDJSON_SCHEMA_HANDLE_BEGIN_(StartArray, (CurrentContext()));
RAPIDJSON_SCHEMA_HANDLE_PARALLEL_(StartArray, ());
return valid_ = outputHandler_.StartArray();
return valid_ = !outputHandler_ || outputHandler_->StartArray();
}

bool EndArray(SizeType elementCount) {
Expand Down Expand Up @@ -1815,7 +1810,7 @@ RAPIDJSON_MULTILINEMACRO_END
ownStateAllocator_(0),
schemaStack_(allocator, schemaStackCapacity),
documentStack_(allocator, documentStackCapacity),
outputHandler_(CreateNullHandler()),
outputHandler_(0),
valid_(true)
#if RAPIDJSON_SCHEMA_VERBOSE
, depth_(depth)
Expand Down Expand Up @@ -1929,10 +1924,6 @@ RAPIDJSON_MULTILINEMACRO_END
Context& CurrentContext() { return *schemaStack_.template Top<Context>(); }
const Context& CurrentContext() const { return *schemaStack_.template Top<Context>(); }

OutputHandler& CreateNullHandler() {
return *(nullHandler_ = new (GetStateAllocator().Malloc(sizeof(OutputHandler))) OutputHandler);
}

static const size_t kDefaultSchemaStackCapacity = 1024;
static const size_t kDefaultDocumentStackCapacity = 256;
const SchemaDocumentType* schemaDocument_;
Expand All @@ -1941,8 +1932,7 @@ RAPIDJSON_MULTILINEMACRO_END
StateAllocator* ownStateAllocator_;
internal::Stack<StateAllocator> schemaStack_; //!< stack to store the current path of schema (BaseSchemaType *)
internal::Stack<StateAllocator> documentStack_; //!< stack to store the current path of validating document (Ch)
OutputHandler& outputHandler_;
OutputHandler* nullHandler_;
OutputHandler* outputHandler_;
bool valid_;
#if RAPIDJSON_SCHEMA_VERBOSE
unsigned depth_;
Expand Down
19 changes: 19 additions & 0 deletions test/unittest/schematest.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1329,6 +1329,25 @@ TEST(SchemaValidator, Issue825) {
VALIDATE(s, "{ \"item\": \"hello\" }", true);
}

TEST(SchemaValidator, Issue1017_allOfHandler) {
Document sd;
sd.Parse("{\"allOf\": [{\"type\": \"object\",\"properties\": {\"cyanArray2\": {\"type\": \"array\",\"items\": { \"type\": \"string\" }}}},{\"type\": \"object\",\"properties\": {\"blackArray\": {\"type\": \"array\",\"items\": { \"type\": \"string\" }}},\"required\": [ \"blackArray\" ]}]}");
SchemaDocument s(sd);
StringBuffer sb;
Writer<StringBuffer> writer(sb);
GenericSchemaValidator<SchemaDocument, Writer<StringBuffer> > validator(s, writer);
EXPECT_TRUE(validator.StartObject());
EXPECT_TRUE(validator.Key("cyanArray2", 10, false));
EXPECT_TRUE(validator.StartArray());
EXPECT_TRUE(validator.EndArray(0));
EXPECT_TRUE(validator.Key("blackArray", 10, false));
EXPECT_TRUE(validator.StartArray());
EXPECT_TRUE(validator.EndArray(0));
EXPECT_TRUE(validator.EndObject(0));
EXPECT_TRUE(validator.IsValid());
EXPECT_STREQ("{\"cyanArray2\":[],\"blackArray\":[]}", sb.GetString());
}

#ifdef __clang__
RAPIDJSON_DIAG_POP
#endif

0 comments on commit c34e3df

Please sign in to comment.