浏览代码

Merge branch 'section-pair-standard' of public/ls-standard-library into development

patrick-christopher.mattulat 1 年之前
父节点
当前提交
d5d6199c45
共有 100 个文件被更改,包括 3966 次插入866 次删除
  1. 1 1
      .clang-format
  2. 230 73
      CMakeLists.txt
  3. 6 2
      README.md
  4. 0 13
      doc/kv-file-definition.md
  5. 二进制
      doc/section-pair-2023-standard.odt
  6. 33 0
      include/ls-std/core/ConditionalFunctionExecutor.hpp
  7. 36 0
      include/ls-std/core/evaluator/IndexOutOfBoundsEvaluator.hpp
  8. 2 2
      include/ls-std/core/evaluator/NullPointerEvaluator.hpp
  9. 35 0
      include/ls-std/core/exception/IndexOutOfBoundsException.hpp
  10. 35 0
      include/ls-std/core/exception/WrongCallException.hpp
  11. 28 0
      include/ls-std/core/interface/IValidator.hpp
  12. 1 2
      include/ls-std/io/File.hpp
  13. 35 0
      include/ls-std/io/evaluator/FileExistenceEvaluator.hpp
  14. 0 42
      include/ls-std/io/kv/KvDocument.hpp
  15. 0 49
      include/ls-std/io/kv/KvFileReader.hpp
  16. 0 39
      include/ls-std/io/kv/KvPair.hpp
  17. 0 37
      include/ls-std/io/kv/KvParseParameter.hpp
  18. 0 48
      include/ls-std/io/kv/KvParser.hpp
  19. 29 0
      include/ls-std/io/section-pair/SectionPairMessageFormatter.hpp
  20. 23 0
      include/ls-std/io/section-pair/SectionPairRowEnumType.hpp
  21. 21 0
      include/ls-std/io/section-pair/SectionPairTypes.hpp
  22. 35 0
      include/ls-std/io/section-pair/evaluator/SectionPairIdentifierArgumentEvaluator.hpp
  23. 35 0
      include/ls-std/io/section-pair/evaluator/SectionPairRowArgumentEvaluator.hpp
  24. 35 0
      include/ls-std/io/section-pair/evaluator/SectionPairRowListValueArgumentEvaluator.hpp
  25. 35 0
      include/ls-std/io/section-pair/evaluator/SectionPairRowSingleValueArgumentEvaluator.hpp
  26. 35 0
      include/ls-std/io/section-pair/evaluator/SectionPairSectionArgumentEvaluator.hpp
  27. 36 0
      include/ls-std/io/section-pair/evaluator/SectionPairValueArgumentEvaluator.hpp
  28. 52 0
      include/ls-std/io/section-pair/model/SectionPairDocument.hpp
  29. 53 0
      include/ls-std/io/section-pair/model/SectionPairRow.hpp
  30. 45 0
      include/ls-std/io/section-pair/model/SectionPairRowListValue.hpp
  31. 45 0
      include/ls-std/io/section-pair/model/SectionPairRowSingleValue.hpp
  32. 38 0
      include/ls-std/io/section-pair/model/SectionPairRowValue.hpp
  33. 56 0
      include/ls-std/io/section-pair/model/SectionPairSection.hpp
  34. 42 0
      include/ls-std/io/section-pair/reader/SectionPairFileReader.hpp
  35. 47 0
      include/ls-std/io/section-pair/reader/SectionPairFileReaderParameter.hpp
  36. 43 0
      include/ls-std/io/section-pair/serialization/SerializableSectionPairDocument.hpp
  37. 39 0
      include/ls-std/io/section-pair/serialization/SerializableSectionPairParameter.hpp
  38. 42 0
      include/ls-std/io/section-pair/serialization/SerializableSectionPairRow.hpp
  39. 41 0
      include/ls-std/io/section-pair/serialization/SerializableSectionPairRowListValue.hpp
  40. 38 0
      include/ls-std/io/section-pair/serialization/SerializableSectionPairRowSingleValue.hpp
  41. 53 0
      include/ls-std/io/section-pair/serialization/SerializableSectionPairSection.hpp
  42. 23 0
      include/ls-std/io/section-pair/type/SectionPairDocumentTypes.hpp
  43. 23 0
      include/ls-std/io/section-pair/type/SectionPairSectionTypes.hpp
  44. 37 0
      include/ls-std/io/section-pair/validator/SectionPairDocumentValidator.hpp
  45. 35 0
      include/ls-std/io/section-pair/validator/SectionPairFileExtensionValidator.hpp
  46. 39 0
      include/ls-std/io/section-pair/validator/SectionPairIdentifierValidator.hpp
  47. 38 0
      include/ls-std/io/section-pair/validator/SectionPairRowListValueValidator.hpp
  48. 37 0
      include/ls-std/io/section-pair/validator/SectionPairRowSingleValueValidator.hpp
  49. 38 0
      include/ls-std/io/section-pair/validator/SectionPairRowValidator.hpp
  50. 38 0
      include/ls-std/io/section-pair/validator/SectionPairSectionValidator.hpp
  51. 39 0
      include/ls-std/io/section-pair/validator/SectionPairValueValidator.hpp
  52. 6 1
      include/ls-std/ls-std-core.hpp
  53. 36 6
      include/ls-std/ls-std-io.hpp
  54. 23 0
      source/ls-std/core/ConditionalFunctionExecutor.cpp
  55. 34 0
      source/ls-std/core/evaluator/IndexOutOfBoundsEvaluator.cpp
  56. 34 0
      source/ls-std/core/exception/IndexOutOfBoundsException.cpp
  57. 34 0
      source/ls-std/core/exception/WrongCallException.cpp
  58. 14 0
      source/ls-std/core/interface/IValidator.cpp
  59. 27 0
      source/ls-std/io/evaluator/FileExistenceEvaluator.cpp
  60. 0 53
      source/ls-std/io/kv/KvDocument.cpp
  61. 0 61
      source/ls-std/io/kv/KvFileReader.cpp
  62. 0 39
      source/ls-std/io/kv/KvPair.cpp
  63. 0 34
      source/ls-std/io/kv/KvParseParameter.cpp
  64. 0 106
      source/ls-std/io/kv/KvParser.cpp
  65. 24 0
      source/ls-std/io/section-pair/SectionPairMessageFormatter.cpp
  66. 28 0
      source/ls-std/io/section-pair/evaluator/SectionPairIdentifierArgumentEvaluator.cpp
  67. 28 0
      source/ls-std/io/section-pair/evaluator/SectionPairRowArgumentEvaluator.cpp
  68. 27 0
      source/ls-std/io/section-pair/evaluator/SectionPairRowListValueArgumentEvaluator.cpp
  69. 27 0
      source/ls-std/io/section-pair/evaluator/SectionPairRowSingleValueArgumentEvaluator.cpp
  70. 27 0
      source/ls-std/io/section-pair/evaluator/SectionPairSectionArgumentEvaluator.cpp
  71. 27 0
      source/ls-std/io/section-pair/evaluator/SectionPairValueArgumentEvaluator.cpp
  72. 124 0
      source/ls-std/io/section-pair/model/SectionPairDocument.cpp
  73. 108 0
      source/ls-std/io/section-pair/model/SectionPairRow.cpp
  74. 92 0
      source/ls-std/io/section-pair/model/SectionPairRowListValue.cpp
  75. 75 0
      source/ls-std/io/section-pair/model/SectionPairRowSingleValue.cpp
  76. 28 0
      source/ls-std/io/section-pair/model/SectionPairRowValue.cpp
  77. 138 0
      source/ls-std/io/section-pair/model/SectionPairSection.cpp
  78. 68 0
      source/ls-std/io/section-pair/reader/SectionPairFileReader.cpp
  79. 54 0
      source/ls-std/io/section-pair/reader/SectionPairFileReaderParameter.cpp
  80. 108 0
      source/ls-std/io/section-pair/serialization/SerializableSectionPairDocument.cpp
  81. 36 0
      source/ls-std/io/section-pair/serialization/SerializableSectionPairParameter.cpp
  82. 100 0
      source/ls-std/io/section-pair/serialization/SerializableSectionPairRow.cpp
  83. 83 0
      source/ls-std/io/section-pair/serialization/SerializableSectionPairRowListValue.cpp
  84. 38 0
      source/ls-std/io/section-pair/serialization/SerializableSectionPairRowSingleValue.cpp
  85. 208 0
      source/ls-std/io/section-pair/serialization/SerializableSectionPairSection.cpp
  86. 36 0
      source/ls-std/io/section-pair/validator/SectionPairDocumentValidator.cpp
  87. 25 0
      source/ls-std/io/section-pair/validator/SectionPairFileExtensionValidator.cpp
  88. 32 0
      source/ls-std/io/section-pair/validator/SectionPairIdentifierValidator.cpp
  89. 41 0
      source/ls-std/io/section-pair/validator/SectionPairRowListValueValidator.cpp
  90. 39 0
      source/ls-std/io/section-pair/validator/SectionPairRowSingleValueValidator.cpp
  91. 39 0
      source/ls-std/io/section-pair/validator/SectionPairRowValidator.cpp
  92. 44 0
      source/ls-std/io/section-pair/validator/SectionPairSectionValidator.cpp
  93. 37 0
      source/ls-std/io/section-pair/validator/SectionPairValueValidator.cpp
  94. 51 0
      test/cases/core/ConditionalFunctionExecutorTest.cpp
  95. 68 0
      test/cases/core/evaluator/IndexOutOfBoundsEvaluatorTest.cpp
  96. 67 0
      test/cases/core/exception/IndexOutOfBoundsExceptionTest.cpp
  97. 67 0
      test/cases/core/exception/WrongCallExceptionTest.cpp
  98. 57 0
      test/cases/io/evaluator/FileExistenceEvaluatorTest.cpp
  99. 0 106
      test/cases/io/kv/KvDocumentTest.cpp
  100. 0 152
      test/cases/io/kv/KvFileReaderTest.cpp

+ 1 - 1
.clang-format

@@ -34,7 +34,7 @@ BreakBeforeTernaryOperators: true
 BreakConstructorInitializers: BeforeColon
 BreakInheritanceList: BeforeColon
 ColumnLimit: 700
-CompactNamespaces: false
+CompactNamespaces: true
 ContinuationIndentWidth: 4
 EmptyLineAfterAccessModifier: Always
 FixNamespaceComments: false

+ 230 - 73
CMakeLists.txt

@@ -128,6 +128,7 @@ set(SOURCE_FILES_BOXING
 
 set(SOURCE_FILES_CORE
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/evaluator/EmptyStringArgumentEvaluator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/evaluator/IndexOutOfBoundsEvaluator.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/evaluator/NullPointerArgumentEvaluator.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/evaluator/NullPointerEvaluator.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/exception/EventNotHandledException.cpp
@@ -138,7 +139,9 @@ set(SOURCE_FILES_CORE
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/exception/IllegalArgumentException.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/exception/IllegalArithmeticOperationException.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/exception/IncompleteJsonException.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/exception/IndexOutOfBoundsException.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/exception/NullPointerException.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/exception/WrongCallException.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/interface/IBoxing.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/interface/IEncoding.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/interface/IEvaluator.cpp
@@ -147,8 +150,10 @@ set(SOURCE_FILES_CORE
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/interface/IReader.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/interface/ISerializable.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/interface/IStorable.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/interface/IValidator.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/interface/IWriter.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/Class.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/ConditionalFunctionExecutor.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/LibraryVersion.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/core/Version.cpp)
 
@@ -163,13 +168,38 @@ set(SOURCE_FILES_EVENT
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/event/Narrator.cpp)
 
 set(SOURCE_FILES_IO
-        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/kv/KvDocument.cpp
-        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/kv/KvFileReader.cpp
-        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/kv/KvPair.cpp
-        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/kv/KvParseParameter.cpp
-        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/kv/KvParser.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/evaluator/FileExistenceEvaluator.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/logging/Logger.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/logging/LogLevel.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/evaluator/SectionPairIdentifierArgumentEvaluator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/evaluator/SectionPairRowArgumentEvaluator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/evaluator/SectionPairRowListValueArgumentEvaluator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/evaluator/SectionPairRowSingleValueArgumentEvaluator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/evaluator/SectionPairSectionArgumentEvaluator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/evaluator/SectionPairValueArgumentEvaluator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/model/SectionPairDocument.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/model/SectionPairRow.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/model/SectionPairRowListValue.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/model/SectionPairRowSingleValue.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/model/SectionPairRowValue.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/model/SectionPairSection.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/reader/SectionPairFileReader.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/reader/SectionPairFileReaderParameter.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/serialization/SerializableSectionPairDocument.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/serialization/SerializableSectionPairParameter.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/serialization/SerializableSectionPairRow.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/serialization/SerializableSectionPairRowListValue.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/serialization/SerializableSectionPairRowSingleValue.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/serialization/SerializableSectionPairSection.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/validator/SectionPairDocumentValidator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/validator/SectionPairFileExtensionValidator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/validator/SectionPairIdentifierValidator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/validator/SectionPairRowListValueValidator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/validator/SectionPairRowSingleValueValidator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/validator/SectionPairRowValidator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/validator/SectionPairSectionValidator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/validator/SectionPairValueValidator.cpp
+        ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/section-pair/SectionPairMessageFormatter.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/xml/XmlAttribute.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/xml/XmlDeclaration.cpp
         ${CMAKE_CURRENT_SOURCE_DIR}/source/ls-std/io/xml/XmlDocument.cpp
@@ -193,13 +223,13 @@ set(SOURCE_FILES_TIME
 ####################################################################################################################
 ####################################################################################################################
 ####################################################################################################################
-# Test Files Modularization
+# Unit Test Files Modularization
 ####################################################################################################################
 ####################################################################################################################
 ####################################################################################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    set(TEST_FILES_BOXING
+    set(UNIT_TEST_FILES_BOXING
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/boxing/BooleanTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/boxing/DoubleTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/boxing/FloatTest.cpp
@@ -207,8 +237,9 @@ if (${LS_STD_BUILD_WITH_TESTS})
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/boxing/LongTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/boxing/StringTest.cpp)
 
-    set(TEST_FILES_CORE
+    set(UNIT_TEST_FILES_CORE
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/evaluator/EmptyStringArgumentEvaluatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/evaluator/IndexOutOfBoundsEvaluatorTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/evaluator/NullPointerArgumentEvaluatorTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/evaluator/NullPointerEvaluatorTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/exception/EventNotHandledExceptionTest.cpp
@@ -219,16 +250,20 @@ if (${LS_STD_BUILD_WITH_TESTS})
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/exception/IllegalArgumentExceptionTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/exception/IllegalArithmeticOperationExceptionTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/exception/IncompleteJsonExceptionTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/exception/IndexOutOfBoundsExceptionTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/exception/NullPointerExceptionTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/exception/WrongCallExceptionTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/ClassTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/ConditionalFunctionExecutorTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/LibraryVersionTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/core/VersionTest.cpp
-            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/core/ClassWrapper.cpp)
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/core/ClassWrapper.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/core/MathOddValidator.cpp)
 
-    set(TEST_FILES_ENCODING
+    set(UNIT_TEST_FILES_ENCODING
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/encoding/Base64Test.cpp)
 
-    set(TEST_FILES_EVENT
+    set(UNIT_TEST_FILES_EVENT
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/event/serialization/SerializableJsonEventTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/event/EventHandlerTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/event/EventManagerTest.cpp
@@ -243,14 +278,38 @@ if (${LS_STD_BUILD_WITH_TESTS})
             ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/event/TestDataCar.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/event/TestDataMercedesCar.cpp)
 
-    set(TEST_FILES_IO
-            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/kv/KvDocumentTest.cpp
-            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/kv/KvFileReaderTest.cpp
-            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/kv/KvPairTest.cpp
-            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/kv/KvParseParameterTest.cpp
-            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/kv/KvParserTest.cpp
+    set(UNIT_TEST_FILES_IO
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/evaluator/FileExistenceEvaluatorTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/logging/LoggerTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/logging/LogLevelTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/evaluator/SectionPairIdentifierArgumentEvaluatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/evaluator/SectionPairRowArgumentEvaluatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/evaluator/SectionPairRowListValueArgumentEvaluatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/evaluator/SectionPairRowSingleValueArgumentEvaluatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/evaluator/SectionPairSectionArgumentEvaluatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/evaluator/SectionPairValueArgumentEvaluatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/model/SectionPairDocumentTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/model/SectionPairRowListValueTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/model/SectionPairRowSingleValueTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/model/SectionPairRowTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/model/SectionPairSectionTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/reader/SectionPairFileReaderParameterTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/reader/SectionPairFileReaderTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/serialization/SerializableSectionPairDocumentTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/serialization/SerializableSectionPairParameterTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/serialization/SerializableSectionPairRowListValueTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/serialization/SerializableSectionPairRowSingleValueTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/serialization/SerializableSectionPairRowTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/serialization/SerializableSectionPairSectionTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/validator/SectionPairDocumentValidatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/validator/SectionPairFileExtensionValidatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/validator/SectionPairIdentifierValidatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/validator/SectionPairRowListValueValidatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/validator/SectionPairRowSingleValueValidatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/validator/SectionPairRowValidatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/validator/SectionPairSectionValidatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/validator/SectionPairValueValidatorTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/SectionPairMessageFormatterTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/xml/XmlAttributeTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/xml/XmlDeclarationTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/xml/XmlDocumentTest.cpp
@@ -265,95 +324,154 @@ if (${LS_STD_BUILD_WITH_TESTS})
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/FileWriterTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/StandardOutputWriterTest.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/StorableFileTest.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/io/section-pair/SectionPairDocumentProvider.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/io/section-pair/SectionPairSectionProvider.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/io/section-pair/SerializableSectionPairRowProvider.cpp
             ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/io/xml/TestDataFactory.cpp
-            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/io/xml/XmlParserTestWrapper.cpp)
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/io/xml/XmlParserTestWrapper.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/io/MockFileExistenceEvaluator.cpp
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/io/MockFileReader.cpp)
 
-    set(TEST_FILES_SERIALIZATION
+    set(UNIT_TEST_FILES_SERIALIZATION
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/serialization/JsonTest.cpp)
 
-    set(TEST_FILES_TIME
+    set(UNIT_TEST_FILES_TIME
             ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/time/DateTest.cpp)
 endif ()
 
 ####################################################################################################################
 ####################################################################################################################
 ####################################################################################################################
-# Test Suite Builds
+# Unit Test Suite Builds
 ####################################################################################################################
 ####################################################################################################################
 ####################################################################################################################
 
 ##########################################################
-# Build Tests (boxing)
+# Unit Build Tests (boxing)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_BOXING}: Building tests...")
-    add_executable(${MODULE_NAME_BOXING}-test ${TEST_FILES_BOXING})
+    message("${MODULE_NAME_BOXING}: Building unit tests...")
+    add_executable(${MODULE_NAME_BOXING}-unit-test ${UNIT_TEST_FILES_BOXING})
 endif ()
 
 ##########################################################
-# Build Tests (core)
+# Unit Build Tests (core)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_CORE}: Building tests...")
-    add_executable(${MODULE_NAME_CORE}-test ${TEST_FILES_CORE})
+    message("${MODULE_NAME_CORE}: Building unit tests...")
+    add_executable(${MODULE_NAME_CORE}-unit-test ${UNIT_TEST_FILES_CORE})
 endif ()
 
 ##########################################################
-# Build Tests (encoding)
+# Unit Build Tests (encoding)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_ENCODING}: Building tests...")
-    add_executable(${MODULE_NAME_ENCODING}-test ${TEST_FILES_ENCODING})
+    message("${MODULE_NAME_ENCODING}: Building unit tests...")
+    add_executable(${MODULE_NAME_ENCODING}-unit-test ${UNIT_TEST_FILES_ENCODING})
 endif ()
 
 ##########################################################
-# Build Tests (event)
+# Unit Build Tests (event)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_EVENT}: Building tests...")
-    add_executable(${MODULE_NAME_EVENT}-test ${TEST_FILES_EVENT})
+    message("${MODULE_NAME_EVENT}: Building unit tests...")
+    add_executable(${MODULE_NAME_EVENT}-unit-test ${UNIT_TEST_FILES_EVENT})
 endif ()
 
 ##########################################################
-# Build Tests (io)
+# Unit Build Tests (io)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_IO}: Building tests...")
-    add_executable(${MODULE_NAME_IO}-test
+    message("${MODULE_NAME_IO}: Building unit tests...")
+    add_executable(${MODULE_NAME_IO}-unit-test
             ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/TestHelper.cpp
-            ${TEST_FILES_IO})
+            ${UNIT_TEST_FILES_IO})
 endif ()
 
 ##########################################################
-# Build Tests (time)
+# Unit Build Tests (time)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_TIME}: Building tests...")
-    add_executable(${MODULE_NAME_TIME}-test ${TEST_FILES_TIME})
+    message("${MODULE_NAME_TIME}: Building unit tests...")
+    add_executable(${MODULE_NAME_TIME}-unit-test ${UNIT_TEST_FILES_TIME})
 endif ()
 
 ##########################################################
-# Build Tests (all)
+# Unit Build Tests (all)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${PROJECT_NAME}: Building tests...")
+    message("${PROJECT_NAME}: Building unit tests...")
+    add_executable(${PROJECT_NAME}-unit-test
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/TestHelper.cpp
+            ${UNIT_TEST_FILES_BOXING}
+            ${UNIT_TEST_FILES_CORE}
+            ${UNIT_TEST_FILES_ENCODING}
+            ${UNIT_TEST_FILES_EVENT}
+            ${UNIT_TEST_FILES_IO}
+            ${UNIT_TEST_FILES_SERIALIZATION}
+            ${UNIT_TEST_FILES_TIME})
+endif ()
+
+####################################################################################################################
+####################################################################################################################
+####################################################################################################################
+# Integration Test Files Modularization
+####################################################################################################################
+####################################################################################################################
+####################################################################################################################
+
+if (${LS_STD_BUILD_WITH_TESTS})
+    set(INTEGRATION_TEST_FILES_IO
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/cases/io/section-pair/reader/SectionPairFileReaderIT.cpp)
+endif ()
+
+####################################################################################################################
+####################################################################################################################
+####################################################################################################################
+# Integration Test Suite Builds
+####################################################################################################################
+####################################################################################################################
+####################################################################################################################
+
+##########################################################
+# Integration Build Tests (io)
+##########################################################
+
+if (${LS_STD_BUILD_WITH_TESTS})
+    message("${MODULE_NAME_IO}: Building integration tests...")
+    add_executable(${MODULE_NAME_IO}-integration-test
+            ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/TestHelper.cpp
+            ${INTEGRATION_TEST_FILES_IO})
+endif ()
+
+####################################################################################################################
+####################################################################################################################
+####################################################################################################################
+# Whole Test Suite Builds
+####################################################################################################################
+####################################################################################################################
+####################################################################################################################
+
+if (${LS_STD_BUILD_WITH_TESTS})
+    message("${PROJECT_NAME}: Building all tests...")
     add_executable(${PROJECT_NAME}-test
             ${CMAKE_CURRENT_SOURCE_DIR}/test/classes/TestHelper.cpp
-            ${TEST_FILES_BOXING}
-            ${TEST_FILES_CORE}
-            ${TEST_FILES_ENCODING}
-            ${TEST_FILES_EVENT}
-            ${TEST_FILES_IO}
-            ${TEST_FILES_SERIALIZATION}
-            ${TEST_FILES_TIME})
+            ${UNIT_TEST_FILES_BOXING}
+            ${UNIT_TEST_FILES_CORE}
+            ${UNIT_TEST_FILES_ENCODING}
+            ${UNIT_TEST_FILES_EVENT}
+            ${UNIT_TEST_FILES_IO}
+            ${INTEGRATION_TEST_FILES_IO}
+            ${UNIT_TEST_FILES_SERIALIZATION}
+            ${UNIT_TEST_FILES_TIME})
 endif ()
 
 ####################################################################################################################
@@ -472,32 +590,31 @@ endif ()
 ####################################################################################################################
 ####################################################################################################################
 ####################################################################################################################
-# Test Suite: Linking
+# Unit Test Suite: Linking
 ####################################################################################################################
 ####################################################################################################################
 ####################################################################################################################
 
 ##########################################################
-# Linking (boxing)
+# Unit Linking (boxing)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_BOXING}: Linking libraries for test application...")
-    target_link_libraries(${MODULE_NAME_BOXING}-test
+    message("${MODULE_NAME_BOXING}: Linking libraries for unit test application...")
+    target_link_libraries(${MODULE_NAME_BOXING}-unit-test
             gtest
-            gmock
             gtest_main
             "${MODULE_NAME_BOXING}"
             "${MODULE_NAME_CORE}")
 endif ()
 
 ##########################################################
-# Linking (core)
+# Unit Linking (core)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_CORE}: Linking libraries for test application...")
-    target_link_libraries(${MODULE_NAME_CORE}-test
+    message("${MODULE_NAME_CORE}: Linking libraries for unit test application...")
+    target_link_libraries(${MODULE_NAME_CORE}-unit-test
             gtest
             gmock
             gtest_main
@@ -505,40 +622,38 @@ if (${LS_STD_BUILD_WITH_TESTS})
 endif ()
 
 ##########################################################
-# Linking (encoding)
+# Unit Linking (encoding)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_ENCODING}: Linking libraries for test application...")
-    target_link_libraries(${MODULE_NAME_ENCODING}-test
+    message("${MODULE_NAME_ENCODING}: Linking libraries for unit test application...")
+    target_link_libraries(${MODULE_NAME_ENCODING}-unit-test
             gtest
-            gmock
             gtest_main
             "${MODULE_NAME_ENCODING}"
             "${MODULE_NAME_CORE}")
 endif ()
 
 ##########################################################
-# Linking (event)
+# Unit Linking (event)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_EVENT}: Linking libraries for test application...")
-    target_link_libraries(${MODULE_NAME_EVENT}-test
+    message("${MODULE_NAME_EVENT}: Linking libraries for unit test application...")
+    target_link_libraries(${MODULE_NAME_EVENT}-unit-test
             gtest
-            gmock
             gtest_main
             "${MODULE_NAME_EVENT}"
             "${MODULE_NAME_CORE}")
 endif ()
 
 ##########################################################
-# Linking (io)
+# Unit Linking (io)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_IO}: Linking libraries for test application...")
-    target_link_libraries(${MODULE_NAME_IO}-test
+    message("${MODULE_NAME_IO}: Linking libraries for unit test application...")
+    target_link_libraries(${MODULE_NAME_IO}-unit-test
             gtest
             gmock
             gtest_main
@@ -547,25 +662,67 @@ if (${LS_STD_BUILD_WITH_TESTS})
 endif ()
 
 ##########################################################
-# Linking (time)
+# Unit Linking (time)
+##########################################################
+
+if (${LS_STD_BUILD_WITH_TESTS})
+    message("${MODULE_NAME_TIME}: Linking libraries for unit test application...")
+    target_link_libraries(${MODULE_NAME_TIME}-unit-test
+            gtest
+            gtest_main
+            "${MODULE_NAME_TIME}"
+            "${MODULE_NAME_CORE}")
+endif ()
+
+##########################################################
+# Unit Linking (all)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${MODULE_NAME_TIME}: Linking libraries for test application...")
-    target_link_libraries(${MODULE_NAME_TIME}-test
+    message("${PROJECT_NAME}: Linking libraries for unit test application...")
+    target_link_libraries(${PROJECT_NAME}-unit-test
             gtest
             gmock
             gtest_main
+            "${MODULE_NAME_BOXING}"
+            "${MODULE_NAME_ENCODING}"
+            "${MODULE_NAME_EVENT}"
+            "${MODULE_NAME_IO}"
             "${MODULE_NAME_TIME}"
             "${MODULE_NAME_CORE}")
 endif ()
 
+####################################################################################################################
+####################################################################################################################
+####################################################################################################################
+# Integration Test Suite: Linking
+####################################################################################################################
+####################################################################################################################
+####################################################################################################################
+
 ##########################################################
-# Linking (all)
+# Integration Linking (io)
 ##########################################################
 
 if (${LS_STD_BUILD_WITH_TESTS})
-    message("${PROJECT_NAME}: Linking libraries for test application...")
+    message("${MODULE_NAME_IO}: Linking libraries for integration test application...")
+    target_link_libraries(${MODULE_NAME_IO}-integration-test
+            gtest
+            gtest_main
+            "${MODULE_NAME_IO}"
+            "${MODULE_NAME_CORE}")
+endif ()
+
+####################################################################################################################
+####################################################################################################################
+####################################################################################################################
+# Whole Test Suite: Linking
+####################################################################################################################
+####################################################################################################################
+####################################################################################################################
+
+if (${LS_STD_BUILD_WITH_TESTS})
+    message("${PROJECT_NAME}: Linking libraries for whole test application...")
     target_link_libraries(${PROJECT_NAME}-test
             gtest
             gmock

+ 6 - 2
README.md

@@ -36,7 +36,10 @@ A __Date__ class comes with this submodule, which you can use to represent a dat
 
 - __AppleClang__ compiler is now officially supported
 - exceptions provided by __core__ submodule now offer a constructor for passing dedicated messages
-- evaluators have been added, which can check a state of variables and throw a dedicated exception in a single line and more convenient way
+- evaluators have been added, which can check a state of variables and throw a dedicated exception in a single line and
+  more convenient way
+- a section-pair file standard has been implemented and is provided via __ls-std-io__ module, a definition of this
+  standard can be found in the libraries __doc__ folder
 
 #### Improvements ####
 
@@ -47,6 +50,7 @@ A __Date__ class comes with this submodule, which you can use to represent a dat
 - fetching the library version can now be achieved by using a dedicated __LibraryVersion__ class - the usage of a static function for this purpose has been removed completely
 - missing nodiscard attributes have been added to library classes
 - rename "types" folder in __core__ submodule to stick to naming convention
+- key-value file standard has been removed from this library and is replaced by section-pair file standard
 
 #### Fixes ####
 
@@ -76,7 +80,7 @@ Building this library would result into providing binaries for each library modu
 | __ls-std-encoding__ | library (static / dynamic) |
 | __ls-std-event__    | library (static / dynamic) |
 | __ls-std-io__       | library (static / dynamic) |
-| __time__            | library (static / dynamic) |
+| __ls-std-time__     | library (static / dynamic) |
 
 #### Prerequisites ####
 

+ 0 - 13
doc/kv-file-definition.md

@@ -1,13 +0,0 @@
-# Key Value File - Definition #
-
-This document defines the standard of a key value file (__.kv__).
-
-1. A Key Value File needs to have the file extension "__.kv__".
-2. A Key Value Pair, which is defined in such a file, has the following format:
-   ```
-   port=8080;
-   ```
-   The key is defined at the beginning of a line followed by an "__=__" sign for assignment.  
-   The value (which is the assigment) comes write after the "__=__" sign. Please note that no quotes are required.
-   To mark the end of a pair definition a semicolon "__;__" is required.
-3. Every line in a __.kv__ file, which does not contain a "__=__" and a "__;__" sign, will be considered as a comment. Also, adding any text to a line after a semicolon has been set - to mark the end of a pair definition - will be ignored.

二进制
doc/section-pair-2023-standard.odt


+ 33 - 0
include/ls-std/core/ConditionalFunctionExecutor.hpp

@@ -0,0 +1,33 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-13
+* Changed:         2023-02-21
+*
+* */
+
+#ifndef LS_STD_CONDITIONAL_FUNCTION_EXECUTOR_HPP
+#define LS_STD_CONDITIONAL_FUNCTION_EXECUTOR_HPP
+
+#include <functional>
+#include <ls-std/os/dynamic-goal.hpp>
+
+namespace ls::std::core
+{
+  class LS_STD_DYNAMIC_GOAL ConditionalFunctionExecutor
+  {
+    public:
+
+      explicit ConditionalFunctionExecutor(bool _condition);
+      ~ConditionalFunctionExecutor();
+
+      void execute(const ::std::function<void()> &_function) const;
+
+    private:
+
+      bool condition{};
+  };
+}
+
+#endif

+ 36 - 0
include/ls-std/core/evaluator/IndexOutOfBoundsEvaluator.hpp

@@ -0,0 +1,36 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-10
+*
+* */
+
+#ifndef LS_STD_INDEX_OUT_OF_BOUNDS_EVALUATOR_EVALUATOR_HPP
+#define LS_STD_INDEX_OUT_OF_BOUNDS_EVALUATOR_EVALUATOR_HPP
+
+#include <ls-std/core/interface/IEvaluator.hpp>
+#include <string>
+
+namespace ls::std::core
+{
+  class IndexOutOfBoundsEvaluator : public ls::std::core::interface_type::IEvaluator
+  {
+    public:
+
+      explicit IndexOutOfBoundsEvaluator(size_t _index, size_t _size);
+      explicit IndexOutOfBoundsEvaluator(size_t _index, size_t _size, ::std::string _message);
+      ~IndexOutOfBoundsEvaluator() override;
+
+      void evaluate() override;
+
+    private:
+
+      size_t index{};
+      ::std::string message{};
+      size_t size{};
+  };
+}
+
+#endif

+ 2 - 2
include/ls-std/core/evaluator/NullPointerEvaluator.hpp

@@ -3,7 +3,7 @@
 * Company:         Lynar Studios
 * E-Mail:          webmaster@lynarstudios.com
 * Created:         2023-02-08
-* Changed:         2023-02-08
+* Changed:         2023-02-10
 *
 * */
 
@@ -16,7 +16,7 @@
 
 namespace ls::std::core
 {
-  class NullPointerEvaluator : public ls::std::core::interface_type::IEvaluator
+  class NullPointerEvaluator : public ls::std::core::interface_type::IEvaluator // TODO: add missing dynamic goal
   {
     public:
 

+ 35 - 0
include/ls-std/core/exception/IndexOutOfBoundsException.hpp

@@ -0,0 +1,35 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-10
+*
+* */
+
+#ifndef LS_STD_INDEX_OUT_OF_BOUNDS_EXCEPTION_HPP
+#define LS_STD_INDEX_OUT_OF_BOUNDS_EXCEPTION_HPP
+
+#include <exception>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::core
+{
+  class LS_STD_DYNAMIC_GOAL IndexOutOfBoundsException : public ::std::exception
+  {
+    public:
+
+      IndexOutOfBoundsException();
+      explicit IndexOutOfBoundsException(::std::string _message);
+      ~IndexOutOfBoundsException() override;
+
+      [[nodiscard]] const char *what() const noexcept override;
+
+    private:
+
+      ::std::string message{};
+  };
+}
+
+#endif

+ 35 - 0
include/ls-std/core/exception/WrongCallException.hpp

@@ -0,0 +1,35 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-11
+*
+* */
+
+#ifndef LS_STD_WRONG_CALL_EXCEPTION_HPP
+#define LS_STD_WRONG_CALL_EXCEPTION_HPP
+
+#include <exception>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::core
+{
+  class LS_STD_DYNAMIC_GOAL WrongCallException : public ::std::exception // TODO: remove, really makes no sense :D
+  {
+    public:
+
+      WrongCallException();
+      explicit WrongCallException(::std::string _message);
+      ~WrongCallException() override;
+
+      [[nodiscard]] const char *what() const noexcept override;
+
+    private:
+
+      ::std::string message{};
+  };
+}
+
+#endif

+ 28 - 0
include/ls-std/core/interface/IValidator.hpp

@@ -0,0 +1,28 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-08
+* Changed:         2023-02-08
+*
+* */
+
+#ifndef LS_STD_I_VALIDATOR_HPP
+#define LS_STD_I_VALIDATOR_HPP
+
+#include <ls-std/os/dynamic-goal.hpp>
+
+namespace ls::std::core::interface_type
+{
+  class LS_STD_DYNAMIC_GOAL IValidator
+  {
+    public:
+
+      IValidator();
+      virtual ~IValidator();
+
+      virtual bool isValid() = 0;
+  };
+}
+
+#endif

+ 1 - 2
include/ls-std/io/File.hpp

@@ -3,7 +3,7 @@
  * Company:         Lynar Studios
  * E-Mail:          webmaster@lynarstudios.com
  * Created:         2020-08-15
- * Changed:         2023-02-06
+ * Changed:         2023-02-18
  *
  * */
 
@@ -17,7 +17,6 @@
 #include <list>
 #include <ls-std/core/Class.hpp>
 #include <ls-std/os/dynamic-goal.hpp>
-#include <regex>
 #include <string>
 #include <vector>
 #ifdef _WIN32

+ 35 - 0
include/ls-std/io/evaluator/FileExistenceEvaluator.hpp

@@ -0,0 +1,35 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-21
+* Changed:         2023-02-21
+*
+* */
+
+#ifndef LS_STD_FILE_EXISTENCE_EVALUATOR_HPP
+#define LS_STD_FILE_EXISTENCE_EVALUATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IEvaluator.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL FileExistenceEvaluator : public ls::std::core::Class, public ls::std::core::interface_type::IEvaluator
+  {
+    public:
+
+      explicit FileExistenceEvaluator(::std::string _filePath);
+      ~FileExistenceEvaluator() override;
+
+      void evaluate() override;
+
+    private:
+
+      ::std::string filePath{};
+  };
+}
+
+#endif

+ 0 - 42
include/ls-std/io/kv/KvDocument.hpp

@@ -1,42 +0,0 @@
-/*
- * Author:          Patrick-Christopher Mattulat
- * Company:         Lynar Studios
- * E-Mail:          webmaster@lynarstudios.com
- * Created:         2020-12-25
- * Changed:         2023-02-08
- *
- * */
-
-#ifndef LS_STD_KV_DOCUMENT_HPP
-#define LS_STD_KV_DOCUMENT_HPP
-
-#include "KvPair.hpp"
-#include <ls-std/core/Class.hpp>
-#include <ls-std/core/type/KvTypes.hpp>
-#include <ls-std/os/dynamic-goal.hpp>
-#include <map>
-
-namespace ls::std::io
-{
-  class LS_STD_DYNAMIC_GOAL KvDocument : public ls::std::core::Class
-  {
-    public:
-
-      KvDocument();
-      ~KvDocument() override;
-
-      bool addPair(ls::std::io::KvPair _pair); // nodiscard is optional here
-      void clear();
-      [[nodiscard]] ::std::map<ls::std::core::type::kv_key, ls::std::io::KvPair> getPairs();
-      [[nodiscard]] bool hasPair(const ls::std::core::type::kv_key &_key);
-      bool removePair(const ls::std::core::type::kv_key &_key); // nodiscard is optional here
-
-    private:
-
-      ::std::map<ls::std::core::type::kv_key, ls::std::io::KvPair> pairs{};
-
-      [[nodiscard]] bool _hasPair(const ls::std::core::type::kv_key &_key);
-  };
-}
-
-#endif

+ 0 - 49
include/ls-std/io/kv/KvFileReader.hpp

@@ -1,49 +0,0 @@
-/*
- * Author:          Patrick-Christopher Mattulat
- * Company:         Lynar Studios
- * E-Mail:          webmaster@lynarstudios.com
- * Created:         2020-12-25
- * Changed:         2023-02-06
- *
- * */
-
-#ifndef LS_STD_KV_FILE_READER_HPP
-#define LS_STD_KV_FILE_READER_HPP
-
-#include <ls-std/core/Class.hpp>
-#include <ls-std/core/interface/IReader.hpp>
-#include <ls-std/io/File.hpp>
-#include <ls-std/io/kv/KvDocument.hpp>
-#include <ls-std/os/dynamic-goal.hpp>
-#include <memory>
-
-namespace ls::std::io
-{
-  class LS_STD_DYNAMIC_GOAL KvFileReader : public ls::std::core::Class, public ls::std::core::interface_type::IReader
-  {
-    public:
-
-      explicit KvFileReader(const ::std::shared_ptr<ls::std::io::KvDocument> &_document, const ::std::string &_absolutePath);
-      ~KvFileReader() override;
-
-      // implementation
-
-      ls::std::core::type::byte_field read() override; // nodiscard is optional here
-
-      // additional functionality
-
-      [[nodiscard]] ::std::shared_ptr<ls::std::io::KvDocument> getDocument();
-      void setDocument(const ::std::shared_ptr<ls::std::io::KvDocument> &_document);
-      void setFile(const ls::std::io::File &_kvFile);
-
-    private:
-
-      ::std::shared_ptr<ls::std::io::KvDocument> document{};
-      ls::std::io::File kvFile;
-
-      void _assignDocument(const ::std::shared_ptr<ls::std::io::KvDocument> &_document);
-      void _assignFile(ls::std::io::File _kvFile);
-  };
-}
-
-#endif

+ 0 - 39
include/ls-std/io/kv/KvPair.hpp

@@ -1,39 +0,0 @@
-/*
- * Author:          Patrick-Christopher Mattulat
- * Company:         Lynar Studios
- * E-Mail:          webmaster@lynarstudios.com
- * Created:         2020-12-25
- * Changed:         2023-02-08
- *
- * */
-
-#ifndef LS_STD_KV_PAIR_HPP
-#define LS_STD_KV_PAIR_HPP
-
-#include <ls-std/core/Class.hpp>
-#include <ls-std/core/type/KvTypes.hpp>
-#include <ls-std/os/dynamic-goal.hpp>
-
-namespace ls::std::io
-{
-  class LS_STD_DYNAMIC_GOAL KvPair : public ls::std::core::Class
-  {
-    public:
-
-      explicit KvPair(const ls::std::core::type::kv_key &_key, ls::std::core::type::kv_value _value);
-      ~KvPair() override;
-
-      [[nodiscard]] ls::std::core::type::kv_key getKey();
-      [[nodiscard]] ls::std::core::type::kv_value getValue();
-      void setValue(const ls::std::core::type::kv_value &_value);
-
-    private:
-
-      ls::std::core::type::kv_key key{};
-      ls::std::core::type::kv_value value{};
-
-      void _assignKey(const ls::std::core::type::kv_key &_key);
-  };
-}
-
-#endif

+ 0 - 37
include/ls-std/io/kv/KvParseParameter.hpp

@@ -1,37 +0,0 @@
-/*
- * Author:          Patrick-Christopher Mattulat
- * Company:         Lynar Studios
- * E-Mail:          webmaster@lynarstudios.com
- * Created:         2020-12-25
- * Changed:         2023-02-06
- *
- * */
-
-#ifndef LS_STD_KV_PARSE_DATA_HPP
-#define LS_STD_KV_PARSE_DATA_HPP
-
-#include <ls-std/os/dynamic-goal.hpp>
-#include <string>
-
-namespace ls::std::io
-{
-  class LS_STD_DYNAMIC_GOAL KvParseParameter
-  {
-    public:
-
-      KvParseParameter();
-      ~KvParseParameter();
-
-      [[nodiscard]] ::std::string::size_type getIndex() const;
-      [[nodiscard]] ::std::string getLine();
-      void setIndex(const ::std::string::size_type &_index);
-      void setLine(const ::std::string &_line);
-
-    private:
-
-      ::std::string::size_type index{};
-      ::std::string line{};
-  };
-}
-
-#endif

+ 0 - 48
include/ls-std/io/kv/KvParser.hpp

@@ -1,48 +0,0 @@
-/*
- * Author:          Patrick-Christopher Mattulat
- * Company:         Lynar Studios
- * E-Mail:          webmaster@lynarstudios.com
- * Created:         2020-12-25
- * Changed:         2023-02-08
- *
- * */
-
-#ifndef LS_STD_KV_PARSER_HPP
-#define LS_STD_KV_PARSER_HPP
-
-#include "KvDocument.hpp"
-#include "KvParseParameter.hpp"
-#include <ls-std/core/Class.hpp>
-#include <ls-std/core/type/Types.hpp>
-#include <ls-std/os/dynamic-goal.hpp>
-#include <memory>
-
-namespace ls::std::io
-{
-  class LS_STD_DYNAMIC_GOAL KvParser : public ls::std::core::Class
-  {
-    public:
-
-      explicit KvParser(const ::std::shared_ptr<ls::std::io::KvDocument> &_document);
-      ~KvParser() override;
-
-      [[nodiscard]] ::std::shared_ptr<ls::std::io::KvDocument> getDocument();
-      void parse(const ls::std::core::type::byte_field &_data);
-      void setDocument(const ::std::shared_ptr<ls::std::io::KvDocument> &_document);
-
-    private:
-
-      ::std::shared_ptr<ls::std::io::KvDocument> document{};
-
-      void _assignDocument(const ::std::shared_ptr<ls::std::io::KvDocument> &_document);
-      [[nodiscard]] static bool _contains(const ::std::string &_text, const ::std::string &_searchText);
-      [[nodiscard]] static bool _lineHasPair(ls::std::io::KvParseParameter &_parseParameter);
-      void _parse(const ls::std::core::type::byte_field &_data);
-      void _parsePair(ls::std::io::KvParseParameter &_parseParameter);
-      [[nodiscard]] static ls::std::io::KvParseParameter _readLine(const ls::std::core::type::byte_field &_data, ::std::string::size_type _index);
-      static void _readLineWithUnixLineBreak(ls::std::io::KvParseParameter &_parseParameter);
-      static void _readLineWithWindowsLineBreak(ls::std::io::KvParseParameter &_parseParameter);
-  };
-}
-
-#endif

+ 29 - 0
include/ls-std/io/section-pair/SectionPairMessageFormatter.hpp

@@ -0,0 +1,29 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-22
+* Changed:         2023-02-22
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_MESSAGE_FORMATTER_HPP
+#define LS_STD_SECTION_PAIR_MESSAGE_FORMATTER_HPP
+
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairMessageFormatter
+  {
+    public:
+
+      SectionPairMessageFormatter();
+      ~SectionPairMessageFormatter();
+
+      [[nodiscard]] static ::std::string getFormattedMessage(const ::std::string &_message);
+  };
+}
+
+#endif

+ 23 - 0
include/ls-std/io/section-pair/SectionPairRowEnumType.hpp

@@ -0,0 +1,23 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-08
+* Changed:         2023-02-10
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_ROW_ENUM_TYPE_HPP
+#define LS_STD_SECTION_PAIR_ROW_ENUM_TYPE_HPP
+
+namespace ls::std::io
+{
+  enum SectionPairRowEnumType
+  {
+    SECTION_PAIR_ROW_NOT_IMPLEMENTED = 0,
+    SECTION_PAIR_ROW_LIST_VALUE,
+    SECTION_PAIR_ROW_SINGLE_VALUE
+  };
+}
+
+#endif

+ 21 - 0
include/ls-std/io/section-pair/SectionPairTypes.hpp

@@ -0,0 +1,21 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-10
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_TYPES_HPP
+#define LS_STD_SECTION_PAIR_TYPES_HPP
+
+#include <string>
+
+namespace ls::std::io
+{
+  using section_pair_identifier = ::std::string;
+  using section_pair_row_value = ::std::string;
+}
+
+#endif

+ 35 - 0
include/ls-std/io/section-pair/evaluator/SectionPairIdentifierArgumentEvaluator.hpp

@@ -0,0 +1,35 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-09
+* Changed:         2023-02-19
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_IDENTIFIER_ARGUMENT_EVALUATOR_HPP
+#define LS_STD_SECTION_PAIR_IDENTIFIER_ARGUMENT_EVALUATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IEvaluator.hpp>
+#include <ls-std/io/section-pair/SectionPairTypes.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairIdentifierArgumentEvaluator : public ls::std::core::interface_type::IEvaluator, public ls::std::core::Class
+  {
+    public:
+
+      explicit SectionPairIdentifierArgumentEvaluator(ls::std::io::section_pair_identifier _identifier);
+      ~SectionPairIdentifierArgumentEvaluator() override;
+
+      void evaluate() override;
+
+    private:
+
+      ls::std::io::section_pair_identifier identifier{};
+  };
+}
+
+#endif

+ 35 - 0
include/ls-std/io/section-pair/evaluator/SectionPairRowArgumentEvaluator.hpp

@@ -0,0 +1,35 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-20
+* Changed:         2023-02-20
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_ROW_ARGUMENT_EVALUATOR_HPP
+#define LS_STD_SECTION_PAIR_ROW_ARGUMENT_EVALUATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IEvaluator.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairRowArgumentEvaluator : public ls::std::core::Class, public ls::std::core::interface_type::IEvaluator
+  {
+    public:
+
+      explicit SectionPairRowArgumentEvaluator(::std::string _sectionPairRow);
+      ~SectionPairRowArgumentEvaluator() override;
+
+      void evaluate() override;
+
+    private:
+
+      ::std::string sectionPairRow{};
+  };
+}
+
+#endif

+ 35 - 0
include/ls-std/io/section-pair/evaluator/SectionPairRowListValueArgumentEvaluator.hpp

@@ -0,0 +1,35 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-20
+* Changed:         2023-02-20
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_ROW_LIST_VALUE_ARGUMENT_EVALUATOR_HPP
+#define LS_STD_SECTION_PAIR_ROW_LIST_VALUE_ARGUMENT_EVALUATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IEvaluator.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairRowListValueArgumentEvaluator : public ls::std::core::Class, public ls::std::core::interface_type::IEvaluator
+  {
+    public:
+
+      explicit SectionPairRowListValueArgumentEvaluator(::std::string _listValueRow);
+      ~SectionPairRowListValueArgumentEvaluator() override;
+
+      void evaluate() override;
+
+    private:
+
+      ::std::string listValueRow{};
+  };
+}
+
+#endif

+ 35 - 0
include/ls-std/io/section-pair/evaluator/SectionPairRowSingleValueArgumentEvaluator.hpp

@@ -0,0 +1,35 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-19
+* Changed:         2023-02-19
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_ROW_SINGLE_VALUE_ARGUMENT_EVALUATOR_HPP
+#define LS_STD_SECTION_PAIR_ROW_SINGLE_VALUE_ARGUMENT_EVALUATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IEvaluator.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairRowSingleValueArgumentEvaluator : public ls::std::core::Class, public ls::std::core::interface_type::IEvaluator
+  {
+    public:
+
+      explicit SectionPairRowSingleValueArgumentEvaluator(::std::string _singleValueRow);
+      ~SectionPairRowSingleValueArgumentEvaluator() override;
+
+      void evaluate() override;
+
+    private:
+
+      ::std::string singleValueRow{};
+  };
+}
+
+#endif

+ 35 - 0
include/ls-std/io/section-pair/evaluator/SectionPairSectionArgumentEvaluator.hpp

@@ -0,0 +1,35 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-20
+* Changed:         2023-02-20
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_SECTION_ARGUMENT_EVALUATOR_HPP
+#define LS_STD_SECTION_PAIR_SECTION_ARGUMENT_EVALUATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IEvaluator.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairSectionArgumentEvaluator : public ls::std::core::Class, public ls::std::core::interface_type::IEvaluator
+  {
+    public:
+
+      explicit SectionPairSectionArgumentEvaluator(::std::string _section);
+      ~SectionPairSectionArgumentEvaluator() override;
+
+      void evaluate() override;
+
+    private:
+
+      ::std::string section{};
+  };
+}
+
+#endif

+ 36 - 0
include/ls-std/io/section-pair/evaluator/SectionPairValueArgumentEvaluator.hpp

@@ -0,0 +1,36 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-19
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_VALUE_ARGUMENT_EVALUATOR_HPP
+#define LS_STD_SECTION_PAIR_VALUE_ARGUMENT_EVALUATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IEvaluator.hpp>
+#include <ls-std/io/section-pair/SectionPairTypes.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairValueArgumentEvaluator : public ls::std::core::interface_type::IEvaluator, public ls::std::core::Class
+  {
+    public:
+
+      explicit SectionPairValueArgumentEvaluator(ls::std::io::section_pair_row_value _value);
+      ~SectionPairValueArgumentEvaluator() override;
+
+      void evaluate() override;
+
+    private:
+
+      ls::std::io::section_pair_row_value value{};
+  };
+}
+
+#endif

+ 52 - 0
include/ls-std/io/section-pair/model/SectionPairDocument.hpp

@@ -0,0 +1,52 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-15
+* Changed:         2023-02-21
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_DOCUMENT_HPP
+#define LS_STD_SECTION_PAIR_DOCUMENT_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/ISerializable.hpp>
+#include <ls-std/io/section-pair/SectionPairTypes.hpp>
+#include <ls-std/io/section-pair/type/SectionPairDocumentTypes.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <memory>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairDocument : public ::std::enable_shared_from_this<SectionPairDocument>, public ls::std::core::Class, public ls::std::core::interface_type::ISerializable
+  {
+    public:
+
+      SectionPairDocument();
+      ~SectionPairDocument() override;
+
+      void add(const section_pair_document_section_list_element &_section);
+      void clear();
+      [[nodiscard]] section_pair_document_section_list_element get(size_t _index);
+      [[nodiscard]] size_t getAmountOfSections();
+      [[nodiscard]] ::std::string getHeader();
+      [[nodiscard]] section_pair_document_section_list getSectionList();
+      [[nodiscard]] ls::std::core::type::byte_field marshal() override;
+      void reserveNewLine(const ::std::string &_reservedNewLine);
+      void unmarshal(const ls::std::core::type::byte_field &_data) override;
+
+    private:
+
+      const ::std::string header = "# section-pair document";
+      ::std::string reservedNewLine{};
+      ls::std::io::section_pair_document_section_list sections{};
+      ::std::shared_ptr<ls::std::core::interface_type::ISerializable> serializable{};
+
+      void _checkSectionExistence(const ls::std::io::section_pair_identifier &_sectionId);
+      void _createSerializable();
+      [[nodiscard]] bool _hasSection(const ls::std::io::section_pair_identifier &_identifier);
+  };
+}
+
+#endif

+ 53 - 0
include/ls-std/io/section-pair/model/SectionPairRow.hpp

@@ -0,0 +1,53 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-08
+* Changed:         2023-02-17
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_ROW_HPP
+#define LS_STD_SECTION_PAIR_ROW_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/ISerializable.hpp>
+#include <ls-std/io/section-pair/SectionPairRowEnumType.hpp>
+#include <ls-std/io/section-pair/SectionPairTypes.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowValue.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <memory>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairRow : public ::std::enable_shared_from_this<SectionPairRow>, public ls::std::core::Class, public ls::std::core::interface_type::ISerializable
+  {
+    public:
+
+      explicit SectionPairRow(const ls::std::io::section_pair_identifier &_key, const ls::std::io::SectionPairRowEnumType &_type);
+      ~SectionPairRow() override;
+
+      [[nodiscard]] ls::std::io::section_pair_identifier getKey();
+      [[nodiscard]] ::std::shared_ptr<ls::std::io::SectionPairRowValue> getValue();
+      [[nodiscard]] bool isList();
+      [[nodiscard]] bool isSingleValue();
+      [[nodiscard]] ls::std::core::type::byte_field marshal() override;
+      void reserveNewLine(const ::std::string &_reservedNewLine);
+      void setKey(const ls::std::io::section_pair_identifier &_key);
+      void unmarshal(const ls::std::core::type::byte_field &_data) override;
+
+    private:
+
+      ls::std::io::section_pair_identifier key{};
+      ::std::string reservedNewLine{};
+      ::std::shared_ptr<ls::std::core::interface_type::ISerializable> serializable{};
+      ::std::shared_ptr<ls::std::io::SectionPairRowValue> value{};
+
+      void _createSerializable();
+      void _initValue(const ls::std::io::SectionPairRowEnumType &_type);
+      void _setKey(const ls::std::io::section_pair_identifier &_key);
+  };
+}
+
+#endif

+ 45 - 0
include/ls-std/io/section-pair/model/SectionPairRowListValue.hpp

@@ -0,0 +1,45 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-16
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_ROW_LIST_VALUE_HPP
+#define LS_STD_SECTION_PAIR_ROW_LIST_VALUE_HPP
+
+#include "SectionPairRowValue.hpp"
+#include <list>
+#include <ls-std/core/Class.hpp>
+#include <ls-std/io/section-pair/SectionPairTypes.hpp>
+
+namespace ls::std::io
+{
+  class SectionPairRowListValue : public ::std::enable_shared_from_this<SectionPairRowListValue>, public ls::std::core::Class, public ls::std::io::SectionPairRowValue
+  {
+    public:
+
+      SectionPairRowListValue();
+      ~SectionPairRowListValue() override;
+
+      void add(const ls::std::io::section_pair_row_value &_value);
+      void clear();
+      [[nodiscard]] ls::std::io::section_pair_row_value get(size_t _index);
+      [[nodiscard]] ::std::list<ls::std::io::section_pair_row_value> getList();
+      [[nodiscard]] size_t getSize();
+      [[nodiscard]] ls::std::io::SectionPairRowEnumType getType() override;
+      [[nodiscard]] ls::std::core::type::byte_field marshal() override;
+      void unmarshal(const ls::std::core::type::byte_field &_data) override;
+
+    private:
+
+      ::std::shared_ptr<ls::std::core::interface_type::ISerializable> serializable{};
+      ::std::list<ls::std::io::section_pair_row_value> values{};
+
+      void _createSerializable();
+  };
+}
+
+#endif

+ 45 - 0
include/ls-std/io/section-pair/model/SectionPairRowSingleValue.hpp

@@ -0,0 +1,45 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-13
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_ROW_SINGLE_VALUE_HPP
+#define LS_STD_SECTION_PAIR_ROW_SINGLE_VALUE_HPP
+
+#include "SectionPairRowValue.hpp"
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/ISerializable.hpp>
+#include <ls-std/io/section-pair/SectionPairTypes.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <memory>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairRowSingleValue : public ::std::enable_shared_from_this<SectionPairRowSingleValue>, public ls::std::core::Class, public ls::std::io::SectionPairRowValue
+  {
+    public:
+
+      explicit SectionPairRowSingleValue(const ls::std::io::section_pair_row_value &_value);
+      ~SectionPairRowSingleValue() override;
+
+      [[nodiscard]] ls::std::io::section_pair_row_value get();
+      [[nodiscard]] ls::std::io::SectionPairRowEnumType getType() override;
+      [[nodiscard]] ls::std::core::type::byte_field marshal() override;
+      void set(const ls::std::io::section_pair_row_value &_value);
+      void unmarshal(const ls::std::core::type::byte_field &_data) override;
+
+    private:
+
+      ::std::shared_ptr<ls::std::core::interface_type::ISerializable> serializable{};
+      ls::std::io::section_pair_row_value value{};
+
+      void _createSerializable();
+      void _set(const ls::std::io::section_pair_row_value &_value);
+  };
+}
+
+#endif

+ 38 - 0
include/ls-std/io/section-pair/model/SectionPairRowValue.hpp

@@ -0,0 +1,38 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-17
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_ROW_VALUE_HPP
+#define LS_STD_SECTION_PAIR_ROW_VALUE_HPP
+
+#include <ls-std/core/interface/ISerializable.hpp>
+#include <ls-std/io/section-pair/SectionPairRowEnumType.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairRowValue : public ls::std::core::interface_type::ISerializable
+  {
+    public:
+
+      explicit SectionPairRowValue(const ls::std::io::SectionPairRowEnumType &_type);
+      ~SectionPairRowValue() override;
+
+      virtual ls::std::io::SectionPairRowEnumType getType() = 0;
+      [[nodiscard]] ls::std::core::type::byte_field marshal() override;
+      void reserveNewLine(const ::std::string &_reservedNewLine);
+      void unmarshal(const ls::std::core::type::byte_field &_data) override;
+
+    protected:
+
+      ::std::string reservedNewLine{};
+      ls::std::io::SectionPairRowEnumType type{};
+  };
+}
+
+#endif

+ 56 - 0
include/ls-std/io/section-pair/model/SectionPairSection.hpp

@@ -0,0 +1,56 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-13
+* Changed:         2023-02-18
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_SECTION_HPP
+#define LS_STD_SECTION_PAIR_SECTION_HPP
+
+#include <list>
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/ISerializable.hpp>
+#include <ls-std/io/section-pair/SectionPairTypes.hpp>
+#include <ls-std/io/section-pair/type/SectionPairSectionTypes.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <memory>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairSection : public ::std::enable_shared_from_this<SectionPairSection>, public ls::std::core::Class, public ls::std::core::interface_type::ISerializable
+  {
+    public:
+
+      explicit SectionPairSection(const ls::std::io::section_pair_identifier &_sectionId);
+      ~SectionPairSection() override;
+
+      void add(const section_pair_row_list_element &_row);
+      void clear();
+      [[nodiscard]] section_pair_row_list_element get(size_t _index);
+      [[nodiscard]] ls::std::io::section_pair_row_list getList();
+      [[nodiscard]] size_t getRowAmount();
+      [[nodiscard]] ls::std::io::section_pair_identifier getSectionId();
+      [[nodiscard]] ls::std::core::type::byte_field marshal() override;
+      void reserveNewLine(const ::std::string &_reservedNewLine);
+      void setSectionId(const ls::std::io::section_pair_identifier &_sectionId);
+      void unmarshal(const ls::std::core::type::byte_field &_data) override;
+
+    private:
+
+      ::std::string reservedNewLine{};
+      ls::std::io::section_pair_row_list rows{};
+      ls::std::io::section_pair_identifier sectionId{};
+      ::std::shared_ptr<ls::std::core::interface_type::ISerializable> serializable{};
+
+      void _createSerializable();
+      [[nodiscard]] bool _hasRow(const ls::std::io::section_pair_identifier &_key);
+      void _rowExistenceCheck(const ls::std::io::section_pair_identifier &_key);
+      void _setSectionId(const ls::std::io::section_pair_identifier &_sectionId);
+  };
+}
+
+#endif

+ 42 - 0
include/ls-std/io/section-pair/reader/SectionPairFileReader.hpp

@@ -0,0 +1,42 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-21
+* Changed:         2023-02-21
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_FILE_READER_HPP
+#define LS_STD_SECTION_PAIR_FILE_READER_HPP
+
+#include "SectionPairFileReaderParameter.hpp"
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IReader.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <memory>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairFileReader : public ls::std::core::Class, public ls::std::core::interface_type::IReader
+  {
+    public:
+
+      explicit SectionPairFileReader(const ls::std::io::SectionPairFileReaderParameter &_parameter);
+      ~SectionPairFileReader() override;
+
+      [[nodiscard]] ::std::shared_ptr<ls::std::io::SectionPairDocument> getDocument();
+      ls::std::core::type::byte_field read() override; // nodiscard is optional here
+
+    private:
+
+      ls::std::io::SectionPairFileReaderParameter parameter{};
+
+      void _checkFileExtension();
+      void _createDocument();
+      void _createFileExistenceEvaluator();
+      void _createReader();
+  };
+}
+
+#endif

+ 47 - 0
include/ls-std/io/section-pair/reader/SectionPairFileReaderParameter.hpp

@@ -0,0 +1,47 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-21
+* Changed:         2023-02-21
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_FILE_READER_PARAMETER_HPP
+#define LS_STD_SECTION_PAIR_FILE_READER_PARAMETER_HPP
+
+#include <ls-std/core/interface/IEvaluator.hpp>
+#include <ls-std/core/interface/IReader.hpp>
+#include <ls-std/io/section-pair/model/SectionPairDocument.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <memory>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairFileReaderParameter
+  {
+    public:
+
+      SectionPairFileReaderParameter();
+      ~SectionPairFileReaderParameter();
+
+      [[nodiscard]] ::std::shared_ptr<ls::std::io::SectionPairDocument> getDocument();
+      [[nodiscard]] ::std::shared_ptr<ls::std::core::interface_type::IEvaluator> getFileExistenceEvaluator();
+      [[nodiscard]] ::std::string getFilePath();
+      [[nodiscard]] ::std::shared_ptr<ls::std::core::interface_type::IReader> getReader();
+      void setDocument(const ::std::shared_ptr<ls::std::io::SectionPairDocument> &_document);
+      void setFileExistenceEvaluator(const ::std::shared_ptr<ls::std::core::interface_type::IEvaluator> &_fileExistenceEvaluator);
+      void setFilePath(const ::std::string &_filePath);
+      void setReader(const ::std::shared_ptr<ls::std::core::interface_type::IReader> &_reader);
+
+    private:
+
+      ::std::shared_ptr<ls::std::io::SectionPairDocument> document{};
+      ::std::shared_ptr<ls::std::core::interface_type::IEvaluator> fileExistenceEvaluator{};
+      ::std::string filePath{};
+      ::std::shared_ptr<ls::std::core::interface_type::IReader> reader{};
+  };
+}
+
+#endif

+ 43 - 0
include/ls-std/io/section-pair/serialization/SerializableSectionPairDocument.hpp

@@ -0,0 +1,43 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-16
+* Changed:         2023-02-18
+*
+* */
+
+#ifndef LS_STD_SERIALIZABLE_SECTION_PAIR_DOCUMENT_HPP
+#define LS_STD_SERIALIZABLE_SECTION_PAIR_DOCUMENT_HPP
+
+#include "SerializableSectionPairParameter.hpp"
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/ISerializable.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <memory>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SerializableSectionPairDocument : public ls::std::core::interface_type::ISerializable, public ls::std::core::Class
+  {
+    public:
+
+      explicit SerializableSectionPairDocument(const ls::std::io::SerializableSectionPairParameter &_parameter);
+      ~SerializableSectionPairDocument() override;
+
+      [[nodiscard]] ::std::shared_ptr<ls::std::core::Class> getValue();
+      [[nodiscard]] ls::std::core::type::byte_field marshal() override;
+      void unmarshal(const ls::std::core::type::byte_field &_data) override;
+
+    private:
+
+      ls::std::io::SerializableSectionPairParameter parameter{};
+
+      [[nodiscard]] ls::std::core::type::byte_field _getCurrentRow(size_t _iterations, const ls::std::core::type::byte_field &_serializedDocument);
+      [[nodiscard]] ls::std::core::type::byte_field _getNextSerializedSection(const ls::std::core::type::byte_field &_serializedDocument);
+      [[nodiscard]] bool _isNotNewSection(const ls::std::core::type::byte_field &_currentRow);
+      void _addSection(const ls::std::core::type::byte_field &_serializedSection);
+  };
+}
+
+#endif

+ 39 - 0
include/ls-std/io/section-pair/serialization/SerializableSectionPairParameter.hpp

@@ -0,0 +1,39 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-17
+* Changed:         2023-02-17
+*
+* */
+
+#ifndef LS_STD_SERIALIZABLE_SECTION_PAIR_PARAMETER_HPP
+#define LS_STD_SERIALIZABLE_SECTION_PAIR_PARAMETER_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <memory>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SerializableSectionPairParameter
+  {
+    public:
+
+      SerializableSectionPairParameter();
+      ~SerializableSectionPairParameter();
+
+      [[nodiscard]] ::std::string getNewLine();
+      [[nodiscard]] ::std::shared_ptr<ls::std::core::Class> getValue() const;
+      void setNewLine(const ::std::string &_newLine);
+      void setValue(const ::std::shared_ptr<ls::std::core::Class> &_value);
+
+    private:
+
+      ::std::string parseNewLine{};
+      ::std::shared_ptr<ls::std::core::Class> value{};
+  };
+}
+
+#endif

+ 42 - 0
include/ls-std/io/section-pair/serialization/SerializableSectionPairRow.hpp

@@ -0,0 +1,42 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-11
+* Changed:         2023-02-17
+*
+* */
+
+#ifndef LS_STD_SERIALIZABLE_SECTION_PAIR_ROW_HPP
+#define LS_STD_SERIALIZABLE_SECTION_PAIR_ROW_HPP
+
+#include "SerializableSectionPairParameter.hpp"
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/ISerializable.hpp>
+#include <memory>
+#include <string>
+
+namespace ls::std::io
+{
+  class SerializableSectionPairRow : public ls::std::core::interface_type::ISerializable, public ls::std::core::Class
+  {
+    public:
+
+      explicit SerializableSectionPairRow(const ls::std::io::SerializableSectionPairParameter &_parameter);
+      ~SerializableSectionPairRow() override;
+
+      [[nodiscard]] ::std::shared_ptr<ls::std::core::Class> getValue();
+      [[nodiscard]] ls::std::core::type::byte_field marshal() override;
+      void unmarshal(const ls::std::core::type::byte_field &_data) override;
+
+    private:
+
+      ls::std::io::SerializableSectionPairParameter parameter{};
+
+      [[nodiscard]] ::std::string _marshalKey();
+      void _unmarshalListValue(const ls::std::core::type::byte_field &_data);
+      void _unmarshalSingleValue(const ls::std::core::type::byte_field &_data);
+  };
+}
+
+#endif

+ 41 - 0
include/ls-std/io/section-pair/serialization/SerializableSectionPairRowListValue.hpp

@@ -0,0 +1,41 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-11
+* Changed:         2023-02-17
+*
+* */
+
+#ifndef LS_STD_SERIALIZABLE_SECTION_PAIR_ROW_LIST_VALUE_HPP
+#define LS_STD_SERIALIZABLE_SECTION_PAIR_ROW_LIST_VALUE_HPP
+
+#include "SerializableSectionPairParameter.hpp"
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/ISerializable.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <memory>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SerializableSectionPairRowListValue : public ls::std::core::interface_type::ISerializable, public ls::std::core::Class
+  {
+    public:
+
+      explicit SerializableSectionPairRowListValue(const ls::std::io::SerializableSectionPairParameter &_parameter);
+      ~SerializableSectionPairRowListValue() override;
+
+      [[nodiscard]] ::std::shared_ptr<ls::std::core::Class> getValue();
+      [[nodiscard]] ls::std::core::type::byte_field marshal() override;
+      void unmarshal(const ls::std::core::type::byte_field &_data) override;
+
+    private:
+
+      ls::std::io::SerializableSectionPairParameter parameter{};
+
+      [[nodiscard]] static ::std::string _getLine(::std::string::size_type _position, const ls::std::core::type::byte_field &_searchText);
+      void _updateSearchText(::std::string::size_type _position, ls::std::core::type::byte_field &_searchText);
+  };
+}
+
+#endif

+ 38 - 0
include/ls-std/io/section-pair/serialization/SerializableSectionPairRowSingleValue.hpp

@@ -0,0 +1,38 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-11
+* Changed:         2023-02-17
+*
+* */
+
+#ifndef LS_STD_SERIALIZABLE_SECTION_PAIR_ROW_SINGLE_VALUE_HPP
+#define LS_STD_SERIALIZABLE_SECTION_PAIR_ROW_SINGLE_VALUE_HPP
+
+#include "SerializableSectionPairParameter.hpp"
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/ISerializable.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <memory>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SerializableSectionPairRowSingleValue : public ls::std::core::interface_type::ISerializable, public ls::std::core::Class
+  {
+    public:
+
+      explicit SerializableSectionPairRowSingleValue(const ls::std::io::SerializableSectionPairParameter &_parameter);
+      ~SerializableSectionPairRowSingleValue() override;
+
+      [[nodiscard]] ::std::shared_ptr<ls::std::core::Class> getValue();
+      [[nodiscard]] ls::std::core::type::byte_field marshal() override;
+      void unmarshal(const ls::std::core::type::byte_field &_data) override;
+
+    private:
+
+      ls::std::io::SerializableSectionPairParameter parameter{};
+  };
+}
+
+#endif

+ 53 - 0
include/ls-std/io/section-pair/serialization/SerializableSectionPairSection.hpp

@@ -0,0 +1,53 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-14
+* Changed:         2023-02-20
+*
+* */
+
+#ifndef LS_STD_SERIALIZABLE_SECTION_PAIR_SECTION_HPP
+#define LS_STD_SERIALIZABLE_SECTION_PAIR_SECTION_HPP
+
+#include "SerializableSectionPairParameter.hpp"
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/ISerializable.hpp>
+#include <ls-std/io/section-pair/SectionPairRowEnumType.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SerializableSectionPairSection : public ls::std::core::interface_type::ISerializable, public ls::std::core::Class
+  {
+    public:
+
+      explicit SerializableSectionPairSection(const ls::std::io::SerializableSectionPairParameter &_parameter);
+      ~SerializableSectionPairSection() override;
+
+      [[nodiscard]] ::std::shared_ptr<ls::std::core::Class> getValue();
+      [[nodiscard]] ls::std::core::type::byte_field marshal() override;
+      void unmarshal(const ls::std::core::type::byte_field &_data) override;
+
+    private:
+
+      ls::std::io::SerializableSectionPairParameter parameter{};
+
+      [[nodiscard]] ls::std::core::type::byte_field _collectSectionRow(const ls::std::core::type::byte_field &_currentRows, ls::std::io::SectionPairRowEnumType &_type);
+      [[nodiscard]] ls::std::core::type::byte_field _collectSectionListValueRow(const core::type::byte_field &_currentRows, SectionPairRowEnumType &_type);
+      [[nodiscard]] static core::type::byte_field _collectSectionSingleValueRow(const ls::std::core::type::byte_field &_firstRow, SectionPairRowEnumType &type);
+      [[nodiscard]] static size_t _getNthSubStringPosition(const ls::std::core::type::byte_field &_text, const ls::std::core::type::byte_field &_subText);
+      [[nodiscard]] ls::std::core::type::byte_field _getSectionHeader(const ls::std::core::type::byte_field &_data);
+      [[nodiscard]] static ls::std::core::type::byte_field _getSectionId(const ls::std::core::type::byte_field &_sectionHeader);
+      [[nodiscard]] static bool _isListValueRow(const ::std::string &_currentRow);
+      [[nodiscard]] static bool _isStartingValueRow(const ::std::string &_currentRow);
+      [[nodiscard]] static bool _isSingleValueRow(const ::std::string &_currentRow);
+      [[nodiscard]] ls::std::core::type::byte_field _marshalRows();
+      [[nodiscard]] ls::std::core::type::byte_field _marshalSectionId();
+      void _unmarshalRow(const ::std::string &_sectionRow, ls::std::io::SectionPairRowEnumType _type);
+      void _unmarshalRows(const ls::std::core::type::byte_field &_serializedRows);
+      [[nodiscard]] size_t _unmarshalSectionHeader(const ls::std::core::type::byte_field &_data);
+  };
+}
+
+#endif

+ 23 - 0
include/ls-std/io/section-pair/type/SectionPairDocumentTypes.hpp

@@ -0,0 +1,23 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-15
+* Changed:         2023-02-15
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_DOCUMENT_TYPES_HPP
+#define LS_STD_SECTION_PAIR_DOCUMENT_TYPES_HPP
+
+#include <list>
+#include <ls-std/io/section-pair/model/SectionPairSection.hpp>
+#include <memory>
+
+namespace ls::std::io
+{
+  using section_pair_document_section_list_element = ::std::shared_ptr<ls::std::io::SectionPairSection>;
+  using section_pair_document_section_list = ::std::list<ls::std::io::section_pair_document_section_list_element>;
+}
+
+#endif

+ 23 - 0
include/ls-std/io/section-pair/type/SectionPairSectionTypes.hpp

@@ -0,0 +1,23 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-13
+* Changed:         2023-02-13
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_SECTION_TYPES_HPP
+#define LS_STD_SECTION_PAIR_SECTION_TYPES_HPP
+
+#include <list>
+#include <ls-std/io/section-pair/model/SectionPairRow.hpp>
+#include <memory>
+
+namespace ls::std::io
+{
+  using section_pair_row_list_element = ::std::shared_ptr<ls::std::io::SectionPairRow>;
+  using section_pair_row_list = ::std::list<ls::std::io::section_pair_row_list_element>;
+}
+
+#endif

+ 37 - 0
include/ls-std/io/section-pair/validator/SectionPairDocumentValidator.hpp

@@ -0,0 +1,37 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-21
+* Changed:         2023-02-21
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_DOCUMENT_VALIDATOR_HPP
+#define LS_STD_SECTION_PAIR_DOCUMENT_VALIDATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IValidator.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairDocumentValidator : public ls::std::core::Class, public ls::std::core::interface_type::IValidator
+  {
+    public:
+
+      explicit SectionPairDocumentValidator(::std::string _document);
+      ~SectionPairDocumentValidator() override;
+
+      [[nodiscard]] bool isValid() override;
+
+    private:
+
+      ::std::string document{};
+
+      [[nodiscard]] static ::std::string _getValidationRegex();
+  };
+}
+
+#endif

+ 35 - 0
include/ls-std/io/section-pair/validator/SectionPairFileExtensionValidator.hpp

@@ -0,0 +1,35 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-21
+* Changed:         2023-02-21
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_FILE_EXTENSION_VALIDATOR_HPP
+#define LS_STD_SECTION_PAIR_FILE_EXTENSION_VALIDATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IValidator.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairFileExtensionValidator : public ls::std::core::Class, public ls::std::core::interface_type::IValidator
+  {
+    public:
+
+      explicit SectionPairFileExtensionValidator(::std::string _fileName);
+      ~SectionPairFileExtensionValidator() override;
+
+      [[nodiscard]] bool isValid() override;
+
+    private:
+
+      ::std::string fileName{};
+  };
+}
+
+#endif

+ 39 - 0
include/ls-std/io/section-pair/validator/SectionPairIdentifierValidator.hpp

@@ -0,0 +1,39 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-09
+* Changed:         2023-02-18
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_IDENTIFIER_VALIDATOR_HPP
+#define LS_STD_SECTION_PAIR_IDENTIFIER_VALIDATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IValidator.hpp>
+#include <ls-std/io/section-pair/SectionPairTypes.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairIdentifierValidator : public ls::std::core::Class, public ls::std::core::interface_type::IValidator
+  {
+    public:
+
+      explicit SectionPairIdentifierValidator(ls::std::io::section_pair_identifier _identifier);
+      ~SectionPairIdentifierValidator() override;
+
+      [[nodiscard]] static ::std::string getValidationRegex();
+      [[nodiscard]] bool isValid() override;
+
+    private:
+
+      ls::std::io::section_pair_identifier identifier{};
+
+      [[nodiscard]] static ::std::string _getValidationRegex();
+  };
+}
+
+#endif

+ 38 - 0
include/ls-std/io/section-pair/validator/SectionPairRowListValueValidator.hpp

@@ -0,0 +1,38 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-19
+* Changed:         2023-02-20
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_ROW_LIST_VALUE_VALIDATOR_HPP
+#define LS_STD_SECTION_PAIR_ROW_LIST_VALUE_VALIDATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IValidator.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairRowListValueValidator : public ls::std::core::Class, public ls::std::core::interface_type::IValidator
+  {
+    public:
+
+      explicit SectionPairRowListValueValidator(::std::string _listValueRow);
+      ~SectionPairRowListValueValidator() override;
+
+      [[nodiscard]] static ::std::string getValidationRegex();
+      [[nodiscard]] bool isValid() override;
+
+    private:
+
+      ::std::string listValueRow{};
+
+      [[nodiscard]] static ::std::string _getValidationRegex();
+  };
+}
+
+#endif

+ 37 - 0
include/ls-std/io/section-pair/validator/SectionPairRowSingleValueValidator.hpp

@@ -0,0 +1,37 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-19
+* Changed:         2023-02-20
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_ROW_SINGLE_VALUE_VALIDATOR_HPP
+#define LS_STD_SECTION_PAIR_ROW_SINGLE_VALUE_VALIDATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IValidator.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairRowSingleValueValidator : public ls::std::core::Class, public ls::std::core::interface_type::IValidator
+  {
+    public:
+
+      explicit SectionPairRowSingleValueValidator(::std::string _singleValueRow);
+      ~SectionPairRowSingleValueValidator() override;
+
+      [[nodiscard]] static ::std::string getValidationRegex();
+      [[nodiscard]] bool isValid() override;
+
+    private:
+
+      ::std::string singleValueRow{};
+
+      [[nodiscard]] static ::std::string _getValidationRegex();
+  };
+}
+
+#endif

+ 38 - 0
include/ls-std/io/section-pair/validator/SectionPairRowValidator.hpp

@@ -0,0 +1,38 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-20
+* Changed:         2023-02-20
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_ROW_VALIDATOR_HPP
+#define LS_STD_SECTION_PAIR_ROW_VALIDATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IValidator.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairRowValidator : public ls::std::core::Class, public ls::std::core::interface_type::IValidator
+  {
+    public:
+
+      explicit SectionPairRowValidator(::std::string _row);
+      ~SectionPairRowValidator() override;
+
+      [[nodiscard]] static ::std::string getValidationRegex();
+      [[nodiscard]] bool isValid() override;
+
+    private:
+
+      ::std::string row{};
+
+      [[nodiscard]] static ::std::string _getValidationRegex();
+  };
+}
+
+#endif

+ 38 - 0
include/ls-std/io/section-pair/validator/SectionPairSectionValidator.hpp

@@ -0,0 +1,38 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-20
+* Changed:         2023-02-20
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_SECTION_VALIDATOR_HPP
+#define LS_STD_SECTION_PAIR_SECTION_VALIDATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IValidator.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairSectionValidator : public ls::std::core::Class, public ls::std::core::interface_type::IValidator
+  {
+    public:
+
+      explicit SectionPairSectionValidator(::std::string _section);
+      ~SectionPairSectionValidator() override;
+
+      [[nodiscard]] static ::std::string getValidationRegex();
+      [[nodiscard]] bool isValid() override;
+
+    private:
+
+      ::std::string section{};
+
+      [[nodiscard]] static ::std::string _getValidationRegex();
+  };
+}
+
+#endif

+ 39 - 0
include/ls-std/io/section-pair/validator/SectionPairValueValidator.hpp

@@ -0,0 +1,39 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-09
+* Changed:         2023-02-19
+*
+* */
+
+#ifndef LS_STD_SECTION_PAIR_VALUE_VALIDATOR_HPP
+#define LS_STD_SECTION_PAIR_VALUE_VALIDATOR_HPP
+
+#include <ls-std/core/Class.hpp>
+#include <ls-std/core/interface/IValidator.hpp>
+#include <ls-std/io/section-pair/SectionPairTypes.hpp>
+#include <ls-std/os/dynamic-goal.hpp>
+#include <string>
+
+namespace ls::std::io
+{
+  class LS_STD_DYNAMIC_GOAL SectionPairValueValidator : public ls::std::core::Class, public ls::std::core::interface_type::IValidator
+  {
+    public:
+
+      explicit SectionPairValueValidator(ls::std::io::section_pair_row_value _value);
+      ~SectionPairValueValidator() override;
+
+      [[nodiscard]] static ::std::string getValidationRegex();
+      [[nodiscard]] bool isValid() override;
+
+    private:
+
+      ls::std::io::section_pair_row_value value{};
+
+      [[nodiscard]] static ::std::string _getValidationRegex();
+  };
+}
+
+#endif

+ 6 - 1
include/ls-std/ls-std-core.hpp

@@ -3,7 +3,7 @@
  * Company:         Lynar Studios
  * E-Mail:          webmaster@lynarstudios.com
  * Created:         2022-05-13
- * Changed:         2023-02-08
+ * Changed:         2023-02-13
  *
  * */
 
@@ -11,6 +11,7 @@
 #define LS_STD_LS_STD_CORE_HPP
 
 #include <ls-std/core/evaluator/EmptyStringArgumentEvaluator.hpp>
+#include <ls-std/core/evaluator/IndexOutOfBoundsEvaluator.hpp>
 #include <ls-std/core/evaluator/NullPointerArgumentEvaluator.hpp>
 #include <ls-std/core/evaluator/NullPointerEvaluator.hpp>
 
@@ -22,7 +23,9 @@
 #include <ls-std/core/exception/IllegalArgumentException.hpp>
 #include <ls-std/core/exception/IllegalArithmeticOperationException.hpp>
 #include <ls-std/core/exception/IncompleteJsonException.hpp>
+#include <ls-std/core/exception/IndexOutOfBoundsException.hpp>
 #include <ls-std/core/exception/NullPointerException.hpp>
+#include <ls-std/core/exception/WrongCallException.hpp>
 
 #include <ls-std/core/interface/IBoxing.hpp>
 #include <ls-std/core/interface/IEncoding.hpp>
@@ -31,6 +34,7 @@
 #include <ls-std/core/interface/IReader.hpp>
 #include <ls-std/core/interface/ISerializable.hpp>
 #include <ls-std/core/interface/IStorable.hpp>
+#include <ls-std/core/interface/IValidator.hpp>
 #include <ls-std/core/interface/IWriter.hpp>
 
 #include <ls-std/core/type/EventTypes.hpp>
@@ -38,6 +42,7 @@
 #include <ls-std/core/type/Types.hpp>
 
 #include <ls-std/core/Class.hpp>
+#include <ls-std/core/ConditionalFunctionExecutor.hpp>
 #include <ls-std/core/LibraryVersion.hpp>
 #include <ls-std/core/Version.hpp>
 

+ 36 - 6
include/ls-std/ls-std-io.hpp

@@ -3,23 +3,53 @@
  * Company:         Lynar Studios
  * E-Mail:          webmaster@lynarstudios.com
  * Created:         2022-05-14
- * Changed:         2023-02-04
+ * Changed:         2023-02-22
  *
  * */
 
 #ifndef LS_STD_LS_STD_IO_HPP
 #define LS_STD_LS_STD_IO_HPP
 
-#include <ls-std/io/kv/KvDocument.hpp>
-#include <ls-std/io/kv/KvFileReader.hpp>
-#include <ls-std/io/kv/KvPair.hpp>
-#include <ls-std/io/kv/KvParseParameter.hpp>
-#include <ls-std/io/kv/KvParser.hpp>
+#include <ls-std/io/evaluator/FileExistenceEvaluator.hpp>
 
 #include <ls-std/io/logging/LogLevel.hpp>
 #include <ls-std/io/logging/LogLevelValue.hpp>
 #include <ls-std/io/logging/Logger.hpp>
 
+#include <ls-std/io/section-pair/SectionPairMessageFormatter.hpp>
+#include <ls-std/io/section-pair/SectionPairRowEnumType.hpp>
+#include <ls-std/io/section-pair/SectionPairTypes.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairIdentifierArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairRowArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairRowListValueArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairRowSingleValueArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairSectionArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairValueArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/model/SectionPairDocument.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRow.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowListValue.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowSingleValue.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowValue.hpp>
+#include <ls-std/io/section-pair/model/SectionPairSection.hpp>
+#include <ls-std/io/section-pair/reader/SectionPairFileReader.hpp>
+#include <ls-std/io/section-pair/reader/SectionPairFileReaderParameter.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairDocument.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairParameter.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairRow.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairRowListValue.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairRowSingleValue.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairSection.hpp>
+#include <ls-std/io/section-pair/type/SectionPairDocumentTypes.hpp>
+#include <ls-std/io/section-pair/type/SectionPairSectionTypes.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairDocumentValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairFileExtensionValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairIdentifierValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairRowListValueValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairRowSingleValueValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairRowValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairSectionValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairValueValidator.hpp>
+
 #include <ls-std/io/xml/XmlAttribute.hpp>
 #include <ls-std/io/xml/XmlDeclaration.hpp>
 #include <ls-std/io/xml/XmlDocument.hpp>

+ 23 - 0
source/ls-std/core/ConditionalFunctionExecutor.cpp

@@ -0,0 +1,23 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-13
+* Changed:         2023-02-21
+*
+* */
+
+#include <ls-std/core/ConditionalFunctionExecutor.hpp>
+
+ls::std::core::ConditionalFunctionExecutor::ConditionalFunctionExecutor(bool _condition) : condition(_condition)
+{}
+
+ls::std::core::ConditionalFunctionExecutor::~ConditionalFunctionExecutor() = default;
+
+void ls::std::core::ConditionalFunctionExecutor::execute(const ::std::function<void()> &_function) const
+{
+  if (this->condition)
+  {
+    _function();
+  }
+}

+ 34 - 0
source/ls-std/core/evaluator/IndexOutOfBoundsEvaluator.cpp

@@ -0,0 +1,34 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-10
+*
+* */
+
+#include <ls-std/core/evaluator/IndexOutOfBoundsEvaluator.hpp>
+#include <ls-std/core/exception/IndexOutOfBoundsException.hpp>
+
+ls::std::core::IndexOutOfBoundsEvaluator::IndexOutOfBoundsEvaluator(size_t _index, size_t _size) : index(_index), size(_size)
+{}
+
+ls::std::core::IndexOutOfBoundsEvaluator::IndexOutOfBoundsEvaluator(size_t _index, size_t _size, ::std::string _message) : index(_index), size(_size), message(::std::move(_message))
+{}
+
+ls::std::core::IndexOutOfBoundsEvaluator::~IndexOutOfBoundsEvaluator() = default;
+
+void ls::std::core::IndexOutOfBoundsEvaluator::evaluate()
+{
+  if (this->index >= this->size)
+  {
+    if (this->message.empty())
+    {
+      throw ls::std::core::IndexOutOfBoundsException{};
+    }
+    else
+    {
+      throw ls::std::core::IndexOutOfBoundsException{this->message};
+    }
+  }
+}

+ 34 - 0
source/ls-std/core/exception/IndexOutOfBoundsException.cpp

@@ -0,0 +1,34 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-10
+*
+* */
+
+#include <ls-std/core/exception/ExceptionMessage.hpp>
+#include <ls-std/core/exception/IndexOutOfBoundsException.hpp>
+
+ls::std::core::IndexOutOfBoundsException::IndexOutOfBoundsException() = default;
+
+ls::std::core::IndexOutOfBoundsException::IndexOutOfBoundsException(::std::string _message) : message(::std::move(_message))
+{}
+
+ls::std::core::IndexOutOfBoundsException::~IndexOutOfBoundsException() = default;
+
+const char *ls::std::core::IndexOutOfBoundsException::what() const noexcept
+{
+  ::std::string concatenatedMessage = "IndexOutOfBoundsException thrown - ";
+
+  if (this->message.empty())
+  {
+    concatenatedMessage = concatenatedMessage + "provided index is out of bounds!";
+  }
+  else
+  {
+    concatenatedMessage = concatenatedMessage + this->message;
+  }
+
+  return ExceptionMessage{concatenatedMessage}.toCharacterPointer();
+}

+ 34 - 0
source/ls-std/core/exception/WrongCallException.cpp

@@ -0,0 +1,34 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-10
+*
+* */
+
+#include <ls-std/core/exception/WrongCallException.hpp>
+#include <ls-std/core/exception/ExceptionMessage.hpp>
+
+ls::std::core::WrongCallException::WrongCallException() = default;
+
+ls::std::core::WrongCallException::WrongCallException(::std::string _message) : message(::std::move(_message))
+{}
+
+ls::std::core::WrongCallException::~WrongCallException() = default;
+
+const char *ls::std::core::WrongCallException::what() const noexcept
+{
+  ::std::string concatenatedMessage = "WrongCallException thrown - ";
+
+  if (this->message.empty())
+  {
+    concatenatedMessage = concatenatedMessage + "this function / method call is invalid!";
+  }
+  else
+  {
+    concatenatedMessage = concatenatedMessage + this->message;
+  }
+
+  return ExceptionMessage{concatenatedMessage}.toCharacterPointer();
+}

+ 14 - 0
source/ls-std/core/interface/IValidator.cpp

@@ -0,0 +1,14 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-08
+* Changed:         2023-02-08
+*
+* */
+
+#include <ls-std/core/interface/IValidator.hpp>
+
+ls::std::core::interface_type::IValidator::IValidator() = default;
+
+ls::std::core::interface_type::IValidator::~IValidator() = default;

+ 27 - 0
source/ls-std/io/evaluator/FileExistenceEvaluator.cpp

@@ -0,0 +1,27 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-21
+* Changed:         2023-02-21
+*
+* */
+
+#include <ls-std/core/exception/FileNotFoundException.hpp>
+#include <ls-std/io/File.hpp>
+#include <ls-std/io/evaluator/FileExistenceEvaluator.hpp>
+#include <string>
+
+ls::std::io::FileExistenceEvaluator::FileExistenceEvaluator(::std::string _filePath) : ls::std::core::Class("FileExistenceEvaluator"), filePath(::std::move(_filePath))
+{}
+
+ls::std::io::FileExistenceEvaluator::~FileExistenceEvaluator() = default;
+
+void ls::std::io::FileExistenceEvaluator::evaluate()
+{
+  if (!ls::std::io::File{this->filePath}.exists())
+  {
+    ::std::string message = "\"" + this->filePath + "\" does not exist!";
+    throw ls::std::core::FileNotFoundException{message};
+  }
+}

+ 0 - 53
source/ls-std/io/kv/KvDocument.cpp

@@ -1,53 +0,0 @@
-/*
- * Author:          Patrick-Christopher Mattulat
- * Company:         Lynar Studios
- * E-Mail:          webmaster@lynarstudios.com
- * Created:         2020-12-25
- * Changed:         2023-02-04
- *
- * */
-
-#include <ls-std/io/kv/KvDocument.hpp>
-
-ls::std::io::KvDocument::KvDocument() : ls::std::core::Class("KvDocument")
-{}
-
-ls::std::io::KvDocument::~KvDocument() = default;
-
-bool ls::std::io::KvDocument::addPair(ls::std::io::KvPair _pair)
-{
-  bool added{};
-
-  if (!this->_hasPair(_pair.getKey()))
-  {
-    ::std::pair<ls::std::core::type::kv_key, ls::std::io::KvPair> pair = ::std::make_pair(_pair.getKey(), _pair);
-    added = this->pairs.insert(pair).second;
-  }
-
-  return added;
-}
-
-void ls::std::io::KvDocument::clear()
-{
-  this->pairs.clear();
-}
-
-::std::map<ls::std::core::type::kv_key, ls::std::io::KvPair> ls::std::io::KvDocument::getPairs()
-{
-  return this->pairs;
-}
-
-bool ls::std::io::KvDocument::hasPair(const ls::std::core::type::kv_key &_key)
-{
-  return this->_hasPair(_key);
-}
-
-bool ls::std::io::KvDocument::removePair(const ls::std::core::type::kv_key &_key)
-{
-  return this->pairs.erase(_key) == 1;
-}
-
-bool ls::std::io::KvDocument::_hasPair(const ls::std::core::type::kv_key &_key)
-{
-  return this->pairs.find(_key) != this->pairs.end();
-}

+ 0 - 61
source/ls-std/io/kv/KvFileReader.cpp

@@ -1,61 +0,0 @@
-/*
- * Author:          Patrick-Christopher Mattulat
- * Company:         Lynar Studios
- * E-Mail:          webmaster@lynarstudios.com
- * Created:         2020-12-25
- * Changed:         2023-02-08
- *
- * */
-
-#include <ls-std/core/evaluator/NullPointerArgumentEvaluator.hpp>
-#include <ls-std/core/exception/IllegalArgumentException.hpp>
-#include <ls-std/io/FileReader.hpp>
-#include <ls-std/io/kv/KvFileReader.hpp>
-#include <ls-std/io/kv/KvParser.hpp>
-
-ls::std::io::KvFileReader::KvFileReader(const ::std::shared_ptr<ls::std::io::KvDocument> &_document, const ::std::string &_absolutePath) : ls::std::core::Class("KvFileReader"), kvFile(ls::std::io::File{""})
-{
-  this->_assignDocument(_document);
-  this->_assignFile(ls::std::io::File{_absolutePath});
-}
-
-ls::std::io::KvFileReader::~KvFileReader() = default;
-
-ls::std::core::type::byte_field ls::std::io::KvFileReader::read()
-{
-  ls::std::core::type::byte_field data = ls::std::io::FileReader{this->kvFile}.read();
-  ls::std::io::KvParser{this->document}.parse(data);
-
-  return data;
-}
-
-::std::shared_ptr<ls::std::io::KvDocument> ls::std::io::KvFileReader::getDocument()
-{
-  return this->document;
-}
-
-void ls::std::io::KvFileReader::setDocument(const ::std::shared_ptr<ls::std::io::KvDocument> &_document)
-{
-  this->_assignDocument(_document);
-}
-
-void ls::std::io::KvFileReader::setFile(const ls::std::io::File &_kvFile)
-{
-  this->_assignFile(_kvFile);
-}
-
-void ls::std::io::KvFileReader::_assignDocument(const ::std::shared_ptr<ls::std::io::KvDocument> &_document)
-{
-  ls::std::core::NullPointerArgumentEvaluator{_document, "passed document reference is null!"}.evaluate();
-  this->document = _document;
-}
-
-void ls::std::io::KvFileReader::_assignFile(ls::std::io::File _kvFile)
-{
-  if (!_kvFile.exists())
-  {
-    throw ls::std::core::IllegalArgumentException{"file does not exist: " + _kvFile.getAbsoluteFilePath()};
-  }
-
-  this->kvFile = _kvFile;
-}

+ 0 - 39
source/ls-std/io/kv/KvPair.cpp

@@ -1,39 +0,0 @@
-/*
- * Author:          Patrick-Christopher Mattulat
- * Company:         Lynar Studios
- * E-Mail:          webmaster@lynarstudios.com
- * Created:         2020-12-25
- * Changed:         2023-02-08
- *
- * */
-
-#include <ls-std/core/evaluator/EmptyStringArgumentEvaluator.hpp>
-#include <ls-std/io/kv/KvPair.hpp>
-
-ls::std::io::KvPair::KvPair(const ls::std::core::type::kv_key &_key, ls::std::core::type::kv_value _value) : ls::std::core::Class("KvPair"), value(::std::move(_value))
-{
-  this->_assignKey(_key);
-}
-
-ls::std::io::KvPair::~KvPair() = default;
-
-ls::std::core::type::kv_key ls::std::io::KvPair::getKey()
-{
-  return this->key;
-}
-
-ls::std::core::type::kv_value ls::std::io::KvPair::getValue()
-{
-  return this->value;
-}
-
-void ls::std::io::KvPair::setValue(const ls::std::core::type::kv_value &_value)
-{
-  this->value = _value;
-}
-
-void ls::std::io::KvPair::_assignKey(const ls::std::core::type::kv_key &_key)
-{
-  ls::std::core::EmptyStringArgumentEvaluator{_key, "key is empty!"}.evaluate();
-  this->key = _key;
-}

+ 0 - 34
source/ls-std/io/kv/KvParseParameter.cpp

@@ -1,34 +0,0 @@
-/*
-* Author:          Patrick-Christopher Mattulat
-* Company:         Lynar Studios
-* E-Mail:          webmaster@lynarstudios.com
-* Created:         2023-02-05
-* Changed:         2023-02-05
-*
-* */
-
-#include <ls-std/io/kv/KvParseParameter.hpp>
-
-ls::std::io::KvParseParameter::KvParseParameter() = default;
-
-ls::std::io::KvParseParameter::~KvParseParameter() = default;
-
-::std::string::size_type ls::std::io::KvParseParameter::getIndex() const
-{
-  return this->index;
-}
-
-::std::string ls::std::io::KvParseParameter::getLine()
-{
-  return this->line;
-}
-
-void ls::std::io::KvParseParameter::setIndex(const ::std::string::size_type &_index)
-{
-  this->index = _index;
-}
-
-void ls::std::io::KvParseParameter::setLine(const ::std::string &_line)
-{
-  this->line = _line;
-}

+ 0 - 106
source/ls-std/io/kv/KvParser.cpp

@@ -1,106 +0,0 @@
-/*
- * Author:          Patrick-Christopher Mattulat
- * Company:         Lynar Studios
- * E-Mail:          webmaster@lynarstudios.com
- * Created:         2020-12-25
- * Changed:         2023-02-08
- *
- * */
-
-#include <ls-std/core/evaluator/NullPointerArgumentEvaluator.hpp>
-#include <ls-std/io/NewLine.hpp>
-#include <ls-std/io/kv/KvParser.hpp>
-
-ls::std::io::KvParser::KvParser(const ::std::shared_ptr<ls::std::io::KvDocument> &_document) : ls::std::core::Class("KvParser")
-{
-  this->_assignDocument(_document);
-}
-
-ls::std::io::KvParser::~KvParser() = default;
-
-::std::shared_ptr<ls::std::io::KvDocument> ls::std::io::KvParser::getDocument()
-{
-  return this->document;
-}
-
-void ls::std::io::KvParser::parse(const ls::std::core::type::byte_field &_data)
-{
-  this->_parse(_data);
-}
-
-void ls::std::io::KvParser::setDocument(const ::std::shared_ptr<ls::std::io::KvDocument> &_document)
-{
-  this->_assignDocument(_document);
-}
-
-void ls::std::io::KvParser::_assignDocument(const ::std::shared_ptr<ls::std::io::KvDocument> &_document)
-{
-  ls::std::core::NullPointerArgumentEvaluator{_document, "reference to document is null!"}.evaluate();
-  this->document = _document;
-}
-
-bool ls::std::io::KvParser::_contains(const ::std::string &_text, const ::std::string &_searchText)
-{
-  return _text.find(_searchText) != ::std::string::npos;
-}
-
-bool ls::std::io::KvParser::_lineHasPair(ls::std::io::KvParseParameter &_parseParameter)
-{
-  return ls::std::io::KvParser::_contains(_parseParameter.getLine(), "=") && ls::std::io::KvParser::_contains(_parseParameter.getLine(), ";");
-}
-
-void ls::std::io::KvParser::_parse(const ls::std::core::type::byte_field &_data)
-{
-  for (::std::string::size_type index = 0; index < _data.size(); index++)
-  {
-    ls::std::io::KvParseParameter parseParameter = ls::std::io::KvParser::_readLine(_data, index);
-    this->_parsePair(parseParameter);
-    index = parseParameter.getIndex();
-  }
-}
-
-void ls::std::io::KvParser::_parsePair(ls::std::io::KvParseParameter &_parseParameter)
-{
-  if (ls::std::io::KvParser::_lineHasPair(_parseParameter))
-  {
-    size_t equalSignPosition = _parseParameter.getLine().find('=');
-    ls::std::core::type::kv_key key = _parseParameter.getLine().substr(0, equalSignPosition);
-    ls::std::core::type::kv_value value = _parseParameter.getLine().substr(equalSignPosition + 1);
-    value = value.substr(0, value.find(';'));
-
-    this->document->addPair(ls::std::io::KvPair{key, value});
-  }
-}
-
-ls::std::io::KvParseParameter ls::std::io::KvParser::_readLine(const ls::std::core::type::byte_field &_data, ::std::string::size_type _index)
-{
-  ls::std::io::KvParseParameter parseParameter{};
-  parseParameter.setLine(_data.substr(_index));
-
-  if (ls::std::io::KvParser::_contains(parseParameter.getLine(), ls::std::io::NewLine::getWindowsNewLine()))
-  {
-    ls::std::io::KvParser::_readLineWithWindowsLineBreak(parseParameter);
-  }
-  else
-  {
-    if (ls::std::io::KvParser::_contains(parseParameter.getLine(), ls::std::io::NewLine::getUnixNewLine()))
-    {
-      ls::std::io::KvParser::_readLineWithUnixLineBreak(parseParameter);
-    }
-  }
-
-  parseParameter.setIndex(_index + parseParameter.getLine().size());
-  return parseParameter;
-}
-
-void ls::std::io::KvParser::_readLineWithUnixLineBreak(ls::std::io::KvParseParameter &_parseParameter)
-{
-  size_t newLinePosition = _parseParameter.getLine().find(ls::std::io::NewLine::getUnixNewLine());
-  _parseParameter.setLine(_parseParameter.getLine().substr(0, newLinePosition));
-}
-
-void ls::std::io::KvParser::_readLineWithWindowsLineBreak(ls::std::io::KvParseParameter &_parseParameter)
-{
-  size_t newLinePosition = _parseParameter.getLine().find(ls::std::io::NewLine::getWindowsNewLine());
-  _parseParameter.setLine(_parseParameter.getLine().substr(0, newLinePosition + 1));
-}

+ 24 - 0
source/ls-std/io/section-pair/SectionPairMessageFormatter.cpp

@@ -0,0 +1,24 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-22
+* Changed:         2023-02-22
+*
+* */
+
+#include <ls-std/io/section-pair/SectionPairMessageFormatter.hpp>
+#include <regex>
+
+ls::std::io::SectionPairMessageFormatter::SectionPairMessageFormatter() = default;
+
+ls::std::io::SectionPairMessageFormatter::~SectionPairMessageFormatter() = default;
+
+::std::string ls::std::io::SectionPairMessageFormatter::getFormattedMessage(const ::std::string &_message)
+{
+  ::std::string formattedMessage = _message;
+  formattedMessage = ::std::regex_replace(formattedMessage, ::std::regex(R"(\r{1}\n{1})"), "{WINDOWS_LINE_BREAK}");
+  formattedMessage = ::std::regex_replace(formattedMessage, ::std::regex(R"(\n{1})"), "{UNIX_LINE_BREAK}");
+
+  return formattedMessage;
+}

+ 28 - 0
source/ls-std/io/section-pair/evaluator/SectionPairIdentifierArgumentEvaluator.cpp

@@ -0,0 +1,28 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-09
+* Changed:         2023-02-22
+*
+* */
+
+#include <ls-std/core/exception/IllegalArgumentException.hpp>
+#include <ls-std/io/section-pair/SectionPairMessageFormatter.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairIdentifierArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairIdentifierValidator.hpp>
+#include <string>
+
+ls::std::io::SectionPairIdentifierArgumentEvaluator::SectionPairIdentifierArgumentEvaluator(ls::std::io::section_pair_identifier _identifier) : ls::std::core::Class("SectionPairIdentifierArgumentEvaluator"), identifier(::std::move(_identifier))
+{}
+
+ls::std::io::SectionPairIdentifierArgumentEvaluator::~SectionPairIdentifierArgumentEvaluator() = default;
+
+void ls::std::io::SectionPairIdentifierArgumentEvaluator::evaluate()
+{
+  if (!ls::std::io::SectionPairIdentifierValidator{this->identifier}.isValid())
+  {
+    ::std::string message = "\"" + this->identifier + "\" is not a valid identifier!";
+    throw ls::std::core::IllegalArgumentException{ls::std::io::SectionPairMessageFormatter::getFormattedMessage(message)};
+  }
+}

+ 28 - 0
source/ls-std/io/section-pair/evaluator/SectionPairRowArgumentEvaluator.cpp

@@ -0,0 +1,28 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-20
+* Changed:         2023-02-22
+*
+* */
+
+#include <ls-std/core/exception/IllegalArgumentException.hpp>
+#include <ls-std/io/section-pair/SectionPairMessageFormatter.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairRowArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairRowValidator.hpp>
+#include <string>
+
+ls::std::io::SectionPairRowArgumentEvaluator::SectionPairRowArgumentEvaluator(::std::string _sectionPairRow) : ls::std::core::Class("SectionPairRowArgumentEvaluator"), sectionPairRow(::std::move(_sectionPairRow))
+{}
+
+ls::std::io::SectionPairRowArgumentEvaluator::~SectionPairRowArgumentEvaluator() = default;
+
+void ls::std::io::SectionPairRowArgumentEvaluator::evaluate()
+{
+  if (!ls::std::io::SectionPairRowValidator{this->sectionPairRow}.isValid())
+  {
+    ::std::string message = "\"" + this->sectionPairRow + "\" is not a valid section pair row!";
+    throw ls::std::core::IllegalArgumentException{ls::std::io::SectionPairMessageFormatter::getFormattedMessage(message)};
+  }
+}

+ 27 - 0
source/ls-std/io/section-pair/evaluator/SectionPairRowListValueArgumentEvaluator.cpp

@@ -0,0 +1,27 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-20
+* Changed:         2023-02-22
+*
+* */
+
+#include <ls-std/core/exception/IllegalArgumentException.hpp>
+#include <ls-std/io/section-pair/SectionPairMessageFormatter.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairRowListValueArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairRowListValueValidator.hpp>
+
+ls::std::io::SectionPairRowListValueArgumentEvaluator::SectionPairRowListValueArgumentEvaluator(::std::string _listValueRow) : ls::std::core::Class("SectionPairRowListValueArgumentEvaluator"), listValueRow(::std::move(_listValueRow))
+{}
+
+ls::std::io::SectionPairRowListValueArgumentEvaluator::~SectionPairRowListValueArgumentEvaluator() = default;
+
+void ls::std::io::SectionPairRowListValueArgumentEvaluator::evaluate()
+{
+  if (!ls::std::io::SectionPairRowListValueValidator{this->listValueRow}.isValid())
+  {
+    ::std::string message = "\"" + this->listValueRow + "\" is not a valid section pair list value row!";
+    throw ls::std::core::IllegalArgumentException{ls::std::io::SectionPairMessageFormatter::getFormattedMessage(message)};
+  }
+}

+ 27 - 0
source/ls-std/io/section-pair/evaluator/SectionPairRowSingleValueArgumentEvaluator.cpp

@@ -0,0 +1,27 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-19
+* Changed:         2023-02-22
+*
+* */
+
+#include <ls-std/core/exception/IllegalArgumentException.hpp>
+#include <ls-std/io/section-pair/SectionPairMessageFormatter.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairRowSingleValueArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairRowSingleValueValidator.hpp>
+
+ls::std::io::SectionPairRowSingleValueArgumentEvaluator::SectionPairRowSingleValueArgumentEvaluator(::std::string _singleValueRow) : ls::std::core::Class("SectionPairRowSingleValueArgumentEvaluator"), singleValueRow(::std::move(_singleValueRow))
+{}
+
+ls::std::io::SectionPairRowSingleValueArgumentEvaluator::~SectionPairRowSingleValueArgumentEvaluator() = default;
+
+void ls::std::io::SectionPairRowSingleValueArgumentEvaluator::evaluate()
+{
+  if (!ls::std::io::SectionPairRowSingleValueValidator{this->singleValueRow}.isValid())
+  {
+    ::std::string message = "\"" + this->singleValueRow + "\" is not a valid section pair single value row!";
+    throw ls::std::core::IllegalArgumentException{ls::std::io::SectionPairMessageFormatter::getFormattedMessage(message)};
+  }
+}

+ 27 - 0
source/ls-std/io/section-pair/evaluator/SectionPairSectionArgumentEvaluator.cpp

@@ -0,0 +1,27 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-20
+* Changed:         2023-02-22
+*
+* */
+
+#include <ls-std/core/exception/IllegalArgumentException.hpp>
+#include <ls-std/io/section-pair/SectionPairMessageFormatter.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairSectionArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairSectionValidator.hpp>
+
+ls::std::io::SectionPairSectionArgumentEvaluator::SectionPairSectionArgumentEvaluator(::std::string _section) : ls::std::core::Class("SectionPairSectionArgumentEvaluator"), section(::std::move(_section))
+{}
+
+ls::std::io::SectionPairSectionArgumentEvaluator::~SectionPairSectionArgumentEvaluator() = default;
+
+void ls::std::io::SectionPairSectionArgumentEvaluator::evaluate()
+{
+  if (!ls::std::io::SectionPairSectionValidator{this->section}.isValid())
+  {
+    ::std::string message = "\"" + this->section + "\" is not a valid section!";
+    throw ls::std::core::IllegalArgumentException{ls::std::io::SectionPairMessageFormatter::getFormattedMessage(message)};
+  }
+}

+ 27 - 0
source/ls-std/io/section-pair/evaluator/SectionPairValueArgumentEvaluator.cpp

@@ -0,0 +1,27 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-22
+*
+* */
+
+#include <ls-std/core/exception/IllegalArgumentException.hpp>
+#include <ls-std/io/section-pair/SectionPairMessageFormatter.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairValueArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairValueValidator.hpp>
+
+ls::std::io::SectionPairValueArgumentEvaluator::SectionPairValueArgumentEvaluator(ls::std::io::section_pair_row_value _value) : ls::std::core::Class("SectionPairValueArgumentEvaluator"), value(::std::move(_value))
+{}
+
+ls::std::io::SectionPairValueArgumentEvaluator::~SectionPairValueArgumentEvaluator() = default;
+
+void ls::std::io::SectionPairValueArgumentEvaluator::evaluate()
+{
+  if (!ls::std::io::SectionPairValueValidator(this->value).isValid())
+  {
+    ::std::string message = "\"" + this->value + "\" is not a valid value!";
+    throw ls::std::core::IllegalArgumentException{ls::std::io::SectionPairMessageFormatter::getFormattedMessage(message)};
+  }
+}

+ 124 - 0
source/ls-std/io/section-pair/model/SectionPairDocument.cpp

@@ -0,0 +1,124 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-15
+* Changed:         2023-02-22
+*
+* */
+
+#include <ls-std/core/ConditionalFunctionExecutor.hpp>
+#include <ls-std/core/evaluator/IndexOutOfBoundsEvaluator.hpp>
+#include <ls-std/core/evaluator/NullPointerArgumentEvaluator.hpp>
+#include <ls-std/core/exception/IllegalArgumentException.hpp>
+#include <ls-std/io/section-pair/SectionPairMessageFormatter.hpp>
+#include <ls-std/io/section-pair/model/SectionPairDocument.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairDocument.hpp>
+
+ls::std::io::SectionPairDocument::SectionPairDocument() : ls::std::core::Class("SectionPairDocument")
+{}
+
+ls::std::io::SectionPairDocument::~SectionPairDocument() = default;
+
+void ls::std::io::SectionPairDocument::add(const section_pair_document_section_list_element &_section)
+{
+  ::std::string message = this->getClassName() + ": add section attempt failed, since \"_section\" argument is null!";
+  ls::std::core::NullPointerArgumentEvaluator(::std::reinterpret_pointer_cast<void>(_section), message).evaluate();
+  this->_checkSectionExistence(_section->getSectionId());
+  this->sections.push_back(_section);
+}
+
+void ls::std::io::SectionPairDocument::clear()
+{
+  this->sections.clear();
+}
+
+ls::std::io::section_pair_document_section_list_element ls::std::io::SectionPairDocument::get(size_t _index)
+{
+  ls::std::io::section_pair_document_section_list_element element{};
+  ls::std::core::IndexOutOfBoundsEvaluator{_index, this->sections.size()}.evaluate();
+  size_t index{};
+
+  for (const auto &_element : this->sections)
+  {
+    if (_index == index)
+    {
+      element = _element;
+      break;
+    }
+
+    ++index;
+  }
+
+  return element;
+}
+
+size_t ls::std::io::SectionPairDocument::getAmountOfSections()
+{
+  return this->sections.size();
+}
+
+::std::string ls::std::io::SectionPairDocument::getHeader()
+{
+  return this->header;
+}
+
+ls::std::io::section_pair_document_section_list ls::std::io::SectionPairDocument::getSectionList()
+{
+  return this->sections;
+}
+
+ls::std::core::type::byte_field ls::std::io::SectionPairDocument::marshal()
+{
+  ls::std::core::ConditionalFunctionExecutor{this->serializable == nullptr}.execute([this] { _createSerializable(); });
+  return this->serializable->marshal();
+}
+
+void ls::std::io::SectionPairDocument::reserveNewLine(const ::std::string &_reservedNewLine)
+{
+  this->reservedNewLine = _reservedNewLine;
+}
+
+void ls::std::io::SectionPairDocument::unmarshal(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::core::ConditionalFunctionExecutor{this->serializable == nullptr}.execute([this] { _createSerializable(); });
+  this->serializable->unmarshal(_data);
+}
+
+void ls::std::io::SectionPairDocument::_checkSectionExistence(const ls::std::io::section_pair_identifier &_sectionId)
+{
+  if (this->_hasSection(_sectionId))
+  {
+    ::std::string message = this->getClassName() + "section ID \"" + _sectionId + "\" already exists in document!";
+    throw ls::std::core::IllegalArgumentException{ls::std::io::SectionPairMessageFormatter::getFormattedMessage(message)};
+  }
+}
+
+void ls::std::io::SectionPairDocument::_createSerializable()
+{
+  ls::std::io::SerializableSectionPairParameter parameter{};
+  parameter.setValue(shared_from_this());
+
+  if (!this->reservedNewLine.empty())
+  {
+    parameter.setNewLine(this->reservedNewLine);
+  }
+
+  this->serializable = ::std::make_shared<ls::std::io::SerializableSectionPairDocument>(parameter);
+}
+
+bool ls::std::io::SectionPairDocument::_hasSection(const ls::std::io::section_pair_identifier &_identifier)
+{
+  bool sectionExists{};
+
+  for (const auto &_section : this->sections)
+  {
+    if (_section->getSectionId() == _identifier)
+    {
+      sectionExists = true;
+      break;
+    }
+  }
+
+  return sectionExists;
+}

+ 108 - 0
source/ls-std/io/section-pair/model/SectionPairRow.cpp

@@ -0,0 +1,108 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-08
+* Changed:         2023-02-19
+*
+* */
+
+#include <ls-std/core/ConditionalFunctionExecutor.hpp>
+#include <ls-std/core/evaluator/EmptyStringArgumentEvaluator.hpp>
+#include <ls-std/core/exception/IllegalArgumentException.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairIdentifierArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRow.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowListValue.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowSingleValue.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairRow.hpp>
+
+ls::std::io::SectionPairRow::SectionPairRow(const ls::std::io::section_pair_identifier &_key, const ls::std::io::SectionPairRowEnumType &_type) : ls::std::core::Class("SectionPairRow")
+{
+  this->_setKey(_key);
+  this->_initValue(_type);
+}
+
+ls::std::io::SectionPairRow::~SectionPairRow() = default;
+
+ls::std::io::section_pair_row_value ls::std::io::SectionPairRow::getKey()
+{
+  return this->key;
+}
+
+::std::shared_ptr<ls::std::io::SectionPairRowValue> ls::std::io::SectionPairRow::getValue()
+{
+  return this->value;
+}
+
+bool ls::std::io::SectionPairRow::isList()
+{
+  return this->value->getType() == ls::std::io::SectionPairRowEnumType::SECTION_PAIR_ROW_LIST_VALUE;
+}
+
+bool ls::std::io::SectionPairRow::isSingleValue()
+{
+  return this->value->getType() == ls::std::io::SectionPairRowEnumType::SECTION_PAIR_ROW_SINGLE_VALUE;
+}
+
+ls::std::core::type::byte_field ls::std::io::SectionPairRow::marshal()
+{
+  ls::std::core::ConditionalFunctionExecutor{this->serializable == nullptr}.execute([this] { _createSerializable(); });
+  return this->serializable->marshal();
+}
+
+void ls::std::io::SectionPairRow::reserveNewLine(const ::std::string &_reservedNewLine)
+{
+  this->reservedNewLine = _reservedNewLine;
+}
+
+void ls::std::io::SectionPairRow::setKey(const ls::std::io::section_pair_identifier &_key)
+{
+  this->_setKey(_key);
+}
+
+void ls::std::io::SectionPairRow::unmarshal(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::core::ConditionalFunctionExecutor{this->serializable == nullptr}.execute([this] { _createSerializable(); });
+  this->serializable->unmarshal(_data);
+}
+
+void ls::std::io::SectionPairRow::_createSerializable()
+{
+  ls::std::io::SerializableSectionPairParameter parameter{};
+  parameter.setValue(shared_from_this());
+
+  if (!this->reservedNewLine.empty())
+  {
+    parameter.setNewLine(this->reservedNewLine);
+  }
+
+  this->serializable = ::std::make_shared<ls::std::io::SerializableSectionPairRow>(parameter);
+}
+
+void ls::std::io::SectionPairRow::_initValue(const ls::std::io::SectionPairRowEnumType &_type)
+{
+  switch (_type)
+  {
+    case SECTION_PAIR_ROW_NOT_IMPLEMENTED:
+    {
+      throw ls::std::core::IllegalArgumentException{this->getClassName() + ": default row enum type can not be set!"};
+    }
+    case SECTION_PAIR_ROW_LIST_VALUE:
+    {
+      this->value = ::std::make_shared<ls::std::io::SectionPairRowListValue>();
+    }
+    break;
+    case SECTION_PAIR_ROW_SINGLE_VALUE:
+    {
+      this->value = ::std::make_shared<ls::std::io::SectionPairRowSingleValue>("empty");
+    }
+    break;
+  }
+}
+
+void ls::std::io::SectionPairRow::_setKey(const ls::std::io::section_pair_identifier &_key)
+{
+  ls::std::core::EmptyStringArgumentEvaluator{_key, this->getClassName() + ": passed key identifier is empty!"}.evaluate();
+  ls::std::io::SectionPairIdentifierArgumentEvaluator(_key).evaluate();
+  this->key = _key;
+}

+ 92 - 0
source/ls-std/io/section-pair/model/SectionPairRowListValue.cpp

@@ -0,0 +1,92 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-22
+*
+* */
+
+#include <ls-std/core/ConditionalFunctionExecutor.hpp>
+#include <ls-std/core/evaluator/EmptyStringArgumentEvaluator.hpp>
+#include <ls-std/core/evaluator/IndexOutOfBoundsEvaluator.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairValueArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowListValue.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairRowListValue.hpp>
+
+ls::std::io::SectionPairRowListValue::SectionPairRowListValue() : ls::std::core::Class("SectionPairRowListValue"), ls::std::io::SectionPairRowValue(ls::std::io::SectionPairRowEnumType::SECTION_PAIR_ROW_LIST_VALUE)
+{}
+
+ls::std::io::SectionPairRowListValue::~SectionPairRowListValue() = default;
+
+void ls::std::io::SectionPairRowListValue::add(const ls::std::io::section_pair_row_value &_value)
+{
+  ls::std::core::EmptyStringArgumentEvaluator{_value}.evaluate();
+  ls::std::io::SectionPairValueArgumentEvaluator{_value}.evaluate();
+  this->values.push_back(_value);
+}
+
+void ls::std::io::SectionPairRowListValue::clear()
+{
+  this->values.clear();
+}
+
+ls::std::io::section_pair_row_value ls::std::io::SectionPairRowListValue::get(size_t _index)
+{
+  ls::std::core::IndexOutOfBoundsEvaluator(_index, this->values.size()).evaluate();
+  ls::std::io::section_pair_row_value value{};
+  size_t index{};
+
+  for (const auto &_value : this->values)
+  {
+    if (index == _index)
+    {
+      value = _value;
+      break;
+    }
+
+    ++index;
+  }
+
+  return value;
+}
+
+::std::list<ls::std::io::section_pair_row_value> ls::std::io::SectionPairRowListValue::getList()
+{
+  return this->values;
+}
+
+size_t ls::std::io::SectionPairRowListValue::getSize()
+{
+  return this->values.size();
+}
+
+ls::std::io::SectionPairRowEnumType ls::std::io::SectionPairRowListValue::getType()
+{
+  return this->type;
+}
+
+ls::std::core::type::byte_field ls::std::io::SectionPairRowListValue::marshal()
+{
+  ls::std::core::ConditionalFunctionExecutor{this->serializable == nullptr}.execute([this] { _createSerializable(); });
+  return this->serializable->marshal();
+}
+
+void ls::std::io::SectionPairRowListValue::unmarshal(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::core::ConditionalFunctionExecutor{this->serializable == nullptr}.execute([this] { _createSerializable(); });
+  this->serializable->unmarshal(_data);
+}
+
+void ls::std::io::SectionPairRowListValue::_createSerializable()
+{
+  ls::std::io::SerializableSectionPairParameter parameter{};
+  parameter.setValue(shared_from_this());
+
+  if (!this->reservedNewLine.empty())
+  {
+    parameter.setNewLine(this->reservedNewLine);
+  }
+
+  this->serializable = ::std::make_shared<ls::std::io::SerializableSectionPairRowListValue>(parameter);
+}

+ 75 - 0
source/ls-std/io/section-pair/model/SectionPairRowSingleValue.cpp

@@ -0,0 +1,75 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-19
+*
+* */
+
+#include <ls-std/core/ConditionalFunctionExecutor.hpp>
+#include <ls-std/core/evaluator/EmptyStringArgumentEvaluator.hpp>
+#include <ls-std/io/NewLine.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairValueArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowSingleValue.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairRowSingleValue.hpp>
+
+ls::std::io::SectionPairRowSingleValue::SectionPairRowSingleValue(const ls::std::io::section_pair_row_value &_value) : ls::std::core::Class("SectionPairRowSingleValue"), ls::std::io::SectionPairRowValue(ls::std::io::SECTION_PAIR_ROW_SINGLE_VALUE)
+{
+  this->_set(_value);
+}
+
+ls::std::io::SectionPairRowSingleValue::~SectionPairRowSingleValue() = default;
+
+ls::std::io::section_pair_row_value ls::std::io::SectionPairRowSingleValue::get()
+{
+  return this->value;
+}
+
+ls::std::io::SectionPairRowEnumType ls::std::io::SectionPairRowSingleValue::getType()
+{
+  return this->type;
+}
+
+ls::std::core::type::byte_field ls::std::io::SectionPairRowSingleValue::marshal()
+{
+  ls::std::core::ConditionalFunctionExecutor{this->serializable == nullptr}.execute([this] { _createSerializable(); });
+  return this->serializable->marshal();
+}
+
+void ls::std::io::SectionPairRowSingleValue::set(const ls::std::io::section_pair_row_value &_value)
+{
+  this->_set(_value);
+}
+
+void ls::std::io::SectionPairRowSingleValue::unmarshal(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::core::ConditionalFunctionExecutor{this->serializable == nullptr}.execute([this] { _createSerializable(); });
+  this->serializable->unmarshal(_data);
+}
+
+void ls::std::io::SectionPairRowSingleValue::_createSerializable()
+{
+  SerializableSectionPairParameter parameter{};
+  parameter.setValue(shared_from_this());
+
+  if (!this->reservedNewLine.empty())
+  {
+    parameter.setNewLine(this->reservedNewLine);
+  }
+
+  this->serializable = ::std::make_shared<ls::std::io::SerializableSectionPairRowSingleValue>(parameter);
+}
+
+void ls::std::io::SectionPairRowSingleValue::_set(const ls::std::io::section_pair_row_value &_value)
+{
+  ls::std::core::EmptyStringArgumentEvaluator{_value}.evaluate();
+  ls::std::io::SectionPairValueArgumentEvaluator(_value).evaluate();
+  ::std::string newLine = this->reservedNewLine.empty() ? NewLine::get() : this->reservedNewLine;
+  this->value = _value;
+
+  if (this->value.find(newLine) != ::std::string::npos)
+  {
+    this->value.replace(this->value.find(newLine), newLine.size(), "");
+  }
+}

+ 28 - 0
source/ls-std/io/section-pair/model/SectionPairRowValue.cpp

@@ -0,0 +1,28 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-17
+*
+* */
+
+#include <ls-std/io/section-pair/model/SectionPairRowValue.hpp>
+
+ls::std::io::SectionPairRowValue::SectionPairRowValue(const ls::std::io::SectionPairRowEnumType &_type) : type(_type)
+{}
+
+ls::std::io::SectionPairRowValue::~SectionPairRowValue() = default;
+
+ls::std::core::type::byte_field ls::std::io::SectionPairRowValue::marshal()
+{
+  return ls::std::core::type::byte_field{};
+}
+
+void ls::std::io::SectionPairRowValue::reserveNewLine(const ::std::string &_reservedNewLine)
+{
+  this->reservedNewLine = _reservedNewLine;
+}
+
+void ls::std::io::SectionPairRowValue::unmarshal(const ls::std::core::type::byte_field &_data)
+{}

+ 138 - 0
source/ls-std/io/section-pair/model/SectionPairSection.cpp

@@ -0,0 +1,138 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-13
+* Changed:         2023-02-22
+*
+* */
+
+#include <ls-std/core/ConditionalFunctionExecutor.hpp>
+#include <ls-std/core/evaluator/EmptyStringArgumentEvaluator.hpp>
+#include <ls-std/core/evaluator/IndexOutOfBoundsEvaluator.hpp>
+#include <ls-std/core/evaluator/NullPointerArgumentEvaluator.hpp>
+#include <ls-std/core/exception/IllegalArgumentException.hpp>
+#include <ls-std/io/section-pair/SectionPairMessageFormatter.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairIdentifierArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/model/SectionPairSection.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairSection.hpp>
+
+ls::std::io::SectionPairSection::SectionPairSection(const ls::std::io::section_pair_identifier &_sectionId) : ls::std::core::Class("SectionPairSection")
+{
+  this->_setSectionId(_sectionId);
+}
+
+ls::std::io::SectionPairSection::~SectionPairSection() = default;
+
+void ls::std::io::SectionPairSection::add(const section_pair_row_list_element &_row)
+{
+  ls::std::core::NullPointerArgumentEvaluator{::std::reinterpret_pointer_cast<void>(_row)}.evaluate();
+  this->_rowExistenceCheck(_row->getKey());
+  this->rows.push_back(_row);
+}
+
+void ls::std::io::SectionPairSection::clear()
+{
+  this->rows.clear();
+}
+
+ls::std::io::section_pair_row_list_element ls::std::io::SectionPairSection::get(size_t _index)
+{
+  ls::std::core::IndexOutOfBoundsEvaluator{_index, this->rows.size()}.evaluate();
+  ls::std::io::section_pair_row_list_element element{};
+  size_t index{};
+
+  for (const auto &_element : this->rows)
+  {
+    if (index == _index)
+    {
+      element = _element;
+      break;
+    }
+
+    ++index;
+  }
+
+  return element;
+}
+
+ls::std::io::section_pair_row_list ls::std::io::SectionPairSection::getList()
+{
+  return this->rows;
+}
+
+size_t ls::std::io::SectionPairSection::getRowAmount()
+{
+  return this->rows.size();
+}
+
+ls::std::io::section_pair_identifier ls::std::io::SectionPairSection::getSectionId()
+{
+  return this->sectionId;
+}
+
+ls::std::core::type::byte_field ls::std::io::SectionPairSection::marshal()
+{
+  ls::std::core::ConditionalFunctionExecutor{this->serializable == nullptr}.execute([this] { _createSerializable(); });
+  return this->serializable->marshal();
+}
+
+void ls::std::io::SectionPairSection::reserveNewLine(const ::std::string &_reservedNewLine)
+{
+  this->reservedNewLine = _reservedNewLine;
+}
+
+void ls::std::io::SectionPairSection::setSectionId(const ls::std::io::section_pair_identifier &_sectionId)
+{
+  this->_setSectionId(_sectionId);
+}
+
+void ls::std::io::SectionPairSection::unmarshal(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::core::ConditionalFunctionExecutor{this->serializable == nullptr}.execute([this] { _createSerializable(); });
+  this->serializable->unmarshal(_data);
+}
+
+void ls::std::io::SectionPairSection::_createSerializable()
+{
+  ls::std::io::SerializableSectionPairParameter parameter{};
+  parameter.setValue(shared_from_this());
+
+  if (!this->reservedNewLine.empty())
+  {
+    parameter.setNewLine(this->reservedNewLine);
+  }
+
+  this->serializable = ::std::make_shared<ls::std::io::SerializableSectionPairSection>(parameter);
+}
+
+bool ls::std::io::SectionPairSection::_hasRow(const ls::std::io::section_pair_identifier &_key)
+{
+  bool rowExists{};
+
+  for (const auto &_row : this->rows)
+  {
+    if (_row->getKey() == _key)
+    {
+      rowExists = true;
+      break;
+    }
+  }
+
+  return rowExists;
+}
+
+void ls::std::io::SectionPairSection::_rowExistenceCheck(const ls::std::io::section_pair_identifier &_key)
+{
+  if (this->_hasRow(_key))
+  {
+    ::std::string message = this->getClassName() + ": row key \"" + _key + "\" already exists in section \"" + this->sectionId + "\"!";
+    throw ls::std::core::IllegalArgumentException{ls::std::io::SectionPairMessageFormatter::getFormattedMessage(message)};
+  }
+}
+void ls::std::io::SectionPairSection::_setSectionId(const ls::std::io::section_pair_identifier &_sectionId)
+{
+  ls::std::core::EmptyStringArgumentEvaluator{_sectionId}.evaluate();
+  ls::std::io::SectionPairIdentifierArgumentEvaluator(_sectionId).evaluate();
+  this->sectionId = _sectionId;
+}

+ 68 - 0
source/ls-std/io/section-pair/reader/SectionPairFileReader.cpp

@@ -0,0 +1,68 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-21
+* Changed:         2023-02-21
+*
+* */
+
+#include <ls-std/core/ConditionalFunctionExecutor.hpp>
+#include <ls-std/core/exception/IllegalArgumentException.hpp>
+#include <ls-std/io/FileReader.hpp>
+#include <ls-std/io/evaluator/FileExistenceEvaluator.hpp>
+#include <ls-std/io/section-pair/model/SectionPairDocument.hpp>
+#include <ls-std/io/section-pair/reader/SectionPairFileReader.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairFileExtensionValidator.hpp>
+#include <memory>
+
+ls::std::io::SectionPairFileReader::SectionPairFileReader(const ls::std::io::SectionPairFileReaderParameter &_parameter) : ls::std::core::Class("SectionPairFileReader")
+{
+  this->parameter = _parameter;
+  ls::std::core::ConditionalFunctionExecutor{this->parameter.getFileExistenceEvaluator() == nullptr}.execute([this] { _createFileExistenceEvaluator(); });
+  this->parameter.getFileExistenceEvaluator()->evaluate();
+  this->_checkFileExtension();
+  ls::std::core::ConditionalFunctionExecutor{this->parameter.getReader() == nullptr}.execute([this] { _createReader(); });
+  ls::std::core::ConditionalFunctionExecutor{this->parameter.getDocument() == nullptr}.execute([this] { _createDocument(); });
+}
+
+ls::std::io::SectionPairFileReader::~SectionPairFileReader() = default;
+
+::std::shared_ptr<ls::std::io::SectionPairDocument> ls::std::io::SectionPairFileReader::getDocument()
+{
+  return this->parameter.getDocument();
+}
+
+ls::std::core::type::byte_field ls::std::io::SectionPairFileReader::read()
+{
+  this->parameter.getDocument()->clear();
+  ls::std::core::type::byte_field data = this->parameter.getReader()->read();
+  this->parameter.getDocument()->unmarshal(data);
+
+  return data;
+}
+
+void ls::std::io::SectionPairFileReader::_checkFileExtension()
+{
+  if (!ls::std::io::SectionPairFileExtensionValidator{this->parameter.getFilePath()}.isValid())
+  {
+    ::std::string message = "\"" + this->parameter.getFilePath() + "\" does not have a valid section pair file extension (.txt or .sp)!";
+    throw ls::std::core::IllegalArgumentException{message};
+  }
+}
+
+void ls::std::io::SectionPairFileReader::_createDocument()
+{
+  this->parameter.setDocument(::std::make_shared<ls::std::io::SectionPairDocument>());
+}
+
+void ls::std::io::SectionPairFileReader::_createFileExistenceEvaluator()
+{
+  this->parameter.setFileExistenceEvaluator(::std::make_shared<FileExistenceEvaluator>(this->parameter.getFilePath()));
+}
+
+void ls::std::io::SectionPairFileReader::_createReader()
+{
+  ls::std::io::File file{this->parameter.getFilePath()};
+  this->parameter.setReader(::std::make_shared<ls::std::io::FileReader>(file));
+}

+ 54 - 0
source/ls-std/io/section-pair/reader/SectionPairFileReaderParameter.cpp

@@ -0,0 +1,54 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-21
+* Changed:         2023-02-21
+*
+* */
+
+#include <ls-std/io/section-pair/reader/SectionPairFileReaderParameter.hpp>
+
+ls::std::io::SectionPairFileReaderParameter::SectionPairFileReaderParameter() = default;
+
+ls::std::io::SectionPairFileReaderParameter::~SectionPairFileReaderParameter() = default;
+
+::std::shared_ptr<ls::std::io::SectionPairDocument> ls::std::io::SectionPairFileReaderParameter::getDocument()
+{
+  return this->document;
+}
+
+::std::shared_ptr<ls::std::core::interface_type::IEvaluator> ls::std::io::SectionPairFileReaderParameter::getFileExistenceEvaluator()
+{
+  return this->fileExistenceEvaluator;
+}
+
+::std::string ls::std::io::SectionPairFileReaderParameter::getFilePath()
+{
+  return this->filePath;
+}
+
+::std::shared_ptr<ls::std::core::interface_type::IReader> ls::std::io::SectionPairFileReaderParameter::getReader()
+{
+  return this->reader;
+}
+
+void ls::std::io::SectionPairFileReaderParameter::setDocument(const ::std::shared_ptr<ls::std::io::SectionPairDocument> &_document)
+{
+  this->document = _document;
+}
+
+void ls::std::io::SectionPairFileReaderParameter::setFileExistenceEvaluator(const ::std::shared_ptr<ls::std::core::interface_type::IEvaluator> &_fileExistenceEvaluator)
+{
+  this->fileExistenceEvaluator = _fileExistenceEvaluator;
+}
+
+void ls::std::io::SectionPairFileReaderParameter::setFilePath(const ::std::string &_filePath)
+{
+  this->filePath = _filePath;
+}
+
+void ls::std::io::SectionPairFileReaderParameter::setReader(const ::std::shared_ptr<ls::std::core::interface_type::IReader> &_reader)
+{
+  this->reader = _reader;
+}

+ 108 - 0
source/ls-std/io/section-pair/serialization/SerializableSectionPairDocument.cpp

@@ -0,0 +1,108 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-16
+* Changed:         2023-02-21
+*
+* */
+
+#include <ls-std/core/evaluator/NullPointerArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/model/SectionPairDocument.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairDocument.hpp>
+#include <string>
+
+ls::std::io::SerializableSectionPairDocument::SerializableSectionPairDocument(const ls::std::io::SerializableSectionPairParameter &_parameter) : ls::std::core::Class("SerializableSectionPairDocument")
+{
+  ::std::string message = this->getClassName() + ": model reference is null!";
+  ls::std::core::NullPointerArgumentEvaluator{_parameter.getValue(), message}.evaluate();
+  this->parameter = _parameter;
+}
+
+ls::std::io::SerializableSectionPairDocument::~SerializableSectionPairDocument() = default;
+
+::std::shared_ptr<ls::std::core::Class> ls::std::io::SerializableSectionPairDocument::getValue()
+{
+  return this->parameter.getValue();
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairDocument::marshal()
+{
+  ::std::shared_ptr<ls::std::io::SectionPairDocument> document = ::std::dynamic_pointer_cast<ls::std::io::SectionPairDocument>(this->parameter.getValue());
+  ::std::string newLine = this->parameter.getNewLine();
+  ls::std::core::type::byte_field serializedDocument = document->getHeader() + newLine;
+
+  for (const auto &_section : document->getSectionList())
+  {
+    _section->reserveNewLine(this->parameter.getNewLine());
+    serializedDocument += _section->marshal();
+  }
+
+  return serializedDocument;
+}
+
+void ls::std::io::SerializableSectionPairDocument::unmarshal(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::core::type::byte_field serializedDocument = _data;
+  size_t headerSize = ::std::dynamic_pointer_cast<ls::std::io::SectionPairDocument>(this->parameter.getValue())->getHeader().size() + this->parameter.getNewLine().size();
+  serializedDocument = serializedDocument.substr(headerSize);
+  ls::std::core::type::byte_field serializedSection{};
+
+  do
+  {
+    serializedSection = this->_getNextSerializedSection(serializedDocument);
+    this->_addSection(serializedSection);
+    serializedDocument = serializedDocument.substr(serializedSection.size());
+  } while (!serializedDocument.empty());
+}
+
+void ls::std::io::SerializableSectionPairDocument::_addSection(const ls::std::core::type::byte_field &_serializedSection)
+{
+  ::std::shared_ptr<ls::std::io::SectionPairSection> section = ::std::make_shared<ls::std::io::SectionPairSection>("tmp-id");
+  section->reserveNewLine(this->parameter.getNewLine());
+  section->unmarshal(_serializedSection);
+  ::std::dynamic_pointer_cast<ls::std::io::SectionPairDocument>(this->parameter.getValue())->add(section);
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairDocument::_getCurrentRow(size_t _iterations, const ls::std::core::type::byte_field &_serializedDocument)
+{
+  ::std::string newLine = this->parameter.getNewLine();
+  ::std::string currentRow{};
+
+  if (_iterations == 1 || _serializedDocument.find('[') != ::std::string::npos)
+  {
+    currentRow = _serializedDocument.substr(0, _serializedDocument.find(newLine + newLine) + 2 * newLine.size());
+  }
+  else
+  {
+    currentRow = _serializedDocument.substr(0, _serializedDocument.find(newLine) + newLine.size());
+  }
+
+  return currentRow;
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairDocument::_getNextSerializedSection(const ls::std::core::type::byte_field &_serializedDocument)
+{
+  ls::std::core::type::byte_field serializedSection{}, currentRow{};
+  size_t iterations{};
+  ls::std::core::type::byte_field serializedDocument = _serializedDocument;
+  bool isNotNewSection{};
+  ::std::string newLine = this->parameter.getNewLine();
+
+  do
+  {
+    ++iterations;
+    currentRow = this->_getCurrentRow(iterations, serializedDocument);
+    isNotNewSection = this->_isNotNewSection(currentRow) && !serializedDocument.empty() || iterations == 1;
+    serializedDocument = serializedDocument.substr(currentRow.size());
+    serializedSection += currentRow;
+  } while (isNotNewSection);
+
+  return serializedDocument.empty() ? serializedSection : serializedSection.substr(0, serializedSection.size() - newLine.size());
+}
+
+bool ls::std::io::SerializableSectionPairDocument::_isNotNewSection(const ls::std::core::type::byte_field &_currentRow)
+{
+  ::std::string newLine = this->parameter.getNewLine();
+  return _currentRow.find(newLine + newLine) == ::std::string::npos;
+}

+ 36 - 0
source/ls-std/io/section-pair/serialization/SerializableSectionPairParameter.cpp

@@ -0,0 +1,36 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-17
+* Changed:         2023-02-17
+*
+* */
+
+#include <ls-std/io/NewLine.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairParameter.hpp>
+
+ls::std::io::SerializableSectionPairParameter::SerializableSectionPairParameter() : parseNewLine(ls::std::io::NewLine::get())
+{}
+
+ls::std::io::SerializableSectionPairParameter::~SerializableSectionPairParameter() = default;
+
+::std::string ls::std::io::SerializableSectionPairParameter::getNewLine()
+{
+  return this->parseNewLine;
+}
+
+::std::shared_ptr<ls::std::core::Class> ls::std::io::SerializableSectionPairParameter::getValue() const
+{
+  return this->value;
+}
+
+void ls::std::io::SerializableSectionPairParameter::setNewLine(const ::std::string &_newLine)
+{
+  this->parseNewLine = _newLine;
+}
+
+void ls::std::io::SerializableSectionPairParameter::setValue(const ::std::shared_ptr<ls::std::core::Class> &_value)
+{
+  this->value = _value;
+}

+ 100 - 0
source/ls-std/io/section-pair/serialization/SerializableSectionPairRow.cpp

@@ -0,0 +1,100 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-11
+* Changed:         2023-02-20
+*
+* */
+
+#include <ls-std/core/evaluator/NullPointerArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairRowListValueArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairRowSingleValueArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRow.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowListValue.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowSingleValue.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairRow.hpp>
+
+ls::std::io::SerializableSectionPairRow::SerializableSectionPairRow(const SerializableSectionPairParameter &_parameter) : ls::std::core::Class("SerializableSectionPairRow")
+{
+  ::std::string message = this->getClassName() + ": model reference is null!";
+  ls::std::core::NullPointerArgumentEvaluator{_parameter.getValue(), message}.evaluate();
+  this->parameter = _parameter;
+}
+
+ls::std::io::SerializableSectionPairRow::~SerializableSectionPairRow() = default;
+
+::std::shared_ptr<ls::std::core::Class> ls::std::io::SerializableSectionPairRow::getValue()
+{
+  return this->parameter.getValue();
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairRow::marshal()
+{
+  ls::std::core::type::byte_field data = this->_marshalKey();
+  ::std::shared_ptr<SectionPairRow> row = ::std::dynamic_pointer_cast<ls::std::io::SectionPairRow>(this->parameter.getValue());
+  row->getValue()->reserveNewLine(this->parameter.getNewLine());
+  return data + row->getValue()->marshal();
+}
+
+void ls::std::io::SerializableSectionPairRow::unmarshal(const ls::std::core::type::byte_field &_data)
+{
+  ::std::shared_ptr<ls::std::io::SectionPairRow> row = ::std::dynamic_pointer_cast<ls::std::io::SectionPairRow>(this->parameter.getValue());
+  row->getValue()->reserveNewLine(this->parameter.getNewLine());
+
+  if (row->isSingleValue())
+  {
+    this->_unmarshalSingleValue(_data);
+  }
+
+  if (row->isList())
+  {
+    this->_unmarshalListValue(_data);
+  }
+}
+
+::std::string ls::std::io::SerializableSectionPairRow::_marshalKey()
+{
+  ::std::string serializedKey{};
+  ::std::shared_ptr<ls::std::io::SectionPairRow> row = ::std::dynamic_pointer_cast<ls::std::io::SectionPairRow>(this->parameter.getValue());
+
+  if (row->isSingleValue())
+  {
+    serializedKey = row->getKey() + "=";
+  }
+
+  if (row->isList())
+  {
+    serializedKey = row->getKey() + ":" + this->parameter.getNewLine();
+  }
+
+  return serializedKey;
+}
+
+void ls::std::io::SerializableSectionPairRow::_unmarshalListValue(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::io::SectionPairRowListValueArgumentEvaluator{_data}.evaluate();
+  ::std::string::size_type separatorPosition = _data.find(':');
+  ::std::string newLine = this->parameter.getNewLine();
+
+  if (separatorPosition != ::std::string::npos)
+  {
+    ::std::shared_ptr<ls::std::io::SectionPairRow> row = ::std::dynamic_pointer_cast<ls::std::io::SectionPairRow>(this->parameter.getValue());
+    row->setKey(_data.substr(0, separatorPosition));
+    ::std::string::size_type newLinePosition = _data.find(newLine) + (newLine.size() - 1);
+    ::std::dynamic_pointer_cast<ls::std::io::SectionPairRowListValue>(row->getValue())->unmarshal(_data.substr(newLinePosition + 1));
+  }
+}
+
+void ls::std::io::SerializableSectionPairRow::_unmarshalSingleValue(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::io::SectionPairRowSingleValueArgumentEvaluator{_data}.evaluate();
+  ::std::string::size_type position = _data.find('=');
+
+  if (position != ::std::string::npos)
+  {
+    ::std::shared_ptr<ls::std::io::SectionPairRow> row = ::std::dynamic_pointer_cast<ls::std::io::SectionPairRow>(this->parameter.getValue());
+    row->setKey(_data.substr(0, position));
+    ::std::dynamic_pointer_cast<ls::std::io::SectionPairRowSingleValue>(row->getValue())->unmarshal(_data.substr(position + 1));
+  }
+}

+ 83 - 0
source/ls-std/io/section-pair/serialization/SerializableSectionPairRowListValue.cpp

@@ -0,0 +1,83 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-11
+* Changed:         2023-02-17
+*
+* */
+
+#include <ls-std/core/evaluator/EmptyStringArgumentEvaluator.hpp>
+#include <ls-std/core/evaluator/NullPointerArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowListValue.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairRowListValue.hpp>
+
+ls::std::io::SerializableSectionPairRowListValue::SerializableSectionPairRowListValue(const ls::std::io::SerializableSectionPairParameter &_parameter) : ls::std::core::Class("SerializableSectionPairRowListValue")
+{
+  ::std::string message = this->getClassName() + ": model reference is null!";
+  ls::std::core::NullPointerArgumentEvaluator{_parameter.getValue(), message}.evaluate();
+  this->parameter = _parameter;
+}
+
+ls::std::io::SerializableSectionPairRowListValue::~SerializableSectionPairRowListValue() = default;
+
+::std::shared_ptr<ls::std::core::Class> ls::std::io::SerializableSectionPairRowListValue::getValue()
+{
+  return this->parameter.getValue();
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairRowListValue::marshal()
+{
+  ls::std::core::type::byte_field data{};
+
+  for (const auto &_value : ::std::dynamic_pointer_cast<ls::std::io::SectionPairRowListValue>(this->getValue())->getList())
+  {
+    data += "  " + _value + this->parameter.getNewLine();
+  }
+
+  return data;
+}
+
+void ls::std::io::SerializableSectionPairRowListValue::unmarshal(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::core::EmptyStringArgumentEvaluator{_data}.evaluate();
+  ls::std::core::type::byte_field searchText = _data;
+  ::std::string newLine = this->parameter.getNewLine();
+
+  while (!searchText.empty() && searchText != newLine)
+  {
+    ::std::string::size_type positionOfNewLine = searchText.find(newLine);
+    ::std::string line = ls::std::io::SerializableSectionPairRowListValue::_getLine(positionOfNewLine, searchText);
+    line = line.substr(2);
+    ::std::dynamic_pointer_cast<ls::std::io::SectionPairRowListValue>(this->getValue())->add(line);
+    this->_updateSearchText(positionOfNewLine, searchText);
+  }
+}
+
+::std::string ls::std::io::SerializableSectionPairRowListValue::_getLine(::std::string::size_type _position, const ls::std::core::type::byte_field &_searchText)
+{
+  ::std::string line{};
+
+  if (_position != ::std::string::npos)
+  {
+    line = _searchText.substr(0, _position);
+  }
+  else
+  {
+    line = _searchText;
+  }
+
+  return line;
+}
+
+void ls::std::io::SerializableSectionPairRowListValue::_updateSearchText(::std::string::size_type _position, ls::std::core::type::byte_field &_searchText)
+{
+  if (_position != ::std::string::npos)
+  {
+    _searchText = _searchText.substr(_position + this->parameter.getNewLine().size());
+  }
+  else
+  {
+    _searchText = "";
+  }
+}

+ 38 - 0
source/ls-std/io/section-pair/serialization/SerializableSectionPairRowSingleValue.cpp

@@ -0,0 +1,38 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-11
+* Changed:         2023-02-17
+*
+* */
+
+#include <ls-std/core/evaluator/EmptyStringArgumentEvaluator.hpp>
+#include <ls-std/core/evaluator/NullPointerArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRowSingleValue.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairRowSingleValue.hpp>
+
+ls::std::io::SerializableSectionPairRowSingleValue::SerializableSectionPairRowSingleValue(const ls::std::io::SerializableSectionPairParameter &_parameter) : ls::std::core::Class("SerializableSectionPairRowSingleValue")
+{
+  ::std::string message = this->getClassName() + ": model reference is null!";
+  ls::std::core::NullPointerArgumentEvaluator{_parameter.getValue(), message}.evaluate();
+  this->parameter = _parameter;
+}
+
+ls::std::io::SerializableSectionPairRowSingleValue::~SerializableSectionPairRowSingleValue() = default;
+
+::std::shared_ptr<ls::std::core::Class> ls::std::io::SerializableSectionPairRowSingleValue::getValue()
+{
+  return this->parameter.getValue();
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairRowSingleValue::marshal()
+{
+  return ::std::dynamic_pointer_cast<ls::std::io::SectionPairRowSingleValue>(this->parameter.getValue())->get() + this->parameter.getNewLine();
+}
+
+void ls::std::io::SerializableSectionPairRowSingleValue::unmarshal(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::core::EmptyStringArgumentEvaluator{_data}.evaluate();
+  ::std::dynamic_pointer_cast<ls::std::io::SectionPairRowSingleValue>(this->parameter.getValue())->set(_data);
+}

+ 208 - 0
source/ls-std/io/section-pair/serialization/SerializableSectionPairSection.cpp

@@ -0,0 +1,208 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-14
+* Changed:         2023-02-21
+*
+* */
+
+#include <ls-std/core/evaluator/NullPointerArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/evaluator/SectionPairSectionArgumentEvaluator.hpp>
+#include <ls-std/io/section-pair/model/SectionPairRow.hpp>
+#include <ls-std/io/section-pair/model/SectionPairSection.hpp>
+#include <ls-std/io/section-pair/serialization/SerializableSectionPairSection.hpp>
+
+ls::std::io::SerializableSectionPairSection::SerializableSectionPairSection(const ls::std::io::SerializableSectionPairParameter &_parameter) : ls::std::core::Class("SerializableSectionPairSection")
+{
+  ::std::string message = this->getClassName() + ": model reference is null!";
+  ls::std::core::NullPointerArgumentEvaluator(_parameter.getValue(), message).evaluate();
+  this->parameter = _parameter;
+}
+
+ls::std::io::SerializableSectionPairSection::~SerializableSectionPairSection() = default;
+
+::std::shared_ptr<ls::std::core::Class> ls::std::io::SerializableSectionPairSection::getValue()
+{
+  return this->parameter.getValue();
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairSection::marshal()
+{
+  ls::std::core::type::byte_field serializedSection{};
+
+  serializedSection += this->_marshalSectionId();
+  serializedSection += this->_marshalRows();
+
+  return serializedSection;
+}
+
+void ls::std::io::SerializableSectionPairSection::unmarshal(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::io::SectionPairSectionArgumentEvaluator{_data}.evaluate();
+  size_t sectionHeaderSize = this->_unmarshalSectionHeader(_data);
+  this->_unmarshalRows(_data.substr(sectionHeaderSize));
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairSection::_collectSectionRow(const ls::std::core::type::byte_field &_currentRows, ls::std::io::SectionPairRowEnumType &_type)
+{
+  ::std::string row{};
+  ::std::string newLine = this->parameter.getNewLine();
+  ::std::string firstRow = _currentRows.substr(0, _currentRows.find(newLine) + newLine.size());
+
+  if (ls::std::io::SerializableSectionPairSection::_isSingleValueRow(firstRow))
+  {
+    row = ls::std::io::SerializableSectionPairSection::_collectSectionSingleValueRow(firstRow, _type);
+  }
+
+  if (ls::std::io::SerializableSectionPairSection::_isListValueRow(firstRow))
+  {
+    row = this->_collectSectionListValueRow(_currentRows, _type);
+  }
+
+  return row;
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairSection::_collectSectionListValueRow(const ls::std::core::type::byte_field &_currentRows, ls::std::io::SectionPairRowEnumType &_type)
+{
+  ls::std::core::type::byte_field currentRows = _currentRows;
+  ls::std::core::type::byte_field currentRow{}, row{};
+  ::std::string newLine = this->parameter.getNewLine();
+  _type = SectionPairRowEnumType::SECTION_PAIR_ROW_LIST_VALUE;
+  size_t iterations{};
+  bool isStillListRow{};
+
+  do
+  {
+    if (currentRows.empty() && iterations > 1)
+    {
+      break;
+    }
+
+    ++iterations;
+    currentRow = currentRows.substr(0, currentRows.find(newLine) + newLine.size());
+    currentRows = currentRows.substr(currentRow.size());
+    isStillListRow = !ls::std::io::SerializableSectionPairSection::_isStartingValueRow(currentRow) || iterations == 1;
+
+    if (isStillListRow)
+    {
+      row += currentRow;
+    }
+  } while (isStillListRow);
+
+  return row;
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairSection::_collectSectionSingleValueRow(const ls::std::core::type::byte_field &_firstRow, ls::std::io::SectionPairRowEnumType &_type)
+{
+  _type = SectionPairRowEnumType::SECTION_PAIR_ROW_SINGLE_VALUE;
+  return _firstRow;
+}
+
+size_t ls::std::io::SerializableSectionPairSection::_getNthSubStringPosition(const ls::std::core::type::byte_field &_text, const ls::std::core::type::byte_field &_subText)
+{
+  size_t position = -1;
+  size_t amount{};
+
+  for (int index = 0; index < (_text.size() - _subText.size()); index++)
+  {
+    if (_text.substr(index, _subText.size()) == _subText)
+    {
+      ++amount;
+    }
+
+    if (amount == 2)
+    {
+      position = index;
+      break;
+    }
+  }
+
+  return position;
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairSection::_getSectionHeader(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::core::type::byte_field sectionHeader{};
+  ::std::string newLine = this->parameter.getNewLine();
+  size_t position = ls::std::io::SerializableSectionPairSection::_getNthSubStringPosition(_data, newLine);
+
+  if (position != -1)
+  {
+    sectionHeader = _data.substr(0, position + 2 * newLine.size());
+  }
+
+  return sectionHeader;
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairSection::_getSectionId(const ls::std::core::type::byte_field &_sectionHeader)
+{
+  ls::std::core::type::byte_field sectionId = _sectionHeader.substr(_sectionHeader.find('[') + 1);
+  return sectionId.substr(0, sectionId.find(']'));
+}
+
+bool ls::std::io::SerializableSectionPairSection::_isListValueRow(const ::std::string &_currentRow)
+{
+  return _currentRow.find(':') != ::std::string::npos;
+}
+
+bool ls::std::io::SerializableSectionPairSection::_isStartingValueRow(const ::std::string &_currentRow)
+{
+  bool isSingleValue = ls::std::io::SerializableSectionPairSection::_isSingleValueRow(_currentRow);
+  bool isListValue = ls::std::io::SerializableSectionPairSection::_isListValueRow(_currentRow);
+
+  return isSingleValue || isListValue;
+}
+
+bool ls::std::io::SerializableSectionPairSection::_isSingleValueRow(const ::std::string &_currentRow)
+{
+  return _currentRow.find('=') != ::std::string::npos;
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairSection::_marshalRows()
+{
+  ls::std::core::type::byte_field serializedSectionRows{};
+
+  for (const auto &_row : ::std::dynamic_pointer_cast<ls::std::io::SectionPairSection>(this->parameter.getValue())->getList())
+  {
+    _row->reserveNewLine(this->parameter.getNewLine());
+    serializedSectionRows += _row->marshal();
+  }
+
+  return serializedSectionRows;
+}
+
+ls::std::core::type::byte_field ls::std::io::SerializableSectionPairSection::_marshalSectionId()
+{
+  ::std::string newLine = this->parameter.getNewLine();
+  return newLine + "[" + ::std::dynamic_pointer_cast<ls::std::io::SectionPairSection>(this->parameter.getValue())->getSectionId() + "]" + newLine + newLine;
+}
+
+void ls::std::io::SerializableSectionPairSection::_unmarshalRow(const ::std::string &_sectionRow, ls::std::io::SectionPairRowEnumType _type)
+{
+  ls::std::io::section_pair_row_list_element row = ::std::make_shared<ls::std::io::SectionPairRow>("tmp-dir", _type);
+  row->reserveNewLine(this->parameter.getNewLine());
+  row->unmarshal(_sectionRow);
+  ::std::dynamic_pointer_cast<ls::std::io::SectionPairSection>(this->parameter.getValue())->add(row);
+}
+
+void ls::std::io::SerializableSectionPairSection::_unmarshalRows(const ls::std::core::type::byte_field &_serializedRows)
+{
+  ::std::string currentRows = _serializedRows;
+  ls::std::io::SectionPairRowEnumType type{};
+
+  while (!currentRows.empty())
+  {
+    ::std::string sectionRow = this->_collectSectionRow(currentRows, type);
+    this->_unmarshalRow(sectionRow, type);
+    currentRows = currentRows.substr(sectionRow.size());
+  }
+}
+
+size_t ls::std::io::SerializableSectionPairSection::_unmarshalSectionHeader(const ls::std::core::type::byte_field &_data)
+{
+  ls::std::core::type::byte_field sectionHeader = this->_getSectionHeader(_data);
+  ::std::dynamic_pointer_cast<ls::std::io::SectionPairSection>(this->parameter.getValue())->setSectionId(ls::std::io::SerializableSectionPairSection::_getSectionId(sectionHeader));
+
+  return sectionHeader.size();
+}

+ 36 - 0
source/ls-std/io/section-pair/validator/SectionPairDocumentValidator.cpp

@@ -0,0 +1,36 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-21
+* Changed:         2023-02-21
+*
+* */
+
+#include <ls-std/io/section-pair/validator/SectionPairDocumentValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairSectionValidator.hpp>
+#include <regex>
+
+ls::std::io::SectionPairDocumentValidator::SectionPairDocumentValidator(::std::string _document) : ls::std::core::Class("SectionPairDocumentValidator"), document(::std::move(_document))
+{}
+
+ls::std::io::SectionPairDocumentValidator::~SectionPairDocumentValidator() = default;
+
+bool ls::std::io::SectionPairDocumentValidator::isValid()
+{
+  ::std::string validationRegex = ls::std::io::SectionPairDocumentValidator::_getValidationRegex();
+  static ::std::regex documentRegex = ::std::regex{"^" + validationRegex + "$"};
+
+  return ::std::regex_match(this->document, documentRegex);
+}
+
+::std::string ls::std::io::SectionPairDocumentValidator::_getValidationRegex()
+{
+  ::std::string newLine = R"(((\n)|(\r\n)))";
+  ::std::string documentHeader = R"((# {1}(section\-pair document))" + newLine + R"())";
+  ::std::string section = ls::std::io::SectionPairSectionValidator::getValidationRegex();
+  ::std::string atLeastOneSection = R"(()" + section + R"())";
+  ::std::string optionalSections = R"(()" + section + R"()*)";
+
+  return documentHeader + atLeastOneSection + optionalSections;
+}

+ 25 - 0
source/ls-std/io/section-pair/validator/SectionPairFileExtensionValidator.cpp

@@ -0,0 +1,25 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-21
+* Changed:         2023-02-22
+*
+* */
+
+#include <ls-std/io/section-pair/validator/SectionPairFileExtensionValidator.hpp>
+
+ls::std::io::SectionPairFileExtensionValidator::SectionPairFileExtensionValidator(::std::string _fileName) : ls::std::core::Class("SectionPairFileExtensionValidator"), fileName(::std::move(_fileName))
+{}
+
+ls::std::io::SectionPairFileExtensionValidator::~SectionPairFileExtensionValidator() = default;
+
+bool ls::std::io::SectionPairFileExtensionValidator::isValid()
+{
+  ::std::string textFileExtension = ".txt";
+  ::std::string sectionPairFileExtension = ".sp";
+  bool endsWithTextFileExtension = this->fileName.rfind(textFileExtension) == (this->fileName.size() - textFileExtension.size());
+  bool endsWithSectionPairFileExtension = this->fileName.rfind(sectionPairFileExtension) == (this->fileName.size() - sectionPairFileExtension.size());
+
+  return endsWithTextFileExtension || endsWithSectionPairFileExtension;
+}

+ 32 - 0
source/ls-std/io/section-pair/validator/SectionPairIdentifierValidator.cpp

@@ -0,0 +1,32 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-09
+* Changed:         2023-02-21
+*
+* */
+
+#include <ls-std/io/section-pair/validator/SectionPairIdentifierValidator.hpp>
+#include <regex>
+
+ls::std::io::SectionPairIdentifierValidator::SectionPairIdentifierValidator(ls::std::io::section_pair_identifier _identifier) : ls::std::core::Class("SectionPairIdentifierValidator"), identifier(::std::move(_identifier))
+{}
+
+ls::std::io::SectionPairIdentifierValidator::~SectionPairIdentifierValidator() = default;
+
+::std::string ls::std::io::SectionPairIdentifierValidator::getValidationRegex()
+{
+  return ls::std::io::SectionPairIdentifierValidator::_getValidationRegex();
+}
+
+bool ls::std::io::SectionPairIdentifierValidator::isValid()
+{
+  static ::std::regex identifierRegex("^" + ls::std::io::SectionPairIdentifierValidator::_getValidationRegex());
+  return ::std::regex_match(this->identifier, identifierRegex);
+}
+
+::std::string ls::std::io::SectionPairIdentifierValidator::_getValidationRegex()
+{
+  return R"([a-z]([a-z0-9-]){1,31})";
+}

+ 41 - 0
source/ls-std/io/section-pair/validator/SectionPairRowListValueValidator.cpp

@@ -0,0 +1,41 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-19
+* Changed:         2023-02-20
+*
+* */
+
+#include <ls-std/io/section-pair/validator/SectionPairIdentifierValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairRowListValueValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairValueValidator.hpp>
+#include <regex>
+
+ls::std::io::SectionPairRowListValueValidator::SectionPairRowListValueValidator(::std::string _listValueRow) : ls::std::core::Class("SectionPairRowListValueValidator"), listValueRow(::std::move(_listValueRow))
+{}
+
+ls::std::io::SectionPairRowListValueValidator::~SectionPairRowListValueValidator() = default;
+
+::std::string ls::std::io::SectionPairRowListValueValidator::getValidationRegex()
+{
+  return ls::std::io::SectionPairRowListValueValidator::_getValidationRegex();
+}
+
+bool ls::std::io::SectionPairRowListValueValidator::isValid()
+{
+  ::std::string validationRegex = ls::std::io::SectionPairRowListValueValidator::_getValidationRegex();
+  static ::std::regex listValueRowRegex = ::std::regex{"^" + validationRegex};
+
+  return ::std::regex_match(this->listValueRow, listValueRowRegex);
+}
+
+::std::string ls::std::io::SectionPairRowListValueValidator::_getValidationRegex()
+{
+  ::std::string identifierRegex = ls::std::io::SectionPairIdentifierValidator::getValidationRegex();
+  ::std::string valueRegex = ls::std::io::SectionPairValueValidator::getValidationRegex();
+  ::std::string lineBreak = R"(((\n{1})|(\r{1}\n{1})))";
+  ::std::string firstLine = R"(((()" + identifierRegex + R"():{1}))" + lineBreak + R"())";
+
+  return R"((()" + firstLine + R"(( {2})" + valueRegex + R"()" + lineBreak + R"()){1}(( {2})" + valueRegex + R"()" + lineBreak + R"()*)))";
+}

+ 39 - 0
source/ls-std/io/section-pair/validator/SectionPairRowSingleValueValidator.cpp

@@ -0,0 +1,39 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-19
+* Changed:         2023-02-20
+*
+* */
+
+#include <ls-std/io/section-pair/validator/SectionPairIdentifierValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairRowSingleValueValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairValueValidator.hpp>
+#include <regex>
+
+ls::std::io::SectionPairRowSingleValueValidator::SectionPairRowSingleValueValidator(::std::string _singleValueRow) : ls::std::core::Class("SectionPairRowSingleValueValidator"), singleValueRow(::std::move(_singleValueRow))
+{}
+
+ls::std::io::SectionPairRowSingleValueValidator::~SectionPairRowSingleValueValidator() = default;
+
+::std::string ls::std::io::SectionPairRowSingleValueValidator::getValidationRegex()
+{
+  return ls::std::io::SectionPairRowSingleValueValidator::_getValidationRegex();
+}
+
+bool ls::std::io::SectionPairRowSingleValueValidator::isValid()
+{
+  ::std::string validationRegex = ls::std::io::SectionPairRowSingleValueValidator::_getValidationRegex();
+  static ::std::regex singleValueRowRegex = ::std::regex{"^" + validationRegex};
+
+  return ::std::regex_match(this->singleValueRow, singleValueRowRegex);
+}
+
+::std::string ls::std::io::SectionPairRowSingleValueValidator::_getValidationRegex()
+{
+  ::std::string identifierRegex = ls::std::io::SectionPairIdentifierValidator::getValidationRegex();
+  ::std::string valueRegex = ls::std::io::SectionPairValueValidator::getValidationRegex();
+
+  return R"(()" + identifierRegex + R"()={1}()" + valueRegex + R"(){1}($|\n{1}|\r{1}\n{1}))";
+}

+ 39 - 0
source/ls-std/io/section-pair/validator/SectionPairRowValidator.cpp

@@ -0,0 +1,39 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-20
+* Changed:         2023-02-20
+*
+* */
+
+#include <ls-std/io/section-pair/validator/SectionPairRowListValueValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairRowSingleValueValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairRowValidator.hpp>
+#include <regex>
+
+ls::std::io::SectionPairRowValidator::SectionPairRowValidator(::std::string _row) : ls::std::core::Class("SectionPairRowValidator"), row(::std::move(_row))
+{}
+
+ls::std::io::SectionPairRowValidator::~SectionPairRowValidator() = default;
+
+::std::string ls::std::io::SectionPairRowValidator::getValidationRegex()
+{
+  return ls::std::io::SectionPairRowValidator::_getValidationRegex();
+}
+
+bool ls::std::io::SectionPairRowValidator::isValid()
+{
+  ::std::string validationRegex = ls::std::io::SectionPairRowValidator::_getValidationRegex();
+  static ::std::regex sectionPairRowRegex = ::std::regex{R"(^()" + validationRegex + R"())"};
+
+  return ::std::regex_match(this->row, sectionPairRowRegex);
+}
+
+::std::string ls::std::io::SectionPairRowValidator::_getValidationRegex()
+{
+  ::std::string listValueRowRegex = ls::std::io::SectionPairRowListValueValidator::getValidationRegex();
+  ::std::string singleValueRowRegex = ls::std::io::SectionPairRowSingleValueValidator::getValidationRegex();
+
+  return R"(()" + singleValueRowRegex + R"()|()" + listValueRowRegex + R"())";
+}

+ 44 - 0
source/ls-std/io/section-pair/validator/SectionPairSectionValidator.cpp

@@ -0,0 +1,44 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-20
+* Changed:         2023-02-21
+*
+* */
+
+#include <ls-std/io/section-pair/validator/SectionPairIdentifierValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairRowValidator.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairSectionValidator.hpp>
+#include <regex>
+#include <string>
+
+ls::std::io::SectionPairSectionValidator::SectionPairSectionValidator(::std::string _section) : ls::std::core::Class("SectionPairSectionValidator"), section(::std::move(_section))
+{}
+
+ls::std::io::SectionPairSectionValidator::~SectionPairSectionValidator() = default;
+
+::std::string ls::std::io::SectionPairSectionValidator::getValidationRegex()
+{
+  return ls::std::io::SectionPairSectionValidator::_getValidationRegex();
+}
+
+bool ls::std::io::SectionPairSectionValidator::isValid()
+{
+  ::std::string validationRegex = ls::std::io::SectionPairSectionValidator::_getValidationRegex();
+  static ::std::regex sectionRegex = ::std::regex{"^" + validationRegex};
+
+  return ::std::regex_match(this->section, sectionRegex);
+}
+
+::std::string ls::std::io::SectionPairSectionValidator::_getValidationRegex()
+{
+  ::std::string newLine = R"(((\n)|(\r\n)))";
+  ::std::string identifier = ls::std::io::SectionPairIdentifierValidator::getValidationRegex();
+  ::std::string sectionHeader = newLine + R"(\[{1}()" + identifier + R"()\]{1}()" + newLine + R"({2}))";
+  ::std::string row = ls::std::io::SectionPairRowValidator::getValidationRegex();
+  ::std::string atLeastOneRow = R"((()" + row + R"(){1}))";
+  ::std::string optionalRows = R"((()" + row + R"()*))";
+
+  return sectionHeader + atLeastOneRow + optionalRows;
+}

+ 37 - 0
source/ls-std/io/section-pair/validator/SectionPairValueValidator.cpp

@@ -0,0 +1,37 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-09
+* Changed:         2023-02-20
+*
+* */
+
+#include <ls-std/io/NewLine.hpp>
+#include <ls-std/io/section-pair/validator/SectionPairValueValidator.hpp>
+#include <regex>
+
+ls::std::io::SectionPairValueValidator::SectionPairValueValidator(ls::std::io::section_pair_row_value _value) : ls::std::core::Class("SectionPairValueValidator"), value(::std::move(_value))
+{}
+
+ls::std::io::SectionPairValueValidator::~SectionPairValueValidator() = default;
+
+::std::string ls::std::io::SectionPairValueValidator::getValidationRegex()
+{
+  return ls::std::io::SectionPairValueValidator::_getValidationRegex();
+}
+
+bool ls::std::io::SectionPairValueValidator::isValid()
+{
+  ::std::string validationRegex = ls::std::io::SectionPairValueValidator::_getValidationRegex();
+  ::std::string concatenation = "(^" + validationRegex + ")|(^" + validationRegex + R"(\n{1})|(^)" + validationRegex + R"(\r{1}\n{1}))";
+  static ::std::regex valueRegex{concatenation};
+
+  return ::std::regex_match(this->value, valueRegex);
+}
+
+::std::string ls::std::io::SectionPairValueValidator::_getValidationRegex()
+{
+  ::std::string value = R"([a-zA-Z0-9\-_#!?\[\]\{\}\(\)\$ۤ<>+:;., \*\/"]{1,32})";
+  return value;
+}

+ 51 - 0
test/cases/core/ConditionalFunctionExecutorTest.cpp

@@ -0,0 +1,51 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-13
+* Changed:         2023-02-13
+*
+* */
+
+#include <gtest/gtest.h>
+#include <ls-std-core-test.hpp>
+#include <ls-std/ls-std-core.hpp>
+
+using namespace ls::std::core;
+using namespace test::core;
+using namespace ::std;
+
+namespace
+{
+  class ConditionalFunctionExecutorTest : public ::testing::Test
+  {
+    protected:
+
+      ConditionalFunctionExecutorTest() = default;
+      ~ConditionalFunctionExecutorTest() override = default;
+
+      void SetUp() override
+      {}
+
+      void TearDown() override
+      {}
+  };
+
+  TEST_F(ConditionalFunctionExecutorTest, execute)
+  {
+    shared_ptr<MathOddValidator> validator = make_shared<MathOddValidator>();
+    int inputNumber = 3;
+    ConditionalFunctionExecutor{true}.execute([validator, inputNumber] { validator->validate(inputNumber); });
+
+    ASSERT_TRUE(validator->isOdd());
+  }
+
+  TEST_F(ConditionalFunctionExecutorTest, execute_no_execution)
+  {
+    shared_ptr<MathOddValidator> validator = make_shared<MathOddValidator>();
+    int inputNumber = 3;
+    ConditionalFunctionExecutor{false}.execute([validator, inputNumber] { validator->validate(inputNumber); });
+
+    ASSERT_FALSE(validator->isOdd());
+  }
+}

+ 68 - 0
test/cases/core/evaluator/IndexOutOfBoundsEvaluatorTest.cpp

@@ -0,0 +1,68 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-10
+*
+* */
+
+#include <gtest/gtest.h>
+#include <ls-std/ls-std-core.hpp>
+#include <string>
+
+using namespace ls::std::core;
+using namespace ::std;
+
+namespace
+{
+  class IndexOutOfBoundsEvaluatorTest : public ::testing::Test
+  {
+    protected:
+
+      IndexOutOfBoundsEvaluatorTest() = default;
+      ~IndexOutOfBoundsEvaluatorTest() override = default;
+
+      void SetUp() override
+      {}
+
+      void TearDown() override
+      {}
+  };
+
+  TEST_F(IndexOutOfBoundsEvaluatorTest, evaluate)
+  {
+    EXPECT_THROW(
+        {
+          try
+          {
+            IndexOutOfBoundsEvaluator(3, 2).evaluate();
+          }
+          catch (const IndexOutOfBoundsException &_exception)
+          {
+            string message = _exception.what();
+            ASSERT_STREQ("IndexOutOfBoundsException thrown - provided index is out of bounds!", message.c_str());
+            throw;
+          }
+        },
+        IndexOutOfBoundsException);
+  }
+
+  TEST_F(IndexOutOfBoundsEvaluatorTest, evaluate_dedicated_message)
+  {
+    EXPECT_THROW(
+        {
+          try
+          {
+            IndexOutOfBoundsEvaluator(3, 2, "index 3 is not in range of the containers size, which is 2!").evaluate();
+          }
+          catch (const IndexOutOfBoundsException &_exception)
+          {
+            string message = _exception.what();
+            ASSERT_STREQ("IndexOutOfBoundsException thrown - index 3 is not in range of the containers size, which is 2!", message.c_str());
+            throw;
+          }
+        },
+        IndexOutOfBoundsException);
+  }
+}

+ 67 - 0
test/cases/core/exception/IndexOutOfBoundsExceptionTest.cpp

@@ -0,0 +1,67 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-10
+*
+* */
+
+#include <gtest/gtest.h>
+#include <ls-std/ls-std-core.hpp>
+#include <string>
+
+using namespace ls::std::core;
+
+namespace
+{
+  class IndexOutOfBoundsExceptionTest : public ::testing::Test
+  {
+    protected:
+
+      IndexOutOfBoundsExceptionTest() = default;
+      ~IndexOutOfBoundsExceptionTest() override = default;
+
+      void SetUp() override
+      {}
+
+      void TearDown() override
+      {}
+  };
+
+  TEST_F(IndexOutOfBoundsExceptionTest, constructor)
+  {
+    EXPECT_THROW(
+        {
+          try
+          {
+            throw IndexOutOfBoundsException{};
+          }
+          catch (const IndexOutOfBoundsException &_exception)
+          {
+            ::std::string message = _exception.what();
+            EXPECT_STREQ("IndexOutOfBoundsException thrown - provided index is out of bounds!", message.c_str());
+            throw;
+          }
+        },
+        IndexOutOfBoundsException);
+  }
+
+  TEST_F(IndexOutOfBoundsExceptionTest, constructor_dedicated_message)
+  {
+    EXPECT_THROW(
+        {
+          try
+          {
+            throw IndexOutOfBoundsException{"index 3 is out of bounds!"};
+          }
+          catch (const IndexOutOfBoundsException &_exception)
+          {
+            ::std::string message = _exception.what();
+            EXPECT_STREQ("IndexOutOfBoundsException thrown - index 3 is out of bounds!", message.c_str());
+            throw;
+          }
+        },
+        IndexOutOfBoundsException);
+  }
+}

+ 67 - 0
test/cases/core/exception/WrongCallExceptionTest.cpp

@@ -0,0 +1,67 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-10
+* Changed:         2023-02-10
+*
+* */
+
+#include <gtest/gtest.h>
+#include <ls-std/ls-std-core.hpp>
+#include <string>
+
+using namespace ls::std::core;
+
+namespace
+{
+ class WrongCallExceptionTest : public ::testing::Test
+ {
+   protected:
+
+     WrongCallExceptionTest() = default;
+     ~WrongCallExceptionTest() override = default;
+
+     void SetUp() override
+     {}
+
+     void TearDown() override
+     {}
+ };
+
+ TEST_F(WrongCallExceptionTest, constructor)
+ {
+   EXPECT_THROW(
+       {
+         try
+         {
+           throw WrongCallException{};
+         }
+         catch (const WrongCallException &_exception)
+         {
+           ::std::string message = _exception.what();
+           EXPECT_STREQ("WrongCallException thrown - this function / method call is invalid!", message.c_str());
+           throw;
+         }
+       },
+       WrongCallException);
+ }
+
+ TEST_F(WrongCallExceptionTest, constructor_dedicated_message)
+ {
+   EXPECT_THROW(
+       {
+         try
+         {
+           throw WrongCallException{"method \"getValue()\" was called, although this is forbidden!"};
+         }
+         catch (const WrongCallException &_exception)
+         {
+           ::std::string message = _exception.what();
+           EXPECT_STREQ("WrongCallException thrown - method \"getValue()\" was called, although this is forbidden!", message.c_str());
+           throw;
+         }
+       },
+       WrongCallException);
+ }
+}

+ 57 - 0
test/cases/io/evaluator/FileExistenceEvaluatorTest.cpp

@@ -0,0 +1,57 @@
+/*
+* Author:          Patrick-Christopher Mattulat
+* Company:         Lynar Studios
+* E-Mail:          webmaster@lynarstudios.com
+* Created:         2023-02-21
+* Changed:         2023-02-21
+*
+* */
+
+#include <gtest/gtest.h>
+#include <ls-std/ls-std-core.hpp>
+#include <ls-std/ls-std-io.hpp>
+#include <string>
+
+using namespace ls::std::core;
+using namespace ls::std::io;
+using namespace ::std;
+
+namespace
+{
+  class FileExistenceEvaluatorTest : public ::testing::TestWithParam<string>
+  {
+    protected:
+
+      FileExistenceEvaluatorTest() = default;
+      ~FileExistenceEvaluatorTest() override = default;
+
+      void SetUp() override
+      {}
+
+      void TearDown() override
+      {}
+  };
+
+  TEST_P(FileExistenceEvaluatorTest, evaluate)
+  {
+    EXPECT_THROW(
+        {
+          try
+          {
+            FileExistenceEvaluator{GetParam()}.evaluate();
+          }
+          catch (const FileNotFoundException &_exception)
+          {
+            string actual = _exception.what();
+            string expected = "FileNotFoundException thrown - \"" + GetParam() + "\" does not exist!";
+            ;
+
+            ASSERT_STREQ(expected.c_str(), actual.c_str());
+            throw;
+          }
+        },
+        FileNotFoundException);
+  }
+
+  INSTANTIATE_TEST_SUITE_P(FileExistenceEvaluatorTest, FileExistenceEvaluatorTest, ::testing::Values("var/log/log.txt", ".test"));
+}

+ 0 - 106
test/cases/io/kv/KvDocumentTest.cpp

@@ -1,106 +0,0 @@
-/*
- * Author:          Patrick-Christopher Mattulat
- * Company:         Lynar Studios
- * E-Mail:          webmaster@lynarstudios.com
- * Created:         2020-12-25
- * Changed:         2023-02-03
- *
- * */
-
-#include <gtest/gtest.h>
-#include <ls-std/ls-std-io.hpp>
-
-using namespace ls::std::io;
-
-namespace
-{
-  class KvDocumentTest : public ::testing::Test
-  {
-    protected:
-
-      KvDocumentTest() = default;
-      ~KvDocumentTest() override = default;
-
-      void SetUp() override
-      {}
-
-      void TearDown() override
-      {}
-  };
-
-  TEST_F(KvDocumentTest, addPair)
-  {
-    KvDocument document{};
-    KvPair pair{"port", "13088"};
-
-    ASSERT_TRUE(document.addPair(pair));
-    ASSERT_EQ(1, document.getPairs().size());
-  }
-
-  TEST_F(KvDocumentTest, addPair_retry_to_add_pair)
-  {
-    KvDocument document{};
-    KvPair pair{"port", "13088"};
-
-    ASSERT_TRUE(document.addPair(pair));
-    ASSERT_FALSE(document.addPair(pair));
-  }
-
-  TEST_F(KvDocumentTest, clear)
-  {
-    // preparation
-
-    KvDocument document{};
-    KvPair pair{"port", "13088"};
-    document.addPair(pair);
-
-    // check
-
-    document.clear();
-    ASSERT_TRUE(document.getPairs().empty());
-    ASSERT_EQ(0, document.getPairs().size());
-  }
-
-  TEST_F(KvDocumentTest, getPairs)
-  {
-    KvDocument document{};
-    ASSERT_TRUE(document.getPairs().empty());
-  }
-
-  TEST_F(KvDocumentTest, hasPair)
-  {
-    KvDocument document{};
-    document.addPair(KvPair{"port", "80"});
-
-    ASSERT_TRUE(document.hasPair("port"));
-  }
-
-  TEST_F(KvDocumentTest, hasPair_no_pairs_available)
-  {
-    KvDocument document{};
-    ASSERT_FALSE(document.hasPair("port"));
-  }
-
-  TEST_F(KvDocumentTest, removePair)
-  {
-    // preparation
-
-    KvDocument document{};
-    document.addPair(KvPair{"port", "80"});
-    document.addPair(KvPair{"host", "localhost"});
-    document.addPair(KvPair{"protocol", "TCP"});
-
-    // remove pair and check
-
-    ASSERT_TRUE(document.removePair("protocol"));
-    ASSERT_EQ(2, document.getPairs().size());
-    ASSERT_TRUE(document.hasPair("port"));
-    ASSERT_TRUE(document.hasPair("host"));
-  }
-
-  TEST_F(KvDocumentTest, removePair_no_pair_available)
-  {
-    KvDocument document{};
-    ASSERT_FALSE(document.removePair("port"));
-  }
-}

+ 0 - 152
test/cases/io/kv/KvFileReaderTest.cpp

@@ -1,152 +0,0 @@
-/*
- * Author:          Patrick-Christopher Mattulat
- * Company:         Lynar Studios
- * E-Mail:          webmaster@lynarstudios.com
- * Created:         2020-12-25
- * Changed:         2023-02-06
- *
- * */
-
-#include <classes/TestHelper.hpp>
-#include <gtest/gtest.h>
-#include <ls-std/ls-std-core.hpp>
-#include <ls-std/ls-std-io.hpp>
-
-using namespace ls::std::core;
-using namespace ls::std::io;
-using namespace ::std;
-using namespace ls::std::test;
-
-namespace
-{
-  class KvFileReaderTest : public ::testing::Test
-  {
-    protected:
-
-      KvFileReaderTest() = default;
-      ~KvFileReaderTest() override = default;
-
-      void SetUp() override
-      {}
-
-      void TearDown() override
-      {}
-
-      static shared_ptr<KvFileReader> createTestKvFileReader()
-      {
-        string kvPath = TestHelper::getResourcesFolderLocation() + "server-settings.kv";
-        shared_ptr<KvDocument> document = make_shared<KvDocument>();
-
-        return make_shared<KvFileReader>(document, kvPath);
-      }
-  };
-
-  TEST_F(KvFileReaderTest, constructor_no_document_reference)
-  {
-    EXPECT_THROW(
-        {
-          try
-          {
-            string kvPath = TestHelper::getResourcesFolderLocation() + "server-settings.kv";
-            KvFileReader reader = KvFileReader(nullptr, kvPath);
-          }
-          catch (const IllegalArgumentException &_exception)
-          {
-            throw;
-          }
-        },
-        IllegalArgumentException);
-  }
-
-  TEST_F(KvFileReaderTest, constructor_invalid_file_path)
-  {
-    EXPECT_THROW(
-        {
-          try
-          {
-            KvFileReader reader = KvFileReader(make_shared<KvDocument>(), "invalid-path");
-          }
-          catch (const IllegalArgumentException &_exception)
-          {
-            throw;
-          }
-        },
-        IllegalArgumentException);
-  }
-
-  TEST_F(KvFileReaderTest, getDocument)
-  {
-    const shared_ptr<KvFileReader> &reader = createTestKvFileReader();
-    ASSERT_TRUE(reader->getDocument() != nullptr);
-  }
-
-  TEST_F(KvFileReaderTest, read)
-  {
-    // preparation
-
-    const shared_ptr<KvFileReader> &reader = createTestKvFileReader();
-
-    // read file and check
-
-    reader->read();
-    const shared_ptr<KvDocument> &document = reader->getDocument();
-
-    ASSERT_EQ(3, document->getPairs().size());
-    ASSERT_TRUE(document->hasPair("port"));
-    ASSERT_TRUE(document->hasPair("host"));
-    ASSERT_TRUE(document->hasPair("service-name"));
-
-    ASSERT_STREQ("8080", document->getPairs().at("port").getValue().c_str());
-    ASSERT_STREQ("localhost", document->getPairs().at("host").getValue().c_str());
-    ASSERT_STREQ("deamon", document->getPairs().at("service-name").getValue().c_str());
-  }
-
-  TEST_F(KvFileReaderTest, setFile_no_existing_file)
-  {
-    const shared_ptr<KvFileReader> &reader = createTestKvFileReader();
-
-    EXPECT_THROW(
-        {
-          try
-          {
-            reader->setFile(File{"invalid-path"});
-          }
-          catch (const IllegalArgumentException &_exception)
-          {
-            throw;
-          }
-        },
-        IllegalArgumentException);
-  }
-
-  TEST_F(KvFileReaderTest, setDocument)
-  {
-    // preparation
-
-    const shared_ptr<KvFileReader> &reader = createTestKvFileReader();
-
-    // set new document and check
-
-    shared_ptr<KvDocument> newDocument = make_shared<KvDocument>();
-    reader->setDocument(newDocument);
-    ASSERT_TRUE(reader->getDocument() == newDocument);
-  }
-
-  TEST_F(KvFileReaderTest, setDocument_no_reference)
-  {
-    const shared_ptr<KvFileReader> &reader = createTestKvFileReader();
-
-    EXPECT_THROW(
-        {
-          try
-          {
-            reader->setDocument(nullptr);
-          }
-          catch (const IllegalArgumentException &_exception)
-          {
-            throw;
-          }
-        },
-        IllegalArgumentException);
-  }
-}

部分文件因为文件数量过多而无法显示