diff options
-rw-r--r-- | src/core/model/Domain.cpp | 26 | ||||
-rw-r--r-- | src/core/model/Domain.hpp | 27 | ||||
-rw-r--r-- | src/plugins/xml/XmlParser.cpp | 2 | ||||
-rw-r--r-- | test/plugins/xml/XmlParserTest.cpp | 23 |
4 files changed, 54 insertions, 24 deletions
diff --git a/src/core/model/Domain.cpp b/src/core/model/Domain.cpp index 9368005..f8c0779 100644 --- a/src/core/model/Domain.cpp +++ b/src/core/model/Domain.cpp @@ -155,19 +155,6 @@ bool Descriptor::doValidate(Logger &logger) const } else { valid = valid & validateName(logger); } - // check if all FieldDescriptors have this Descriptor as parent. - for (Handle<FieldDescriptor> fd : fieldDescriptors) { - if (fd->getParent() != this) { - logger.error(std::string("Descriptor \"") + getName() + - "\" has " - "field \"" + - fd->getName() + - "\" as child but the field does not " - "have the Descriptor as parent.", - *this); - valid = false; - } - } // check the FieldDescriptors themselves. return valid & continueValidationCheckDuplicates(fieldDescriptors, logger); } @@ -248,6 +235,7 @@ bool Descriptor::continuePath(Handle<StructuredClass> target, return found; } + void Descriptor::addFieldDescriptor(Handle<FieldDescriptor> fd) { // only add it if we need to. @@ -255,6 +243,18 @@ void Descriptor::addFieldDescriptor(Handle<FieldDescriptor> fd) invalidate(); fieldDescriptors.push_back(fd); } + if (fd->getParent() == nullptr) { + fd->setParent(this); + } +} + +void Descriptor::moveFieldDescriptor(Handle<FieldDescriptor> fd) +{ + // only add it if we need to. + if (fieldDescriptors.find(fd) == fieldDescriptors.end()) { + invalidate(); + fieldDescriptors.push_back(fd); + } Handle<Managed> par = fd->getParent(); if (par != this) { if (par != nullptr) { diff --git a/src/core/model/Domain.hpp b/src/core/model/Domain.hpp index bef7919..dd0af4c 100644 --- a/src/core/model/Domain.hpp +++ b/src/core/model/Domain.hpp @@ -509,12 +509,33 @@ public: /** * Adds the given FieldDescriptor to this Descriptor. This also sets the + * parent of the given FieldDescriptor if it is not set yet. + * + * @param fd is a FieldDescriptor. + */ + void addFieldDescriptor(Handle<FieldDescriptor> fd); + + /** + * Adds the given FieldDescriptors to this Descriptor. This also sets the + * parent of each given FieldDescriptor if it is not set yet. + * + * @param fds are FieldDescriptors. + */ + void addFieldDescriptors(const std::vector<Handle<FieldDescriptor>> &fds) + { + for (Handle<FieldDescriptor> fd : fds) { + addFieldDescriptor(fd); + } + } + + /** + * Adds the given FieldDescriptor to this Descriptor. This also sets the * parent of the given FieldDescriptor if it is not set to this Descriptor * already and removes it from the old parent Descriptor. * * @param fd is a FieldDescriptor. */ - void addFieldDescriptor(Handle<FieldDescriptor> fd); + void moveFieldDescriptor(Handle<FieldDescriptor> fd); /** * Adds the given FieldDescriptors to this Descriptor. This also sets the @@ -523,10 +544,10 @@ public: * * @param fds are FieldDescriptors. */ - void addFieldDescriptors(const std::vector<Handle<FieldDescriptor>> &fds) + void moveFieldDescriptors(const std::vector<Handle<FieldDescriptor>> &fds) { for (Handle<FieldDescriptor> fd : fds) { - addFieldDescriptor(fd); + moveFieldDescriptor(fd); } } diff --git a/src/plugins/xml/XmlParser.cpp b/src/plugins/xml/XmlParser.cpp index c288f40..2d62c11 100644 --- a/src/plugins/xml/XmlParser.cpp +++ b/src/plugins/xml/XmlParser.cpp @@ -411,7 +411,7 @@ public: name, parent, logger(), [](Handle<Node> field, Handle<Node> parent, Logger &logger) { if (field != nullptr) { - parent.cast<StructuredClass>()->copyFieldDescriptor( + parent.cast<StructuredClass>()->addFieldDescriptor( field.cast<FieldDescriptor>()); } }); diff --git a/test/plugins/xml/XmlParserTest.cpp b/test/plugins/xml/XmlParserTest.cpp index 6619199..0512fd0 100644 --- a/test/plugins/xml/XmlParserTest.cpp +++ b/test/plugins/xml/XmlParserTest.cpp @@ -156,14 +156,25 @@ static void checkFieldDescriptor( } static void checkFieldDescriptor( - Handle<Descriptor> desc, NodeVector<StructuredClass> children, + Handle<Descriptor> desc, Handle<Descriptor> parent, + NodeVector<StructuredClass> children, const std::string &name = DEFAULT_FIELD_NAME, FieldDescriptor::FieldType type = FieldDescriptor::FieldType::TREE, Handle<Type> primitiveType = nullptr, bool optional = false) { auto res = desc->resolve(RttiTypes::FieldDescriptor, name); ASSERT_EQ(1, res.size()); - checkFieldDescriptor(res[0].node, name, desc, children, type, primitiveType, + checkFieldDescriptor(res[0].node, name, parent, children, type, + primitiveType, optional); +} + +static void checkFieldDescriptor( + Handle<Descriptor> desc, NodeVector<StructuredClass> children, + const std::string &name = DEFAULT_FIELD_NAME, + FieldDescriptor::FieldType type = FieldDescriptor::FieldType::TREE, + Handle<Type> primitiveType = nullptr, bool optional = false) +{ + checkFieldDescriptor(desc, desc, children, name, type, primitiveType, optional); } @@ -216,8 +227,8 @@ TEST(XmlParser, domainParsing) Rooted<StructuredClass> heading = checkStructuredClass("heading", "heading", headings_domain, single, nullptr, nullptr, true, false); - // which should allow text content - checkFieldDescriptor(heading, {text}); + // which should be a reference to the paragraph descriptor. + checkFieldDescriptor(heading, paragraph, {text}); // and each struct in the book domain (except for text) should have a // heading field now. checkFieldDescriptor(book, {heading}, "heading", @@ -261,9 +272,7 @@ TEST(XmlParser, domainParsing) // paragraph should have comment as child now as well. checkFieldDescriptor(paragraph, {text, comment}); // as should heading, because it references the paragraph default field. - // TODO: This does not work as of now, because in fact fields get copied, - // not referenced. Should we reference fields, though? - //checkFieldDescriptor(heading, {text, comment}); + checkFieldDescriptor(heading, paragraph, {text, comment}); } } |