Remove nlohmann::json::items()
nlohmann::json::items() throws an exception if the object in question is
not a json object. This has the potential to cause problems, and isn't
in line with the standard that we code against.
Replace all uses of items with iterating the nlohmann::json::object_t.
This adds a new error check for pulling the object_t out of the
nlohmann::json object before each iteration, to ensure that we're
handling errors.
Tested: Redfish service validator passes.
Change-Id: I2934c9450ec296c76544c2a7c5855c9b519eae7f
Signed-off-by: Ed Tanous <ed@tanous.net>
diff --git a/include/event_service_store.hpp b/include/event_service_store.hpp
index f03bd79..f7f03ab 100644
--- a/include/event_service_store.hpp
+++ b/include/event_service_store.hpp
@@ -26,26 +26,27 @@
std::vector<std::string> metricReportDefinitions;
static std::shared_ptr<UserSubscription>
- fromJson(const nlohmann::json& j, const bool loadFromOldConfig = false)
+ fromJson(const nlohmann::json::object_t& j,
+ const bool loadFromOldConfig = false)
{
std::shared_ptr<UserSubscription> subvalue =
std::make_shared<UserSubscription>();
- for (const auto& element : j.items())
+ for (const auto& element : j)
{
- if (element.key() == "Id")
+ if (element.first == "Id")
{
const std::string* value =
- element.value().get_ptr<const std::string*>();
+ element.second.get_ptr<const std::string*>();
if (value == nullptr)
{
continue;
}
subvalue->id = *value;
}
- else if (element.key() == "Destination")
+ else if (element.first == "Destination")
{
const std::string* value =
- element.value().get_ptr<const std::string*>();
+ element.second.get_ptr<const std::string*>();
if (value == nullptr)
{
continue;
@@ -58,63 +59,68 @@
}
subvalue->destinationUrl = std::move(*url);
}
- else if (element.key() == "Protocol")
+ else if (element.first == "Protocol")
{
const std::string* value =
- element.value().get_ptr<const std::string*>();
+ element.second.get_ptr<const std::string*>();
if (value == nullptr)
{
continue;
}
subvalue->protocol = *value;
}
- else if (element.key() == "DeliveryRetryPolicy")
+ else if (element.first == "DeliveryRetryPolicy")
{
const std::string* value =
- element.value().get_ptr<const std::string*>();
+ element.second.get_ptr<const std::string*>();
if (value == nullptr)
{
continue;
}
subvalue->retryPolicy = *value;
}
- else if (element.key() == "Context")
+ else if (element.first == "Context")
{
const std::string* value =
- element.value().get_ptr<const std::string*>();
+ element.second.get_ptr<const std::string*>();
if (value == nullptr)
{
continue;
}
subvalue->customText = *value;
}
- else if (element.key() == "EventFormatType")
+ else if (element.first == "EventFormatType")
{
const std::string* value =
- element.value().get_ptr<const std::string*>();
+ element.second.get_ptr<const std::string*>();
if (value == nullptr)
{
continue;
}
subvalue->eventFormatType = *value;
}
- else if (element.key() == "SubscriptionType")
+ else if (element.first == "SubscriptionType")
{
const std::string* value =
- element.value().get_ptr<const std::string*>();
+ element.second.get_ptr<const std::string*>();
if (value == nullptr)
{
continue;
}
subvalue->subscriptionType = *value;
}
- else if (element.key() == "MessageIds")
+ else if (element.first == "MessageIds")
{
- const auto& obj = element.value();
- for (const auto& val : obj.items())
+ const nlohmann::json::array_t* obj =
+ element.second.get_ptr<const nlohmann::json::array_t*>();
+ if (obj == nullptr)
+ {
+ continue;
+ }
+ for (const auto& val : *obj)
{
const std::string* value =
- val.value().get_ptr<const std::string*>();
+ val.get_ptr<const std::string*>();
if (value == nullptr)
{
continue;
@@ -122,13 +128,18 @@
subvalue->registryMsgIds.emplace_back(*value);
}
}
- else if (element.key() == "RegistryPrefixes")
+ else if (element.first == "RegistryPrefixes")
{
- const auto& obj = element.value();
- for (const auto& val : obj.items())
+ const nlohmann::json::array_t* obj =
+ element.second.get_ptr<const nlohmann::json::array_t*>();
+ if (obj == nullptr)
+ {
+ continue;
+ }
+ for (const auto& val : *obj)
{
const std::string* value =
- val.value().get_ptr<const std::string*>();
+ val.get_ptr<const std::string*>();
if (value == nullptr)
{
continue;
@@ -136,13 +147,18 @@
subvalue->registryPrefixes.emplace_back(*value);
}
}
- else if (element.key() == "ResourceTypes")
+ else if (element.first == "ResourceTypes")
{
- const auto& obj = element.value();
- for (const auto& val : obj.items())
+ const nlohmann::json::array_t* obj =
+ element.second.get_ptr<const nlohmann::json::array_t*>();
+ if (obj == nullptr)
+ {
+ continue;
+ }
+ for (const auto& val : *obj)
{
const std::string* value =
- val.value().get_ptr<const std::string*>();
+ val.get_ptr<const std::string*>();
if (value == nullptr)
{
continue;
@@ -150,29 +166,39 @@
subvalue->resourceTypes.emplace_back(*value);
}
}
- else if (element.key() == "HttpHeaders")
+ else if (element.first == "HttpHeaders")
{
- const auto& obj = element.value();
- for (const auto& val : obj.items())
+ const nlohmann::json::object_t* obj =
+ element.second.get_ptr<const nlohmann::json::object_t*>();
+ if (obj == nullptr)
+ {
+ continue;
+ }
+ for (const auto& val : *obj)
{
const std::string* value =
- val.value().get_ptr<const std::string*>();
+ val.second.get_ptr<const std::string*>();
if (value == nullptr)
{
BMCWEB_LOG_ERROR("Failed to parse value for key{}",
- val.key());
+ val.first);
continue;
}
- subvalue->httpHeaders.set(val.key(), *value);
+ subvalue->httpHeaders.set(val.first, *value);
}
}
- else if (element.key() == "MetricReportDefinitions")
+ else if (element.first == "MetricReportDefinitions")
{
- const auto& obj = element.value();
- for (const auto& val : obj.items())
+ const nlohmann::json::array_t* obj =
+ element.second.get_ptr<const nlohmann::json::array_t*>();
+ if (obj == nullptr)
+ {
+ continue;
+ }
+ for (const auto& val : *obj)
{
const std::string* value =
- val.value().get_ptr<const std::string*>();
+ val.get_ptr<const std::string*>();
if (value == nullptr)
{
continue;
@@ -184,7 +210,7 @@
{
BMCWEB_LOG_ERROR(
"Got unexpected property reading persistent file: {}",
- element.key());
+ element.first);
continue;
}
}
@@ -210,23 +236,23 @@
uint32_t retryAttempts = 3;
uint32_t retryTimeoutInterval = 30;
- void fromJson(const nlohmann::json& j)
+ void fromJson(const nlohmann::json::object_t& j)
{
- for (const auto& element : j.items())
+ for (const auto& element : j)
{
- if (element.key() == "ServiceEnabled")
+ if (element.first == "ServiceEnabled")
{
- const bool* value = element.value().get_ptr<const bool*>();
+ const bool* value = element.second.get_ptr<const bool*>();
if (value == nullptr)
{
continue;
}
enabled = *value;
}
- else if (element.key() == "DeliveryRetryAttempts")
+ else if (element.first == "DeliveryRetryAttempts")
{
const uint64_t* value =
- element.value().get_ptr<const uint64_t*>();
+ element.second.get_ptr<const uint64_t*>();
if ((value == nullptr) ||
(*value > std::numeric_limits<uint32_t>::max()))
{
@@ -234,10 +260,10 @@
}
retryAttempts = static_cast<uint32_t>(*value);
}
- else if (element.key() == "DeliveryRetryIntervalSeconds")
+ else if (element.first == "DeliveryRetryIntervalSeconds")
{
const uint64_t* value =
- element.value().get_ptr<const uint64_t*>();
+ element.second.get_ptr<const uint64_t*>();
if ((value == nullptr) ||
(*value > std::numeric_limits<uint32_t>::max()))
{