31 #ifndef MODULE_CONFIG_HPP_ 32 #define MODULE_CONFIG_HPP_ 35 #define MODULE_CONFIG_DEBUG 37 #include "../Helper/Json.hpp" 38 #include "../Helper/Strings.hpp" 39 #include "../Main/Exception.hpp" 40 #include "../Struct/ConfigItem.hpp" 42 #include "../_extern/rapidjson/include/rapidjson/document.h" 44 #ifdef MODULE_CONFIG_DEBUG 55 #include <string_view> 65 using std::string_view_literals::operator
""sv;
128 using LogQueue = std::queue<std::string>&;
129 using LogPtr = std::queue<std::string> *;
145 void loadConfig(
const std::string& configJson, LogQueue& warningsTo);
213 void option(
const std::string& name,
bool& target);
214 void option(
const std::string& name, std::vector<bool>& target);
217 void option(
const std::string& name, std::int16_t& target);
218 void option(
const std::string& name, std::vector<std::int16_t>& target);
219 void option(
const std::string& name, std::int32_t& target);
220 void option(
const std::string& name, std::vector<std::int32_t>& target);
221 void option(
const std::string& name, std::int64_t& target);
222 void option(
const std::string& name, std::vector<std::int64_t>& target);
223 void option(
const std::string& name, std::uint8_t& target);
224 void option(
const std::string& name, std::vector<std::uint8_t>& target);
225 void option(
const std::string& name, std::uint16_t& target);
226 void option(
const std::string& name, std::vector<std::uint16_t>& target);
227 void option(
const std::string& name, std::uint32_t& target);
228 void option(
const std::string& name, std::vector<std::uint32_t>& target);
229 void option(
const std::string& name, std::uint64_t& target);
230 void option(
const std::string& name, std::vector<std::uint64_t>& target);
231 void option(
const std::string& name,
float& target);
232 void option(
const std::string& name, std::vector<float>& target);
268 virtual void reset() = 0;
275 bool setCategory{
false};
276 bool foundCategory{
false};
277 bool currentCategory{
false};
278 bool finished{
false};
279 LogPtr logPtr{
nullptr};
281 #ifdef MODULE_CONFIG_DEBUG 283 std::string categoryString;
284 std::vector<std::string> list;
288 void logQueue(
const std::string& entry);
291 static void makeSubUrl(std::string& s);
292 static void makeUrl(std::string& s);
318 const std::string& configJson,
319 std::queue<std::string>& warningsTo
322 this->logPtr = &warningsTo;
325 rapidjson::Document json;
332 "Module::Config::loadConfig():" 333 " Could not parse configuration JSON - " 334 + std::string(e.
view())
338 if(!json.IsArray()) {
340 "Module::Config::loadConfig():" 341 " Invalid configuration JSON (is no array)." 346 for(
const auto& entry : json.GetArray()) {
348 if(!entry.IsObject()) {
350 "Configuration entry that is no object ignored." 360 for(
const auto& member : entry.GetObject()) {
362 if(member.name.IsString()) {
363 const std::string memberName(
364 member.name.GetString(),
365 member.name.GetStringLength()
368 if(memberName ==
"cat") {
370 if(member.value.IsString()) {
371 this->currentItem.
category = std::string(
372 member.value.GetString(),
373 member.value.GetStringLength()
378 "Configuration entry with invalid category name ignored." 386 else if(memberName ==
"name") {
388 if(member.value.IsString()) {
389 this->currentItem.
name = std::string(
390 member.value.GetString(),
391 member.value.GetStringLength()
396 "Configuration entry with invalid option name ignored." 405 else if(memberName ==
"value") {
407 this->currentItem.
value = &(member.value);
413 if(memberName.empty()) {
415 "Unnamed configuration entry member ignored." 420 "Unknown configuration entry member '" 432 "Configuration entry member with invalid name ignored." 443 if(this->currentItem.
category.empty()) {
444 if(this->currentItem.
name !=
"_algo") {
445 this->logQueue(
"Configuration item without category ignored");
451 if(this->currentItem.
name.empty()) {
452 this->logQueue(
"Configuration item without name ignored.");
458 this->logQueue(
"Configuration entry without value ignored.");
466 #ifdef MODULE_CONFIG_DEBUG 469 std::sort(this->list.begin(), this->list.end());
472 std::adjacent_find(this->list.cbegin(), this->list.cend())
475 if(it != this->list.cend()) {
476 throw Exception(
"Duplicate option '" + *it +
"'");
486 if(!this->finished) {
487 if(this->foundCategory) {
489 "Unknown configuration entry '" 490 + this->currentItem.
str()
496 "Configuration entry with unknown category '" 505 this->foundCategory =
false;
506 this->currentCategory =
false;
507 this->finished =
false;
514 this->logPtr =
nullptr;
528 #ifdef MODULE_CONFIG_DEBUG 540 this->setCategory =
true;
543 if(this->currentItem.
category == category) {
544 this->foundCategory =
true;
545 this->currentCategory =
true;
548 this->currentCategory =
false;
574 #ifdef MODULE_CONFIG_DEBUG 576 this->list.emplace_back(this->categoryString +
"." + name);
581 if(!(this->setCategory)) {
583 "Module::Config::option():" 584 " No category has been set" 588 if(this->finished || !(this->currentCategory)) {
593 if(this->currentItem.
name != name) {
598 if(this->currentItem.
value->IsBool()) {
599 target = this->currentItem.
value->GetBool();
601 else if(this->currentItem.
value->IsNull()) {
607 + this->currentItem.
str()
608 +
"' ignored because of wrong type (not bool)." 613 this->finished =
true;
638 #ifdef MODULE_CONFIG_DEBUG 640 this->list.emplace_back(this->categoryString +
"." + name);
645 if(!(this->setCategory)) {
647 "Module::Config::option():" 648 " No category has been set" 652 if(this->finished || !(this->currentCategory)) {
657 if(this->currentItem.
name != name) {
662 if(this->currentItem.
value->IsArray()) {
666 target.reserve(this->currentItem.
value->Size());
669 for(
const auto& item : this->currentItem.
value->GetArray()) {
671 target.push_back(item.GetBool());
674 target.push_back(
false);
679 + this->currentItem.
str()
680 +
"' ignored because of wrong type (not bool)." 689 + this->currentItem.
str()
690 +
"' ignored because of wrong type (not array)." 695 this->finished =
true;
722 #ifdef MODULE_CONFIG_DEBUG 724 this->list.emplace_back(this->categoryString +
"." + name);
729 if(!(this->setCategory)) {
731 "Module::Config::option():" 732 " No category has been set" 736 if(this->finished || !(this->currentCategory)) {
741 if(this->currentItem.
name != name) {
748 if(this->currentItem.
value->IsInt()) {
749 const auto value{this->currentItem.
value->GetInt()};
751 if(value > std::numeric_limits<char>::max()) {
754 + this->currentItem.
str()
755 +
"' ignored because the number is too large." 762 else if(this->currentItem.
value->IsNull()) {
768 + this->currentItem.
str()
769 +
"' ignored because of wrong type (not int)." 777 if(this->currentItem.
value->IsString()) {
780 this->currentItem.
value->GetString(),
781 this->currentItem.
value->GetStringLength()
788 + this->currentItem.
str()
789 +
"' ignored because of wrong type (not string)." 796 throw Exception(
"Config::option(): Invalid string parsing option");
800 this->finished =
true;
827 #ifdef MODULE_CONFIG_DEBUG 829 this->list.emplace_back(this->categoryString +
"." + name);
834 if(!(this->setCategory)) {
836 "Module::Config::option():" 837 " No category has been set" 841 if(this->finished || !(this->currentCategory)) {
846 if(this->currentItem.
name != name) {
851 if(this->currentItem.
value->IsArray()) {
855 target.reserve(this->currentItem.
value->Size());
858 for(
const auto& item : this->currentItem.
value->GetArray()) {
863 const auto value{item.GetInt()};
865 if(value > std::numeric_limits<char>::max()) {
868 + this->currentItem.
str()
869 +
"' ignored because the number is too large." 873 target.push_back(value);
882 + this->currentItem.
str()
883 +
"' ignored because of wrong type (not int)." 892 if(item.IsString()) {
897 item.GetStringLength()
903 if(::isascii(target.back()) == 0) {
905 "First character of string in '" 906 + this->currentItem.
str()
907 +
"' is no ASCII character: " 910 item.GetStringLength()
921 + this->currentItem.
str()
922 +
"' ignored because of wrong type (not string)." 930 throw Exception(
"Config::option(): Invalid string parsing option");
937 + this->currentItem.
str()
938 +
"' ignored because of wrong type (not array)." 943 this->finished =
true;
968 #ifdef MODULE_CONFIG_DEBUG 970 this->list.emplace_back(this->categoryString +
"." + name);
975 if(!(this->setCategory)) {
977 "Module::Config::option():" 978 " No category has been set" 982 if(this->finished || !(this->currentCategory)) {
987 if(this->currentItem.
name != name) {
992 if(this->currentItem.
value->IsInt()) {
993 const auto value{this->currentItem.
value->GetInt()};
995 if(value > std::numeric_limits<std::int16_t>::max()) {
998 + this->currentItem.
str()
999 +
"' ignored because the number is too large." 1006 else if(this->currentItem.
value->IsNull()) {
1012 + this->currentItem.
str()
1013 +
"' ignored because of wrong type (not integer)." 1018 this->finished =
true;
1042 inline void Config::option(
const std::string& name, std::vector<std::int16_t>& target) {
1043 #ifdef MODULE_CONFIG_DEBUG 1045 this->list.emplace_back(this->categoryString +
"." + name);
1050 if(!(this->setCategory)) {
1052 "Module::Config::option():" 1053 " No category has been set" 1057 if(this->finished || !(this->currentCategory)) {
1062 if(this->currentItem.
name != name) {
1067 if(this->currentItem.
value->IsArray()) {
1071 target.reserve(this->currentItem.
value->Size());
1074 for(
const auto& item : this->currentItem.
value->GetArray()) {
1076 const auto value{item.GetInt()};
1078 if(value > std::numeric_limits<std::int16_t>::max()) {
1081 + this->currentItem.
str()
1082 +
"' ignored because the number is too large." 1086 target.push_back(value);
1090 target.push_back(0);
1092 if(!item.IsNull()) {
1095 + this->currentItem.
str()
1096 +
"' ignored because of wrong type (not integer)." 1105 + this->currentItem.
str()
1106 +
"' ignored because of wrong type (not array)." 1111 this->finished =
true;
1136 #ifdef MODULE_CONFIG_DEBUG 1138 this->list.emplace_back(this->categoryString +
"." + name);
1143 if(!(this->setCategory)) {
1145 "Module::Config::option():" 1146 " No category has been set" 1150 if(this->finished || !(this->currentCategory)) {
1155 if(this->currentItem.
name != name) {
1160 if(this->currentItem.
value->IsInt()) {
1161 target = this->currentItem.
value->GetInt();
1163 else if(this->currentItem.
value->IsNull()) {
1169 + this->currentItem.
str()
1170 +
"' ignored because of wrong type (not integer)." 1175 this->finished =
true;
1199 inline void Config::option(
const std::string& name, std::vector<std::int32_t>& target) {
1200 #ifdef MODULE_CONFIG_DEBUG 1202 this->list.emplace_back(this->categoryString +
"." + name);
1207 if(!(this->setCategory)) {
1209 "Module::Config::option():" 1210 " No category has been set" 1214 if(this->finished || !(this->currentCategory)) {
1219 if(this->currentItem.
name != name) {
1224 if(this->currentItem.
value->IsArray()) {
1228 target.reserve(this->currentItem.
value->Size());
1231 for(
const auto& item : this->currentItem.
value->GetArray()) {
1233 target.push_back(item.GetInt());
1236 target.push_back(0);
1238 if(!item.IsNull()) {
1241 + this->currentItem.
str()
1242 +
"' ignored because of wrong type (not integer)." 1251 + this->currentItem.
str()
1252 +
"' ignored because of wrong type (not array)." 1257 this->finished =
true;
1282 #ifdef MODULE_CONFIG_DEBUG 1284 this->list.emplace_back(this->categoryString +
"." + name);
1289 if(!(this->setCategory)) {
1291 "Module::Config::option():" 1292 " No category has been set" 1296 if(this->finished || !(this->currentCategory)) {
1301 if(this->currentItem.
name != name) {
1306 if(this->currentItem.
value->IsInt64()) {
1307 target = this->currentItem.
value->GetInt64();
1309 else if(this->currentItem.
value->IsNull()) {
1315 + this->currentItem.
str()
1316 +
"' ignored because of wrong type (not 64-bit integer)." 1321 this->finished =
true;
1345 inline void Config::option(
const std::string& name, std::vector<std::int64_t>& target) {
1347 if(!(this->setCategory)) {
1349 "Module::Config::option():" 1350 " No category has been set" 1354 if(this->finished || !(this->currentCategory)) {
1359 if(this->currentItem.
name != name) {
1364 if(this->currentItem.
value->IsArray()) {
1368 target.reserve(this->currentItem.
value->Size());
1371 for(
const auto& item : this->currentItem.
value->GetArray()) {
1372 if(item.IsInt64()) {
1373 target.push_back(item.GetInt64());
1376 target.push_back(0);
1378 if(!item.IsNull()) {
1381 + this->currentItem.
str()
1382 +
"' ignored because of wrong type (not 64-bit integer)." 1391 + this->currentItem.
str()
1392 +
"' ignored because of wrong type (not array)." 1397 this->finished =
true;
1422 #ifdef MODULE_CONFIG_DEBUG 1424 this->list.emplace_back(this->categoryString +
"." + name);
1429 if(!(this->setCategory)) {
1431 "Module::Config::option():" 1432 " No category has been set" 1436 if(this->finished || !(this->currentCategory)) {
1441 if(this->currentItem.
name != name) {
1446 if(this->currentItem.
value->IsUint()) {
1447 const auto value{this->currentItem.
value->GetUint()};
1449 if(value > std::numeric_limits<std::uint8_t>::max()) {
1452 + this->currentItem.
str()
1453 +
"' ignored because the number is too large." 1460 else if(this->currentItem.
value->IsNull()) {
1466 + this->currentItem.
str()
1467 +
"' ignored because of wrong type (not unsigned integer)." 1472 this->finished =
true;
1496 inline void Config::option(
const std::string& name, std::vector<std::uint8_t>& target) {
1497 #ifdef MODULE_CONFIG_DEBUG 1499 this->list.emplace_back(this->categoryString +
"." + name);
1504 if(!(this->setCategory)) {
1506 "Module::Config::option():" 1507 " No category has been set");
1510 if(this->finished || !(this->currentCategory)) {
1515 if(this->currentItem.
name != name) {
1520 if(this->currentItem.
value->IsArray()) {
1524 target.reserve(this->currentItem.
value->Size());
1527 for(
const auto& item : this->currentItem.
value->GetArray()) {
1529 const auto value{item.GetUint()};
1531 if(value > std::numeric_limits<std::uint8_t>::max()) {
1534 + this->currentItem.
str()
1535 +
"' ignored because the number is too large." 1539 target.push_back(value);
1543 target.push_back(0);
1545 if(!item.IsNull()) {
1548 + this->currentItem.
str()
1549 +
"' ignored because of wrong type (not unsigned integer)." 1558 + this->currentItem.
str()
1559 +
"' ignored because of wrong type (not array)." 1564 this->finished =
true;
1589 #ifdef MODULE_CONFIG_DEBUG 1591 this->list.emplace_back(this->categoryString +
"." + name);
1596 if(!(this->setCategory)) {
1598 "Module::Config::option():" 1599 " No category has been set" 1603 if(this->finished || !(this->currentCategory)) {
1608 if(this->currentItem.
name != name) {
1613 if(this->currentItem.
value->IsUint()) {
1614 const auto value{this->currentItem.
value->GetUint()};
1616 if(value > std::numeric_limits<std::uint16_t>::max()) {
1619 + this->currentItem.
str()
1620 +
"' ignored because the number is too large." 1627 else if(this->currentItem.
value->IsNull()) {
1633 + this->currentItem.
str()
1634 +
"' ignored because of wrong type (not unsigned integer)." 1639 this->finished =
true;
1663 inline void Config::option(
const std::string& name, std::vector<std::uint16_t>& target) {
1664 #ifdef MODULE_CONFIG_DEBUG 1666 this->list.emplace_back(this->categoryString +
"." + name);
1671 if(!(this->setCategory)) {
1673 "Module::Config::option():" 1674 " No category has been set" 1678 if(this->finished || !(this->currentCategory)) {
1683 if(this->currentItem.
name != name) {
1688 if(this->currentItem.
value->IsArray()) {
1692 target.reserve(this->currentItem.
value->Size());
1695 for(
const auto& item : this->currentItem.
value->GetArray()) {
1697 const auto value{item.GetUint()};
1699 if(value > std::numeric_limits<std::uint16_t>::max()) {
1702 + this->currentItem.
str()
1703 +
"' ignored because the number is too large." 1707 target.push_back(value);
1711 target.push_back(0);
1713 if(!item.IsNull()) {
1716 + this->currentItem.
str()
1717 +
"' ignored because of wrong type (not unsigned integer)." 1726 + this->currentItem.
str()
1727 +
"' ignored because of wrong type (not array)." 1732 this->finished =
true;
1757 #ifdef MODULE_CONFIG_DEBUG 1759 this->list.emplace_back(this->categoryString +
"." + name);
1764 if(!(this->setCategory)) {
1765 throw Exception(
"Module::Config::option(): No category has been set");
1768 if(this->finished || !(this->currentCategory)) {
1773 if(this->currentItem.
name != name) {
1778 if(this->currentItem.
value->IsUint()) {
1779 target = this->currentItem.
value->GetUint();
1781 else if(this->currentItem.
value->IsNull()) {
1787 + this->currentItem.
str()
1788 +
"' ignored because of wrong type (not unsigned integer)." 1793 this->finished =
true;
1817 inline void Config::option(
const std::string& name, std::vector<std::uint32_t>& target) {
1818 #ifdef MODULE_CONFIG_DEBUG 1820 this->list.emplace_back(this->categoryString +
"." + name);
1825 if(!(this->setCategory)) {
1826 throw Exception(
"Module::Config::option(): No category has been set");
1829 if(this->finished || !(this->currentCategory)) {
1834 if(this->currentItem.
name != name) {
1839 if(this->currentItem.
value->IsArray()) {
1843 target.reserve(this->currentItem.
value->Size());
1846 for(
const auto& item : this->currentItem.
value->GetArray()) {
1848 target.push_back(item.GetUint());
1851 target.push_back(0);
1853 if(!item.IsNull()) {
1856 + this->currentItem.
str()
1857 +
"' ignored because of wrong type (not unsigned integer)." 1866 + this->currentItem.
str()
1867 +
"' ignored because of wrong type (not array)." 1872 this->finished =
true;
1897 #ifdef MODULE_CONFIG_DEBUG 1899 this->list.emplace_back(this->categoryString +
"." + name);
1904 if(!(this->setCategory)) {
1905 throw Exception(
"Module::Config::option(): No category has been set");
1908 if(this->finished || !(this->currentCategory)) {
1913 if(this->currentItem.
name != name) {
1918 if(this->currentItem.
value->IsUint64()) {
1919 target = this->currentItem.
value->GetUint64();
1921 else if(this->currentItem.
value->IsNull()) {
1927 + this->currentItem.
str()
1928 +
"' ignored because of wrong type (not unsigned 64-bit integer)." 1933 this->finished =
true;
1957 inline void Config::option(
const std::string& name, std::vector<std::uint64_t>& target) {
1958 #ifdef MODULE_CONFIG_DEBUG 1960 this->list.emplace_back(this->categoryString +
"." + name);
1965 if(!(this->setCategory)) {
1966 throw Exception(
"Module::Config::option(): No category has been set");
1969 if(this->finished || !(this->currentCategory)) {
1974 if(this->currentItem.
name != name) {
1979 if(this->currentItem.
value->IsArray()) {
1983 target.reserve(this->currentItem.
value->Size());
1986 for(
const auto& item : this->currentItem.
value->GetArray()) {
1987 if(item.IsUint64()) {
1988 target.push_back(item.GetUint64());
1991 target.push_back(0);
1993 if(!item.IsNull()) {
1996 + this->currentItem.
str()
1997 +
"' ignored because of wrong type (not unsigned 64-bit integer)." 2006 + this->currentItem.
str()
2007 +
"' ignored because of wrong type (not array)." 2012 this->finished =
true;
2037 #ifdef MODULE_CONFIG_DEBUG 2039 this->list.emplace_back(this->categoryString +
"." + name);
2044 if(!(this->setCategory)) {
2045 throw Exception(
"Module::Config::option(): No category has been set");
2048 if(this->finished || !(this->currentCategory)) {
2053 if(this->currentItem.
name != name) {
2058 if(this->currentItem.
value->IsFloat()) {
2059 target = this->currentItem.
value->GetFloat();
2061 else if(this->currentItem.
value->IsNull()) {
2067 + this->currentItem.
str()
2068 +
"' ignored because of wrong type (not floating-point number)." 2073 this->finished =
true;
2098 #ifdef MODULE_CONFIG_DEBUG 2100 this->list.emplace_back(this->categoryString +
"." + name);
2105 if(!(this->setCategory)) {
2106 throw Exception(
"Module::Config::option(): No category has been set");
2109 if(this->finished || !(this->currentCategory)) {
2114 if(this->currentItem.
name != name) {
2119 if(this->currentItem.
value->IsArray()) {
2123 target.reserve(this->currentItem.
value->Size());
2126 for(
const auto& item : this->currentItem.
value->GetArray()) {
2127 if(item.IsFloat()) {
2128 target.push_back(item.GetFloat());
2131 target.push_back(0);
2133 if(!item.IsNull()) {
2136 + this->currentItem.
str()
2137 +
"' ignored because of wrong type (not floating-point number)." 2146 + this->currentItem.
str()
2147 +
"' ignored because of wrong type (not array)." 2152 this->finished =
true;
2179 #ifdef MODULE_CONFIG_DEBUG 2181 this->list.emplace_back(this->categoryString +
"." + name);
2186 if(!(this->setCategory)) {
2188 "Module::Config::option():" 2189 " No category has been set" 2193 if(this->finished || !(this->currentCategory)) {
2198 if(this->currentItem.
name != name) {
2203 if(this->currentItem.
value->IsString()) {
2205 this->currentItem.
value->GetString(),
2206 this->currentItem.
value->GetStringLength()
2226 + this->currentItem.
str()
2227 +
"' ignored because it contains invalid characters." 2235 Config::makeSubUrl(str);
2243 Config::makeUrl(str);
2258 throw Exception(
"Config::option(): Invalid string parsing option");
2261 else if(this->currentItem.
value->IsNull()) {
2267 + this->currentItem.
str()
2268 +
"' ignored because of wrong type (not string)." 2273 this->finished =
true;
2300 const std::string& name,
2301 std::vector<std::string>& target,
2304 #ifdef MODULE_CONFIG_DEBUG 2306 this->list.emplace_back(this->categoryString +
"." + name);
2311 if(!(this->setCategory)) {
2313 "Module::Config::option():" 2314 " No category has been set" 2318 if(this->finished || !(this->currentCategory)) {
2323 if(this->currentItem.
name != name) {
2328 if(this->currentItem.
value->IsArray()) {
2332 target.reserve(this->currentItem.
value->Size());
2335 for(
const auto& item : this->currentItem.
value->GetArray()) {
2336 if(item.IsString()) {
2337 std::string str(item.GetString(), item.GetStringLength());
2342 target.emplace_back(str);
2349 target.emplace_back(str);
2356 + this->currentItem.
str()
2357 +
"' ignored because it contains invalid characters." 2365 Config::makeSubUrl(str);
2367 target.emplace_back(str);
2373 Config::makeUrl(str);
2375 target.emplace_back(str);
2383 target.emplace_back(str);
2388 throw Exception(
"Config::option(): Invalid string parsing option");
2392 target.emplace_back();
2394 if(!item.IsNull()) {
2397 + this->currentItem.
str()
2398 +
"' ignored because of wrong type (not string)." 2407 + this->currentItem.
str()
2408 +
"' ignored because of wrong type (not array)." 2413 this->finished =
true;
2428 if(this->logPtr ==
nullptr) {
2430 "Config::warning(): No log queue is active." 2431 " Do not use this function outside of Config::loadConfig()!" 2435 this->logPtr->emplace(warning);
2485 inline void Config::logQueue(
const std::string& entry) {
2486 if(this->logPtr !=
nullptr) {
2487 this->logPtr->emplace(entry);
2497 inline void Config::makeSubUrl(std::string& s) {
2499 if(s.at(0) ==
'/') {
2504 if(s.length() >= protocol.length()) {
2505 if(s.substr(0, protocol.length()) == protocol) {
2517 inline void Config::makeUrl(std::string& s) {
2519 auto pos{s.find(
"://")};
2521 if(pos == std::string::npos) {
2528 pos = s.find(
'/', pos);
2530 if(pos != std::string::npos) {
CharParsingOption
Options for parsing char's.
Definition: Config.hpp:194
Uses a string as it is.
Definition: Config.hpp:178
void option(const std::string &name, bool &target)
Checks for a configuration option of type bool.
Definition: Config.hpp:573
const rapidjson::Value * value
JSON value of the configuration item, or nullptr if not initialized.
Definition: ConfigItem.hpp:52
Get char by its numeric value.
Definition: Config.hpp:196
std::string category
Category of the configuration item.
Definition: ConfigItem.hpp:46
virtual void reset()=0
Resets the module-specific configuration.
Abstract class as base for module-specific configurations.
Definition: Config.hpp:122
virtual void resetBase()
Resets basic options.
Definition: Config.hpp:2476
virtual void checkOptions()=0
Checks the module-specific configuration after parsing.
rapidjson::Document parseRapid(std::string_view json)
Parses JSON code using RapidJSON.
Definition: Json.hpp:575
#define MAIN_EXCEPTION_CLASS()
Macro used to easily define classes for general exceptions.
Definition: Exception.hpp:50
Config()=default
Default constructor.
Class for JSON exceptions.
Definition: Json.hpp:136
void trim(std::string &stringToTrim)
Removes whitespaces around a string.
Definition: Strings.hpp:360
std::string name
Name of the configuration item.
Definition: ConfigItem.hpp:49
StringParsingOption
Options for parsing strings.
Definition: Config.hpp:176
Class for configuration exceptions.
Definition: Config.hpp:150
virtual void parseBasicOption()
Parses a basic option.
Definition: Config.hpp:2457
constexpr std::array protocols
Protocols supported by the libcurl library.
Definition: Config.hpp:71
Get char from the beginning of a string.
Definition: Config.hpp:204
Config & operator=(Config &)=delete
Deleted copy assignment operator.
char getFirstOrEscapeChar(std::string_view from)
Gets the first character or an escaped character from the beginning of the given string.
Definition: Strings.hpp:948
void category(const std::string &category)
Sets the category of the subsequent configuration items to be checked for.
Definition: Config.hpp:527
Converts a string to a URL (without the protocol).
Definition: Config.hpp:187
void loadConfig(const std::string &configJson, LogQueue &warningsTo)
Loads a configuration.
Definition: Config.hpp:317
std::string_view view() const noexcept
Gets the description of the exception as a view to the underlying string.
Definition: Exception.hpp:158
std::string str() const
Combines category and name into one string.
Definition: ConfigItem.hpp:63
virtual ~Config()=default
Default destructor.
bool checkSQLName(std::string_view name)
Checks whether the given string is a valid name for MySQL tables and fields.
Definition: Strings.hpp:1079
Requires a SQL-compatible string.
Definition: Config.hpp:181
virtual void parseOption()=0
Parses a module-specific configuration option.
Trims a string.
Definition: Config.hpp:190
Converts a string to a sub-URL.
Definition: Config.hpp:184
Namespace for the different modules run by threads.
void warning(const std::string &warning)
Adds a warning to the logging queue.
Definition: Config.hpp:2427
Configuration item containing its category, name, and JSON value.
Definition: ConfigItem.hpp:41