Browse Source

Improve XmlNode class test coverage

- add missing error checks
- change signature to provide more clean return
values
- add missing test cases
Patrick-Christopher Mattulat 2 years ago
parent
commit
3ffd0c29e9
3 changed files with 445 additions and 86 deletions
  1. 12 7
      include/ls_std/io/xml/XmlNode.hpp
  2. 116 28
      source/ls_std/io/xml/XmlNode.cpp
  3. 317 51
      test/cases/io/xml/XmlNodeTest.cpp

+ 12 - 7
include/ls_std/io/xml/XmlNode.hpp

@@ -3,7 +3,7 @@
  * Company:         Lynar Studios
  * E-Mail:          webmaster@lynarstudios.com
  * Created:         2020-09-24
- * Changed:         2021-05-02
+ * Changed:         2021-07-16
  *
  * */
 
@@ -41,12 +41,12 @@ namespace ls_std
       bool hasAttribute(const std::string &_name);
       bool hasChild(const std::string &_name);
       bool hasChild(const std::shared_ptr<ls_std::XmlNode> &_child);
-      void removeFirstAttribute();
-      void removeLastAttribute();
-      void removeFirstChild();
-      void removeLastChild();
-      void setName(std::string _name);
-      void setValue(std::string _value);
+      bool removeFirstAttribute();
+      bool removeLastAttribute();
+      bool removeFirstChild();
+      bool removeLastChild();
+      void setName(const std::string& _name);
+      void setValue(const std::string& _value);
       std::string toXml();
 
     protected:
@@ -61,6 +61,11 @@ namespace ls_std
       const static uint8_t TAB_SIZE{4};
       std::string value{};
 
+      void _assignName(const std::string& _name);
+      void _assignValue(const std::string& _value);
+      static void _checkIfAttributeReferenceIsValid(const std::shared_ptr<ls_std::XmlAttribute> &_attribute);
+      static void _checkIfNameIsNotEmpty(const std::string& _name);
+      static void _checkIfNodeReferenceIsValid(const std::shared_ptr<ls_std::XmlNode> &_child);
       static std::string _getTab(uint8_t _tabSize);
       bool _hasAttribute(const std::string &_name);
       bool _hasChild(const std::shared_ptr<ls_std::XmlNode> &_child);

+ 116 - 28
source/ls_std/io/xml/XmlNode.cpp

@@ -3,12 +3,13 @@
  * Company:         Lynar Studios
  * E-Mail:          webmaster@lynarstudios.com
  * Created:         2020-09-24
- * Changed:         2021-05-02
+ * Changed:         2021-07-16
  *
  * */
 
 #include <ls_std/io/xml/XmlNode.hpp>
 #include <ls_std/utils/STLUtils.hpp>
+#include <ls_std/exception/IllegalArgumentException.hpp>
 
 ls_std::XmlNode::XmlNode(std::string _name)
     : ls_std::Class("XmlNode"),
@@ -19,6 +20,8 @@ bool ls_std::XmlNode::addAttributeAfter(const std::shared_ptr<ls_std::XmlAttribu
 {
   bool added{};
   auto iterator = this->attributes.begin();
+  _checkIfAttributeReferenceIsValid(_attribute);
+  _checkIfNameIsNotEmpty(_name);
 
   if (!this->_hasAttribute(_attribute->getName()))
   {
@@ -43,6 +46,8 @@ bool ls_std::XmlNode::addAttributeBefore(const std::shared_ptr<ls_std::XmlAttrib
 {
   bool added{};
   auto iterator = this->attributes.begin();
+  _checkIfAttributeReferenceIsValid(_attribute);
+  _checkIfNameIsNotEmpty(_name);
 
   if (!this->_hasAttribute(_attribute->getName()))
   {
@@ -65,8 +70,9 @@ bool ls_std::XmlNode::addAttributeBefore(const std::shared_ptr<ls_std::XmlAttrib
 bool ls_std::XmlNode::addAttributeToBeginning(const std::shared_ptr<ls_std::XmlAttribute> &_attribute)
 {
   bool added{};
+  _checkIfAttributeReferenceIsValid(_attribute);
 
-  if (_attribute != nullptr && !_hasAttribute(_attribute->getName()))
+  if (!_hasAttribute(_attribute->getName()))
   {
     this->attributes.push_front(_attribute);
     added = true;
@@ -78,8 +84,9 @@ bool ls_std::XmlNode::addAttributeToBeginning(const std::shared_ptr<ls_std::XmlA
 bool ls_std::XmlNode::addAttributeToEnd(const std::shared_ptr<ls_std::XmlAttribute> &_attribute)
 {
   bool added{};
+  _checkIfAttributeReferenceIsValid(_attribute);
 
-  if (_attribute != nullptr && !_hasAttribute(_attribute->getName()))
+  if (!_hasAttribute(_attribute->getName()))
   {
     this->attributes.push_back(_attribute);
     added = true;
@@ -92,8 +99,10 @@ bool ls_std::XmlNode::addChildAfter(const std::shared_ptr<ls_std::XmlNode> &_chi
 {
   bool added{};
   auto iterator = this->children.begin();
+  _checkIfNodeReferenceIsValid(_child);
+  _checkIfNodeReferenceIsValid(_search);
 
-  if (_child != nullptr && !this->_hasChild(_child))
+  if (!this->_hasChild(_child))
   {
     while (iterator != this->children.end())
     {
@@ -116,8 +125,10 @@ bool ls_std::XmlNode::addChildBefore(const std::shared_ptr<ls_std::XmlNode> &_ch
 {
   bool added{};
   auto iterator = this->children.begin();
+  _checkIfNodeReferenceIsValid(_child);
+  _checkIfNodeReferenceIsValid(_search);
 
-  if (_child != nullptr && !this->_hasChild(_child))
+  if (!this->_hasChild(_child))
   {
     while (iterator != this->children.end())
     {
@@ -138,8 +149,9 @@ bool ls_std::XmlNode::addChildBefore(const std::shared_ptr<ls_std::XmlNode> &_ch
 bool ls_std::XmlNode::addChildToBeginning(const std::shared_ptr<ls_std::XmlNode> &_child)
 {
   bool added{};
+  _checkIfNodeReferenceIsValid(_child);
 
-  if (_child != nullptr && !this->_hasChild(_child))
+  if (!this->_hasChild(_child))
   {
     this->children.push_front(_child);
     added = true;
@@ -151,8 +163,9 @@ bool ls_std::XmlNode::addChildToBeginning(const std::shared_ptr<ls_std::XmlNode>
 bool ls_std::XmlNode::addChildToEnd(const std::shared_ptr<ls_std::XmlNode> &_child)
 {
   bool added{};
+  _checkIfNodeReferenceIsValid(_child);
 
-  if (_child != nullptr && !this->_hasChild(_child))
+  if (!this->_hasChild(_child))
   {
     this->children.push_back(_child);
     added = true;
@@ -216,46 +229,62 @@ bool ls_std::XmlNode::hasChild(const std::shared_ptr<ls_std::XmlNode> &_child)
   return this->_hasChild(_child);
 }
 
-void ls_std::XmlNode::removeFirstAttribute()
+bool ls_std::XmlNode::removeFirstAttribute()
 {
-  if (!this->attributes.empty())
+  bool isValidOperation = !this->attributes.empty();
+
+  if (isValidOperation)
   {
     this->attributes.pop_front();
   }
+
+  return isValidOperation;
 }
 
-void ls_std::XmlNode::removeLastAttribute()
+bool ls_std::XmlNode::removeLastAttribute()
 {
-  if (!this->attributes.empty())
+  bool isValidOperation = !this->attributes.empty();
+
+  if (isValidOperation)
   {
     this->attributes.pop_back();
   }
+
+  return isValidOperation;
 }
 
-void ls_std::XmlNode::removeFirstChild()
+bool ls_std::XmlNode::removeFirstChild()
 {
-  if (!this->children.empty())
+  bool isValidOperation = !this->children.empty();
+
+  if (isValidOperation)
   {
     this->children.pop_front();
   }
+
+  return isValidOperation;
 }
 
-void ls_std::XmlNode::removeLastChild()
+bool ls_std::XmlNode::removeLastChild()
 {
-  if (!this->children.empty())
+  bool isValidOperation = !this->children.empty();
+
+  if (isValidOperation)
   {
     this->children.pop_back();
   }
+
+  return isValidOperation;
 }
 
-void ls_std::XmlNode::setName(std::string _name)
+void ls_std::XmlNode::setName(const std::string &_name)
 {
-  this->name = std::move(_name);
+  this->_assignName(_name);
 }
 
-void ls_std::XmlNode::setValue(std::string _value)
+void ls_std::XmlNode::setValue(const std::string &_value)
 {
-  this->value = std::move(_value);
+  this->_assignValue(_value);
 }
 
 std::string ls_std::XmlNode::toXml()
@@ -279,6 +308,50 @@ std::string ls_std::XmlNode::_toXml_(uint8_t _tabSize)
   return xmlStream;
 }
 
+void ls_std::XmlNode::_assignName(const std::string &_name)
+{
+  if (_name.empty())
+  {
+    throw ls_std::IllegalArgumentException{};
+  }
+
+  this->name = _name;
+}
+
+void ls_std::XmlNode::_assignValue(const std::string &_value)
+{
+  if (_value.empty())
+  {
+    throw ls_std::IllegalArgumentException{};
+  }
+
+  this->value = _value;
+}
+
+void ls_std::XmlNode::_checkIfAttributeReferenceIsValid(const std::shared_ptr<ls_std::XmlAttribute> &_attribute)
+{
+  if (_attribute == nullptr)
+  {
+    throw ls_std::IllegalArgumentException{};
+  }
+}
+
+void ls_std::XmlNode::_checkIfNameIsNotEmpty(const std::string &_name)
+{
+  if (_name.empty())
+  {
+    throw ls_std::IllegalArgumentException{};
+  }
+}
+
+void ls_std::XmlNode::_checkIfNodeReferenceIsValid(const std::shared_ptr<ls_std::XmlNode> &_child)
+{
+  if (_child == nullptr)
+  {
+    throw ls_std::IllegalArgumentException{};
+  }
+}
+
 std::string ls_std::XmlNode::_getTab(uint8_t _tabSize)
 {
   std::string tab{};
@@ -295,12 +368,19 @@ bool ls_std::XmlNode::_hasAttribute(const std::string &_name)
 {
   bool exists{};
 
-  for (const auto &attribute : this->attributes)
+  if (_name.empty())
   {
-    if (attribute->getName() == _name)
+    throw ls_std::IllegalArgumentException{};
+  }
+  else
+  {
+    for (const auto &attribute : this->attributes)
     {
-      exists = true;
-      break;
+      if (attribute->getName() == _name)
+      {
+        exists = true;
+        break;
+      }
     }
   }
 
@@ -309,6 +389,7 @@ bool ls_std::XmlNode::_hasAttribute(const std::string &_name)
 
 bool ls_std::XmlNode::_hasChild(const std::shared_ptr<ls_std::XmlNode> &_child)
 {
+  _checkIfNodeReferenceIsValid(_child);
   return ls_std::STLUtils::contains(this->children, _child);
 }
 
@@ -316,12 +397,19 @@ bool ls_std::XmlNode::_hasChild(const std::string &_name)
 {
   bool exists{};
 
-  for (const auto &attribute : this->children)
+  if (_name.empty())
   {
-    if (attribute->getName() == _name)
+    throw ls_std::IllegalArgumentException{};
+  }
+  else
+  {
+    for (const auto &attribute : this->children)
     {
-      exists = true;
-      break;
+      if (attribute->getName() == _name)
+      {
+        exists = true;
+        break;
+      }
     }
   }
 
@@ -378,7 +466,7 @@ std::string ls_std::XmlNode::_toXmlOpenTagClose()
 
   if (this->children.empty() && this->value.empty())
   {
-    stream = "/>";
+    stream = " />";
   }
   else
   {

+ 317 - 51
test/cases/io/xml/XmlNodeTest.cpp

@@ -3,7 +3,7 @@
  * Company:         Lynar Studios
  * E-Mail:          webmaster@lynarstudios.com
  * Created:         2020-09-25
- * Changed:         2021-05-02
+ * Changed:         2021-07-16
  *
  * */
 
@@ -62,12 +62,42 @@ namespace
     ASSERT_STREQ("tasks", currentAttribute->getName().c_str());
   }
 
-  TEST_F(XmlNodeTest, addAttributeAfterNegative)
+  TEST_F(XmlNodeTest, addAttributeAfter_name_not_found)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+    ASSERT_FALSE(dialogNode.addAttributeAfter(std::make_shared<ls_std::XmlAttribute>("id"), "events"));
+  }
+
+  TEST_F(XmlNodeTest, addAttributeAfter_no_reference)
   {
     ls_std::XmlNode dialogNode{"dialog"};
-    dialogNode.addAttributeToEnd(std::make_shared<ls_std::XmlAttribute>("events"));
 
-    ASSERT_FALSE(dialogNode.addAttributeAfter(std::make_shared<ls_std::XmlAttribute>("id"), "assets"));
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addAttributeAfter(nullptr, "assets");
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
+  TEST_F(XmlNodeTest, addAttributeAfter_empty_name)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addAttributeAfter(std::make_shared<ls_std::XmlAttribute>("id"), "");
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
   }
 
   TEST_F(XmlNodeTest, addAttributeBefore)
@@ -105,12 +135,42 @@ namespace
     ASSERT_STREQ("assets", currentAttribute->getName().c_str());
   }
 
-  TEST_F(XmlNodeTest, addAttributeBeforeNegative)
+  TEST_F(XmlNodeTest, addAttributeBefore_name_not_found)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+    ASSERT_FALSE(dialogNode.addAttributeBefore(std::make_shared<ls_std::XmlAttribute>("tasks"), "assets"));
+  }
+
+  TEST_F(XmlNodeTest, addAttributeBefore_no_reference)
   {
     ls_std::XmlNode dialogNode{"dialog"};
-    dialogNode.addAttributeToEnd(std::make_shared<ls_std::XmlAttribute>("events"));
 
-    ASSERT_FALSE(dialogNode.addAttributeBefore(std::make_shared<ls_std::XmlAttribute>("id"), "assets"));
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addAttributeBefore(nullptr, "assets");
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
+  TEST_F(XmlNodeTest, addAttributeBefore_empty_name)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addAttributeBefore(std::make_shared<ls_std::XmlAttribute>("id"), "");
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
   }
 
   TEST_F(XmlNodeTest, addAttributeToBeginning)
@@ -140,6 +200,22 @@ namespace
     ASSERT_STREQ("id", currentAttribute->getName().c_str());
   }
 
+  TEST_F(XmlNodeTest, addAttributeToBeginning_no_reference)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addAttributeToBeginning(nullptr);
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
   TEST_F(XmlNodeTest, addAttributeToEnd)
   {
     ls_std::XmlNode dialogNode{"dialog"};
@@ -167,6 +243,22 @@ namespace
     ASSERT_STREQ("events", currentAttribute->getName().c_str());
   }
 
+  TEST_F(XmlNodeTest, addAttributeToEnd_no_reference)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addAttributeToEnd(nullptr);
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
   TEST_F(XmlNodeTest, addChildAfter)
   {
     ls_std::XmlNode dialogsNode{"dialogs"};
@@ -209,13 +301,45 @@ namespace
     ASSERT_STREQ("dialogNodeD", currentNode->getName().c_str());
   }
 
-  TEST_F(XmlNodeTest, addChildAfterNegative)
+  TEST_F(XmlNodeTest, addChildAfter_no_search_node_available)
   {
     ls_std::XmlNode dialogsNode{"dialogs"};
-    std::shared_ptr<ls_std::XmlNode> dialogNodeA = std::make_shared<ls_std::XmlNode>("dialogNodeA");
-    std::shared_ptr<ls_std::XmlNode> dialogNodeB = std::make_shared<ls_std::XmlNode>("dialogNodeB");
+    std::shared_ptr<ls_std::XmlNode> newChild = std::make_shared<ls_std::XmlNode>("newChild");
+    std::shared_ptr<ls_std::XmlNode> searchNode = std::make_shared<ls_std::XmlNode>("searchNode");
+
+    ASSERT_FALSE(dialogsNode.addChildAfter(newChild, searchNode));
+  }
 
-    ASSERT_FALSE(dialogsNode.addChildAfter(dialogNodeA, dialogNodeB));
+  TEST_F(XmlNodeTest, addChildAfter_no_child_reference)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addChildAfter(nullptr, std::make_shared<ls_std::XmlNode>("children"));
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
+  TEST_F(XmlNodeTest, addChildAfter_no_search_reference)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addChildAfter(std::make_shared<ls_std::XmlNode>("newChild"), nullptr);
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
   }
 
   TEST_F(XmlNodeTest, addChildBefore)
@@ -260,6 +384,47 @@ namespace
     ASSERT_STREQ("dialogNodeC", currentNode->getName().c_str());
   }
 
+  TEST_F(XmlNodeTest, addChildBefore_no_search_node_available)
+  {
+    ls_std::XmlNode dialogsNode{"dialogs"};
+    std::shared_ptr<ls_std::XmlNode> newChild = std::make_shared<ls_std::XmlNode>("newChild");
+    std::shared_ptr<ls_std::XmlNode> searchNode = std::make_shared<ls_std::XmlNode>("searchNode");
+
+    ASSERT_FALSE(dialogsNode.addChildBefore(newChild, searchNode));
+  }
+
+  TEST_F(XmlNodeTest, addChildBefore_no_child_reference)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addChildBefore(nullptr, std::make_shared<ls_std::XmlNode>("children"));
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
+  TEST_F(XmlNodeTest, addChildBefore_no_search_reference)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addChildBefore(std::make_shared<ls_std::XmlNode>("newChild"), nullptr);
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
   TEST_F(XmlNodeTest, addChildToBeginning)
   {
     ls_std::XmlNode dialogsNode{"dialogs"};
@@ -302,6 +467,22 @@ namespace
     ASSERT_STREQ("dialogNodeC", currentNode->getName().c_str());
   }
 
+  TEST_F(XmlNodeTest, addChildToBeginning_no_child_reference)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addChildToBeginning(nullptr);
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
   TEST_F(XmlNodeTest, addChildToEnd)
   {
     ls_std::XmlNode dialogsNode{"dialogs"};
@@ -344,6 +525,22 @@ namespace
     ASSERT_STREQ("dialogNodeA", currentNode->getName().c_str());
   }
 
+  TEST_F(XmlNodeTest, addChildToEnd_no_child_reference)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.addChildToEnd(nullptr);
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
   TEST_F(XmlNodeTest, clearValue)
   {
     ls_std::XmlNode dialogNode{"dialog"};
@@ -413,16 +610,28 @@ namespace
     ASSERT_TRUE(dialogNode.hasAttribute("assets"));
   }
 
-  TEST_F(XmlNodeTest, hasAttributeNegative)
+  TEST_F(XmlNodeTest, hasAttribute_attribute_not_available)
   {
     ls_std::XmlNode dialogNode{"dialogNode"};
-    dialogNode.addAttributeToEnd(std::make_shared<ls_std::XmlAttribute>("id"));
-    dialogNode.addAttributeToEnd(std::make_shared<ls_std::XmlAttribute>("events"));
-    dialogNode.addAttributeToEnd(std::make_shared<ls_std::XmlAttribute>("assets"));
-
     ASSERT_FALSE(dialogNode.hasAttribute("fields"));
   }
 
+  TEST_F(XmlNodeTest, hasAttribute_empty_name)
+  {
+    ls_std::XmlNode dialogNode{"dialogNode"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.hasAttribute("");
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
   TEST_F(XmlNodeTest, hasChild)
   {
     ls_std::XmlNode dialogsNode{"dialogsNode"};
@@ -435,16 +644,26 @@ namespace
     ASSERT_TRUE(dialogsNode.hasChild("dialogC"));
   }
 
-  TEST_F(XmlNodeTest, hasChildNegative)
+  TEST_F(XmlNodeTest, hasChild_child_not_available)
   {
     ls_std::XmlNode dialogsNode{"dialogsNode"};
-    dialogsNode.addChildToEnd(std::make_shared<ls_std::XmlNode>("dialogA"));
-    dialogsNode.addChildToEnd(std::make_shared<ls_std::XmlNode>("dialogB"));
-    dialogsNode.addChildToEnd(std::make_shared<ls_std::XmlNode>("dialogC"));
-
     ASSERT_FALSE(dialogsNode.hasChild("dialogD"));
-    ASSERT_FALSE(dialogsNode.hasChild("dialogE"));
-    ASSERT_FALSE(dialogsNode.hasChild("dialogF"));
+  }
+
+  TEST_F(XmlNodeTest, hasChild_empty_name)
+  {
+    ls_std::XmlNode dialogNode{"dialogNode"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.hasChild("");
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
   }
 
   TEST_F(XmlNodeTest, hasChildV2)
@@ -458,16 +677,31 @@ namespace
     ASSERT_TRUE(dialogsNode.hasChild(searchNode));
   }
 
-  TEST_F(XmlNodeTest, hasChildV2Negative)
+  TEST_F(XmlNodeTest, hasChildV2_child_not_available)
   {
     ls_std::XmlNode dialogsNode{"dialogsNode"};
     std::shared_ptr<ls_std::XmlNode> searchNode = std::make_shared<ls_std::XmlNode>("dialogB");
-    dialogsNode.addChildToEnd(std::make_shared<ls_std::XmlNode>("dialogA"));
-    dialogsNode.addChildToEnd(std::make_shared<ls_std::XmlNode>("dialogC"));
 
     ASSERT_FALSE(dialogsNode.hasChild(searchNode));
   }
 
+  TEST_F(XmlNodeTest, hasChildV2_no_child_reference)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+    std::shared_ptr<ls_std::XmlNode> searchNode{};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.hasChild(searchNode);
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
   TEST_F(XmlNodeTest, removeFirstAttribute)
   {
     ls_std::XmlNode dialogNode{"dialog"};
@@ -479,7 +713,7 @@ namespace
     ASSERT_TRUE(!dialogNode.getAttributes().empty());
     ASSERT_EQ(3, dialogNode.getAttributes().size());
 
-    dialogNode.removeFirstAttribute();
+    ASSERT_TRUE(dialogNode.removeFirstAttribute());
     ASSERT_EQ(2, dialogNode.getAttributes().size());
 
     currentAttribute = *std::next(dialogNode.getAttributes().begin(), 0);
@@ -488,13 +722,10 @@ namespace
     ASSERT_STREQ("assets", currentAttribute->getName().c_str());
   }
 
-  TEST_F(XmlNodeTest, removeFirstAttributeNegative)
+  TEST_F(XmlNodeTest, removeFirstAttribute_no_attributes_available)
   {
     ls_std::XmlNode dialogNode{"dialog"};
-    ASSERT_TRUE(dialogNode.getAttributes().empty());
-
-    dialogNode.removeFirstAttribute();
-    ASSERT_TRUE(dialogNode.getAttributes().empty());
+    ASSERT_FALSE(dialogNode.removeFirstAttribute());
   }
 
   TEST_F(XmlNodeTest, removeLastAttribute)
@@ -508,7 +739,7 @@ namespace
     ASSERT_TRUE(!dialogNode.getAttributes().empty());
     ASSERT_EQ(3, dialogNode.getAttributes().size());
 
-    dialogNode.removeLastAttribute();
+    ASSERT_TRUE(dialogNode.removeLastAttribute());
     ASSERT_EQ(2, dialogNode.getAttributes().size());
 
     currentAttribute = *std::next(dialogNode.getAttributes().begin(), 0);
@@ -517,13 +748,10 @@ namespace
     ASSERT_STREQ("events", currentAttribute->getName().c_str());
   }
 
-  TEST_F(XmlNodeTest, removeLastAttributeNegative)
+  TEST_F(XmlNodeTest, removeLastAttribute_no_attributes_available)
   {
     ls_std::XmlNode dialogNode{"dialog"};
-    ASSERT_TRUE(dialogNode.getAttributes().empty());
-
-    dialogNode.removeLastAttribute();
-    ASSERT_TRUE(dialogNode.getAttributes().empty());
+    ASSERT_FALSE(dialogNode.removeLastAttribute());
   }
 
   TEST_F(XmlNodeTest, removeFirstChild)
@@ -553,7 +781,7 @@ namespace
 
     // check
 
-    dialogsNode.removeFirstChild();
+    ASSERT_TRUE(dialogsNode.removeFirstChild());
     currentNode = *std::next(dialogsNode.getChildren().begin(), 0);
     ASSERT_STREQ("dialogB", currentNode->getName().c_str());
     currentNode = *std::next(dialogsNode.getChildren().begin(), 1);
@@ -564,13 +792,10 @@ namespace
     ASSERT_STREQ("event", currentNode->getName().c_str());
   }
 
-  TEST_F(XmlNodeTest, removeFirstChildNegative)
+  TEST_F(XmlNodeTest, removeFirstChild_no_children_available)
   {
     ls_std::XmlNode dialogsNode{"dialogs"};
-    ASSERT_TRUE(dialogsNode.getChildren().empty());
-
-    dialogsNode.removeFirstChild();
-    ASSERT_TRUE(dialogsNode.getChildren().empty());
+    ASSERT_FALSE(dialogsNode.removeFirstChild());
   }
 
   TEST_F(XmlNodeTest, removeLastChild)
@@ -600,7 +825,7 @@ namespace
 
     // check
 
-    dialogsNode.removeLastChild();
+    ASSERT_TRUE(dialogsNode.removeLastChild());
     currentNode = *std::next(dialogsNode.getChildren().begin(), 0);
     ASSERT_STREQ("dialogA", currentNode->getName().c_str());
     currentNode = *std::next(dialogsNode.getChildren().begin(), 1);
@@ -611,13 +836,10 @@ namespace
     ASSERT_STREQ("additionalInfo", currentNode->getName().c_str());
   }
 
-  TEST_F(XmlNodeTest, removeLastChildNegative)
+  TEST_F(XmlNodeTest, removeLastChild_no_children_available)
   {
     ls_std::XmlNode dialogsNode{"dialogs"};
-    ASSERT_TRUE(dialogsNode.getChildren().empty());
-
-    dialogsNode.removeLastChild();
-    ASSERT_TRUE(dialogsNode.getChildren().empty());
+    ASSERT_FALSE(dialogsNode.removeLastChild());
   }
 
   TEST_F(XmlNodeTest, setName)
@@ -628,6 +850,22 @@ namespace
     ASSERT_STREQ("dialog2", dialogNode.getName().c_str());
   }
 
+  TEST_F(XmlNodeTest, setName_empty_name)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.setName("");
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
   TEST_F(XmlNodeTest, setValue)
   {
     ls_std::XmlNode dialogNode{"dialog"};
@@ -636,12 +874,40 @@ namespace
     ASSERT_STREQ("Something written", dialogNode.getValue().c_str());
   }
 
+  TEST_F(XmlNodeTest, setValue_empty_value)
+  {
+    ls_std::XmlNode dialogNode{"dialog"};
+
+    EXPECT_THROW({
+                   try
+                   {
+                     dialogNode.setValue("");
+                   }
+                   catch (const ls_std::IllegalArgumentException &_exception)
+                   {
+                     throw;
+                   }
+                 }, ls_std::IllegalArgumentException);
+  }
+
   TEST_F(XmlNodeTest, toXml)
   {
     auto root = ls_std_test::TestDataFactory::createXmlContent();
     std::string xmlContent = root->toXml();
-    std::string expectedXmlString = R"("<dialog name="dungeon_001"><dialogUnit id="001"><text>Hello!</text></dialogUnit><dialogUnit id="002"><text>Hello again!</text></dialogUnit></dialog>")";
 
     ASSERT_TRUE(!xmlContent.empty());
   }
+
+  TEST_F(XmlNodeTest, toXml_no_value)
+  {
+    std::shared_ptr<ls_std::XmlNode> singleLineElement = std::make_shared<ls_std::XmlNode>("info");
+    std::shared_ptr<ls_std::XmlAttribute> attribute = std::make_shared<ls_std::XmlAttribute>("id");
+    attribute->setValue("important");
+    singleLineElement->addAttributeToEnd(attribute);
+
+    ls_std::String xmlContent {singleLineElement->toXml()};
+    std::string expectedXmlString = R"(<info id="important" />)";
+
+    ASSERT_TRUE(xmlContent.contains(expectedXmlString));
+  }
 }