/******************************************************************************
* Icinga 2 *
- * Copyright (C) 2012-2014 Icinga Development Team (http://www.icinga.org) *
+ * Copyright (C) 2012-2018 Icinga Development Team (https://www.icinga.com/) *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License *
#include "livestatus/servicestable.hpp"
#include "livestatus/hoststable.hpp"
+#include "livestatus/servicegroupstable.hpp"
+#include "livestatus/hostgroupstable.hpp"
#include "livestatus/endpointstable.hpp"
#include "icinga/service.hpp"
+#include "icinga/servicegroup.hpp"
+#include "icinga/hostgroup.hpp"
#include "icinga/checkcommand.hpp"
#include "icinga/eventcommand.hpp"
#include "icinga/timeperiod.hpp"
#include "icinga/macroprocessor.hpp"
#include "icinga/icingaapplication.hpp"
#include "icinga/compatutility.hpp"
-#include "base/dynamictype.hpp"
+#include "icinga/pluginutility.hpp"
+#include "base/configtype.hpp"
#include "base/objectlock.hpp"
+#include "base/json.hpp"
#include "base/convert.hpp"
#include "base/utility.hpp"
-#include <boost/foreach.hpp>
#include <boost/tuple/tuple.hpp>
#include <boost/algorithm/string/replace.hpp>
using namespace icinga;
-ServicesTable::ServicesTable(void)
+ServicesTable::ServicesTable(LivestatusGroupByType type)
+ : Table(type)
{
AddColumns(this);
}
+
void ServicesTable::AddColumns(Table *table, const String& prefix,
- const Column::ObjectAccessor& objectAccessor)
+ const Column::ObjectAccessor& objectAccessor)
{
table->AddColumn(prefix + "description", Column(&ServicesTable::ShortNameAccessor, objectAccessor));
table->AddColumn(prefix + "service_description", Column(&ServicesTable::ShortNameAccessor, objectAccessor)); //ugly compatibility hack
table->AddColumn(prefix + "plugin_output", Column(&ServicesTable::PluginOutputAccessor, objectAccessor));
table->AddColumn(prefix + "long_plugin_output", Column(&ServicesTable::LongPluginOutputAccessor, objectAccessor));
table->AddColumn(prefix + "perf_data", Column(&ServicesTable::PerfDataAccessor, objectAccessor));
- table->AddColumn(prefix + "notification_period", Column(&ServicesTable::NotificationPeriodAccessor, objectAccessor));
+ table->AddColumn(prefix + "notification_period", Column(&Table::EmptyStringAccessor, objectAccessor));
table->AddColumn(prefix + "check_period", Column(&ServicesTable::CheckPeriodAccessor, objectAccessor));
table->AddColumn(prefix + "notes", Column(&ServicesTable::NotesAccessor, objectAccessor));
table->AddColumn(prefix + "notes_expanded", Column(&ServicesTable::NotesExpandedAccessor, objectAccessor));
table->AddColumn(prefix + "process_performance_data", Column(&ServicesTable::ProcessPerformanceDataAccessor, objectAccessor));
table->AddColumn(prefix + "is_executing", Column(&Table::ZeroAccessor, objectAccessor));
table->AddColumn(prefix + "active_checks_enabled", Column(&ServicesTable::ActiveChecksEnabledAccessor, objectAccessor));
- table->AddColumn(prefix + "check_options", Column(&ServicesTable::CheckOptionsAccessor, objectAccessor));
+ table->AddColumn(prefix + "check_options", Column(&Table::EmptyStringAccessor, objectAccessor));
table->AddColumn(prefix + "flap_detection_enabled", Column(&ServicesTable::FlapDetectionEnabledAccessor, objectAccessor));
- table->AddColumn(prefix + "check_freshness", Column(&ServicesTable::CheckFreshnessAccessor, objectAccessor));
+ table->AddColumn(prefix + "check_freshness", Column(&Table::OneAccessor, objectAccessor));
table->AddColumn(prefix + "obsess_over_service", Column(&Table::ZeroAccessor, objectAccessor));
- table->AddColumn(prefix + "modified_attributes", Column(&ServicesTable::ModifiedAttributesAccessor, objectAccessor));
- table->AddColumn(prefix + "modified_attributes_list", Column(&ServicesTable::ModifiedAttributesListAccessor, objectAccessor));
+ table->AddColumn(prefix + "modified_attributes", Column(&Table::ZeroAccessor, objectAccessor));
+ table->AddColumn(prefix + "modified_attributes_list", Column(&Table::ZeroAccessor, objectAccessor));
table->AddColumn(prefix + "pnpgraph_present", Column(&Table::ZeroAccessor, objectAccessor));
table->AddColumn(prefix + "staleness", Column(&ServicesTable::StalenessAccessor, objectAccessor));
table->AddColumn(prefix + "check_interval", Column(&ServicesTable::CheckIntervalAccessor, objectAccessor));
table->AddColumn(prefix + "contact_groups", Column(&ServicesTable::ContactGroupsAccessor, objectAccessor));
table->AddColumn(prefix + "check_source", Column(&ServicesTable::CheckSourceAccessor, objectAccessor));
table->AddColumn(prefix + "is_reachable", Column(&ServicesTable::IsReachableAccessor, objectAccessor));
-
- HostsTable::AddColumns(table, "host_", boost::bind(&ServicesTable::HostAccessor, _1, objectAccessor));
+ table->AddColumn(prefix + "cv_is_json", Column(&ServicesTable::CVIsJsonAccessor, objectAccessor));
+ table->AddColumn(prefix + "original_attributes", Column(&ServicesTable::OriginalAttributesAccessor, objectAccessor));
+
+ HostsTable::AddColumns(table, "host_", std::bind(&ServicesTable::HostAccessor, _1, objectAccessor));
+
+ /* add additional group by values received through the object accessor */
+ if (table->GetGroupByType() == LivestatusGroupByServiceGroup) {
+ /* _1 = row, _2 = groupByType, _3 = groupByObject */
+ Log(LogDebug, "Livestatus")
+ << "Processing services group by servicegroup table.";
+ ServiceGroupsTable::AddColumns(table, "servicegroup_", std::bind(&ServicesTable::ServiceGroupAccessor, _1, _2, _3));
+ } else if (table->GetGroupByType() == LivestatusGroupByHostGroup) {
+ /* _1 = row, _2 = groupByType, _3 = groupByObject */
+ Log(LogDebug, "Livestatus")
+ << "Processing services group by hostgroup table.";
+ HostGroupsTable::AddColumns(table, "hostgroup_", std::bind(&ServicesTable::HostGroupAccessor, _1, _2, _3));
+ }
}
-String ServicesTable::GetName(void) const
+String ServicesTable::GetName() const
{
return "services";
}
-String ServicesTable::GetPrefix(void) const
+String ServicesTable::GetPrefix() const
{
return "service";
}
void ServicesTable::FetchRows(const AddRowFunction& addRowFn)
{
- BOOST_FOREACH(const Service::Ptr& service, DynamicType::GetObjectsByType<Service>()) {
- addRowFn(service);
+ if (GetGroupByType() == LivestatusGroupByServiceGroup) {
+ for (const ServiceGroup::Ptr& sg : ConfigType::GetObjectsByType<ServiceGroup>()) {
+ for (const Service::Ptr& service : sg->GetMembers()) {
+ /* the caller must know which groupby type and value are set for this row */
+ if (!addRowFn(service, LivestatusGroupByServiceGroup, sg))
+ return;
+ }
+ }
+ } else if (GetGroupByType() == LivestatusGroupByHostGroup) {
+ for (const HostGroup::Ptr& hg : ConfigType::GetObjectsByType<HostGroup>()) {
+ ObjectLock ylock(hg);
+ for (const Host::Ptr& host : hg->GetMembers()) {
+ ObjectLock ylock(host);
+ for (const Service::Ptr& service : host->GetServices()) {
+ /* the caller must know which groupby type and value are set for this row */
+ if (!addRowFn(service, LivestatusGroupByHostGroup, hg))
+ return;
+ }
+ }
+ }
+ } else {
+ for (const Service::Ptr& service : ConfigType::GetObjectsByType<Service>()) {
+ if (!addRowFn(service, LivestatusGroupByNone, Empty))
+ return;
+ }
}
}
Value service;
if (parentObjectAccessor)
- service = parentObjectAccessor(row);
+ service = parentObjectAccessor(row, LivestatusGroupByNone, Empty);
else
service = row;
Service::Ptr svc = static_cast<Service::Ptr>(service);
if (!svc)
- return Object::Ptr();
+ return nullptr;
return svc->GetHost();
}
+Object::Ptr ServicesTable::ServiceGroupAccessor(const Value& row, LivestatusGroupByType groupByType, const Object::Ptr& groupByObject)
+{
+ /* return the current group by value set from within FetchRows()
+ * this is the servicegroup object used for the table join inside
+ * in AddColumns()
+ */
+ if (groupByType == LivestatusGroupByServiceGroup)
+ return groupByObject;
+
+ return nullptr;
+}
+
+Object::Ptr ServicesTable::HostGroupAccessor(const Value& row, LivestatusGroupByType groupByType, const Object::Ptr& groupByObject)
+{
+ /* return the current group by value set from within FetchRows()
+ * this is the servicegroup object used for the table join inside
+ * in AddColumns()
+ */
+ if (groupByType == LivestatusGroupByHostGroup)
+ return groupByObject;
+
+ return nullptr;
+}
+
Value ServicesTable::ShortNameAccessor(const Value& row)
{
Service::Ptr service = static_cast<Service::Ptr>(row);
String perfdata;
CheckResult::Ptr cr = service->GetLastCheckResult();
- if (cr)
- perfdata = CompatUtility::GetCheckResultPerfdata(cr);
-
- return perfdata;
-}
-
-Value ServicesTable::NotificationPeriodAccessor(const Value& row)
-{
- Service::Ptr service = static_cast<Service::Ptr>(row);
-
- if (!service)
+ if (!cr)
return Empty;
- return CompatUtility::GetCheckableNotificationNotificationPeriod(service);
+ return PluginUtility::FormatPerfdata(cr->GetPerformanceData());
}
Value ServicesTable::CheckPeriodAccessor(const Value& row)
if (!service)
return Empty;
- MacroProcessor::ResolverList resolvers;
- resolvers.push_back(std::make_pair("service", service));
- resolvers.push_back(std::make_pair("host", service->GetHost()));
- resolvers.push_back(std::make_pair("icinga", IcingaApplication::GetInstance()));
+ MacroProcessor::ResolverList resolvers {
+ { "service", service },
+ { "host", service->GetHost() },
+ { "icinga", IcingaApplication::GetInstance() }
+ };
return MacroProcessor::ResolveMacros(service->GetNotes(), resolvers);
}
if (!service)
return Empty;
- MacroProcessor::ResolverList resolvers;
- resolvers.push_back(std::make_pair("service", service));
- resolvers.push_back(std::make_pair("host", service->GetHost()));
- resolvers.push_back(std::make_pair("icinga", IcingaApplication::GetInstance()));
+ MacroProcessor::ResolverList resolvers {
+ { "service", service },
+ { "host", service->GetHost() },
+ { "icinga", IcingaApplication::GetInstance() }
+ };
return MacroProcessor::ResolveMacros(service->GetNotesUrl(), resolvers);
}
if (!service)
return Empty;
- MacroProcessor::ResolverList resolvers;
- resolvers.push_back(std::make_pair("service", service));
- resolvers.push_back(std::make_pair("host", service->GetHost()));
- resolvers.push_back(std::make_pair("icinga", IcingaApplication::GetInstance()));
+ MacroProcessor::ResolverList resolvers {
+ { "service", service },
+ { "host", service->GetHost() },
+ { "icinga", IcingaApplication::GetInstance() }
+ };
return MacroProcessor::ResolveMacros(service->GetActionUrl(), resolvers);
}
if (!service)
return Empty;
- MacroProcessor::ResolverList resolvers;
- resolvers.push_back(std::make_pair("service", service));
- resolvers.push_back(std::make_pair("host", service->GetHost()));
- resolvers.push_back(std::make_pair("icinga", IcingaApplication::GetInstance()));
+ MacroProcessor::ResolverList resolvers {
+ { "service", service },
+ { "host", service->GetHost() },
+ { "icinga", IcingaApplication::GetInstance() }
+ };
return MacroProcessor::ResolveMacros(service->GetIconImage(), resolvers);
}
if (!service)
return Empty;
- return CompatUtility::GetCheckableHasBeenChecked(service);
+ return Convert::ToLong(service->HasBeenChecked());
}
Value ServicesTable::LastStateAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckableCheckType(service);
+ return (service->GetEnableActiveChecks() ? 0 : 1); /* 0 .. active, 1 .. passive */
}
Value ServicesTable::AcknowledgedAccessor(const Value& row)
return Empty;
ObjectLock olock(service);
- return CompatUtility::GetCheckableIsAcknowledged(service);
+ return service->IsAcknowledged();
}
Value ServicesTable::AcknowledgementTypeAccessor(const Value& row)
return Empty;
ObjectLock olock(service);
- return CompatUtility::GetCheckableAcknowledgementType(service);
+ return service->GetAcknowledgement();
}
Value ServicesTable::NoMoreNotificationsAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckableActiveChecksEnabled(service);
+ return Convert::ToLong(service->GetEnableActiveChecks());
}
Value ServicesTable::AcceptPassiveChecksAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckablePassiveChecksEnabled(service);
+ return Convert::ToLong(service->GetEnablePassiveChecks());
}
Value ServicesTable::EventHandlerEnabledAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckableEventHandlerEnabled(service);
+ return Convert::ToLong(service->GetEnableEventHandler());
}
Value ServicesTable::NotificationsEnabledAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckableNotificationsEnabled(service);
+ return Convert::ToLong(service->GetEnableNotifications());
}
Value ServicesTable::ProcessPerformanceDataAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckableProcessPerformanceData(service);
+ return Convert::ToLong(service->GetEnablePerfdata());
}
Value ServicesTable::ActiveChecksEnabledAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckableActiveChecksEnabled(service);
-}
-
-Value ServicesTable::CheckOptionsAccessor(const Value& row)
-{
- /* TODO - forcexec, freshness, orphan, none */
- return Empty;
+ return Convert::ToLong(service->GetEnableActiveChecks());
}
Value ServicesTable::FlapDetectionEnabledAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckableFlapDetectionEnabled(service);
-}
-
-Value ServicesTable::CheckFreshnessAccessor(const Value& row)
-{
- Service::Ptr service = static_cast<Service::Ptr>(row);
-
- if (!service)
- return Empty;
-
- return CompatUtility::GetCheckableFreshnessChecksEnabled(service);
-}
-
-Value ServicesTable::ModifiedAttributesAccessor(const Value& row)
-{
- Service::Ptr service = static_cast<Service::Ptr>(row);
-
- if (!service)
- return Empty;
-
- return service->GetModifiedAttributes();
-}
-
-Value ServicesTable::ModifiedAttributesListAccessor(const Value& row)
-{
- Service::Ptr service = static_cast<Service::Ptr>(row);
-
- if (!service)
- return Empty;
-
- return CompatUtility::GetModifiedAttributesList(service);
+ return Convert::ToLong(service->GetEnableFlapping());
}
Value ServicesTable::StalenessAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckableStaleness(service);
+ if (service->HasBeenChecked() && service->GetLastCheck() > 0)
+ return (Utility::GetTime() - service->GetLastCheck()) / (service->GetCheckInterval() * 3600);
+
+ return 0.0;
}
Value ServicesTable::CheckIntervalAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckableLowFlapThreshold(service);
+ return service->GetFlappingThresholdLow();
}
Value ServicesTable::HighFlapThresholdAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckableHighFlapThreshold(service);
+ return service->GetFlappingThresholdHigh();
}
Value ServicesTable::LatencyAccessor(const Value& row)
if (!service)
return Empty;
- return (Service::CalculateLatency(service->GetLastCheckResult()));
+ CheckResult::Ptr cr = service->GetLastCheckResult();
+
+ if (!cr)
+ return Empty;
+
+ return cr->CalculateLatency();
}
Value ServicesTable::ExecutionTimeAccessor(const Value& row)
if (!service)
return Empty;
- return (Service::CalculateExecutionTime(service->GetLastCheckResult()));
+ CheckResult::Ptr cr = service->GetLastCheckResult();
+
+ if (!cr)
+ return Empty;
+
+ return cr->CalculateExecutionTime();
}
Value ServicesTable::PercentStateChangeAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckablePercentStateChange(service);
+ return service->GetFlappingCurrent();
}
Value ServicesTable::InCheckPeriodAccessor(const Value& row)
if (!service)
return Empty;
- return CompatUtility::GetCheckableInCheckPeriod(service);
+ TimePeriod::Ptr timeperiod = service->GetCheckPeriod();
+
+ /* none set means always checked */
+ if (!timeperiod)
+ return 1;
+
+ return Convert::ToLong(timeperiod->IsInside(Utility::GetTime()));
}
Value ServicesTable::InNotificationPeriodAccessor(const Value& row)
if (!service)
return Empty;
- Array::Ptr contact_names = make_shared<Array>();
+ Array::Ptr contact_names = new Array();
- BOOST_FOREACH(const User::Ptr& user, CompatUtility::GetCheckableNotificationUsers(service)) {
+ for (const User::Ptr& user : CompatUtility::GetCheckableNotificationUsers(service)) {
contact_names->Add(user->GetName());
}
if (!service)
return Empty;
- Dictionary::Ptr downtimes = service->GetDowntimes();
-
- Array::Ptr ids = make_shared<Array>();
-
- ObjectLock olock(downtimes);
-
- String id;
- Downtime::Ptr downtime;
- BOOST_FOREACH(tie(id, downtime), downtimes) {
-
- if (!downtime)
- continue;
+ Array::Ptr results = new Array();
+ for (const Downtime::Ptr& downtime : service->GetDowntimes()) {
if (downtime->IsExpired())
continue;
- ids->Add(downtime->GetLegacyId());
+ results->Add(downtime->GetLegacyId());
}
- return ids;
+ return results;
}
Value ServicesTable::DowntimesWithInfoAccessor(const Value& row)
if (!service)
return Empty;
- Dictionary::Ptr downtimes = service->GetDowntimes();
-
- Array::Ptr ids = make_shared<Array>();
-
- ObjectLock olock(downtimes);
-
- String id;
- Downtime::Ptr downtime;
- BOOST_FOREACH(tie(id, downtime), downtimes) {
-
- if (!downtime)
- continue;
+ Array::Ptr results = new Array();
+ for (const Downtime::Ptr& downtime : service->GetDowntimes()) {
if (downtime->IsExpired())
continue;
- Array::Ptr downtime_info = make_shared<Array>();
+ Array::Ptr downtime_info = new Array();
downtime_info->Add(downtime->GetLegacyId());
downtime_info->Add(downtime->GetAuthor());
downtime_info->Add(downtime->GetComment());
- ids->Add(downtime_info);
+ results->Add(downtime_info);
}
- return ids;
+ return results;
}
Value ServicesTable::CommentsAccessor(const Value& row)
if (!service)
return Empty;
- Dictionary::Ptr comments = service->GetComments();
-
- Array::Ptr ids = make_shared<Array>();
-
- ObjectLock olock(comments);
-
- String id;
- Comment::Ptr comment;
- BOOST_FOREACH(tie(id, comment), comments) {
-
- if (!comment)
- continue;
+ Array::Ptr results = new Array();
+ for (const Comment::Ptr& comment : service->GetComments()) {
if (comment->IsExpired())
continue;
- ids->Add(comment->GetLegacyId());
+ results->Add(comment->GetLegacyId());
}
- return ids;
+ return results;
}
Value ServicesTable::CommentsWithInfoAccessor(const Value& row)
if (!service)
return Empty;
- Dictionary::Ptr comments = service->GetComments();
-
- Array::Ptr ids = make_shared<Array>();
-
- ObjectLock olock(comments);
-
- String id;
- Comment::Ptr comment;
- BOOST_FOREACH(tie(id, comment), comments) {
-
- if (!comment)
- continue;
+ Array::Ptr results = new Array();
+ for (const Comment::Ptr& comment : service->GetComments()) {
if (comment->IsExpired())
continue;
- Array::Ptr comment_info = make_shared<Array>();
+ Array::Ptr comment_info = new Array();
comment_info->Add(comment->GetLegacyId());
comment_info->Add(comment->GetAuthor());
comment_info->Add(comment->GetText());
- ids->Add(comment_info);
+ results->Add(comment_info);
}
- return ids;
+ return results;
}
Value ServicesTable::CommentsWithExtraInfoAccessor(const Value& row)
if (!service)
return Empty;
- Dictionary::Ptr comments = service->GetComments();
-
- Array::Ptr ids = make_shared<Array>();
-
- ObjectLock olock(comments);
-
- String id;
- Comment::Ptr comment;
- BOOST_FOREACH(tie(id, comment), comments) {
-
- if (!comment)
- continue;
+ Array::Ptr results = new Array();
+ for (const Comment::Ptr& comment : service->GetComments()) {
if (comment->IsExpired())
continue;
- Array::Ptr comment_info = make_shared<Array>();
+ Array::Ptr comment_info = new Array();
comment_info->Add(comment->GetLegacyId());
comment_info->Add(comment->GetAuthor());
comment_info->Add(comment->GetText());
comment_info->Add(comment->GetEntryType());
comment_info->Add(static_cast<int>(comment->GetEntryTime()));
- ids->Add(comment_info);
+ results->Add(comment_info);
}
- return ids;
+ return results;
}
Value ServicesTable::CustomVariableNamesAccessor(const Value& row)
{
ObjectLock olock(service);
- vars = CompatUtility::GetCustomAttributeConfig(service);
+ vars = service->GetVars();
}
- if (!vars)
- return Empty;
+ Array::Ptr cv = new Array();
- Array::Ptr cv = make_shared<Array>();
+ if (!vars)
+ return cv;
ObjectLock olock(vars);
- BOOST_FOREACH(const Dictionary::Pair kv, vars) {
- cv->Add(kv.second);
+ for (const Dictionary::Pair& kv : vars) {
+ cv->Add(kv.first);
}
return cv;
{
ObjectLock olock(service);
- vars = CompatUtility::GetCustomAttributeConfig(service);
+ vars = service->GetVars();
}
- if (!vars)
- return Empty;
+ Array::Ptr cv = new Array();
- Array::Ptr cv = make_shared<Array>();
+ if (!vars)
+ return cv;
ObjectLock olock(vars);
- BOOST_FOREACH(const Dictionary::Pair& kv, vars) {
- cv->Add(kv.second);
+ for (const Dictionary::Pair& kv : vars) {
+ if (kv.second.IsObjectType<Array>() || kv.second.IsObjectType<Dictionary>())
+ cv->Add(JsonEncode(kv.second));
+ else
+ cv->Add(kv.second);
}
return cv;
{
ObjectLock olock(service);
- vars = CompatUtility::GetCustomAttributeConfig(service);
+ vars = service->GetVars();
}
+ Array::Ptr cv = new Array();
+
if (!vars)
- return Empty;
+ return cv;
- Array::Ptr cv = make_shared<Array>();
+ ObjectLock olock(vars);
+ for (const Dictionary::Pair& kv : vars) {
+ Array::Ptr key_val = new Array();
+ key_val->Add(kv.first);
+
+ if (kv.second.IsObjectType<Array>() || kv.second.IsObjectType<Dictionary>())
+ key_val->Add(JsonEncode(kv.second));
+ else
+ key_val->Add(kv.second);
- String key;
- Value value;
- BOOST_FOREACH(tie(key, value), vars) {
- Array::Ptr key_val = make_shared<Array>();
- key_val->Add(key);
- key_val->Add(value);
cv->Add(key_val);
}
return cv;
}
+Value ServicesTable::CVIsJsonAccessor(const Value& row)
+{
+ Service::Ptr service = static_cast<Service::Ptr>(row);
+
+ if (!service)
+ return Empty;
+
+ Dictionary::Ptr vars;
+
+ {
+ ObjectLock olock(service);
+ vars = service->GetVars();
+ }
+
+ if (!vars)
+ return Empty;
+
+ bool cv_is_json = false;
+
+ ObjectLock olock(vars);
+ for (const Dictionary::Pair& kv : vars) {
+ if (kv.second.IsObjectType<Array>() || kv.second.IsObjectType<Dictionary>())
+ cv_is_json = true;
+ }
+
+ return cv_is_json;
+}
+
Value ServicesTable::GroupsAccessor(const Value& row)
{
Service::Ptr service = static_cast<Service::Ptr>(row);
if (!service)
return Empty;
- Array::Ptr contactgroup_names = make_shared<Array>();
+ Array::Ptr contactgroup_names = new Array();
- BOOST_FOREACH(const UserGroup::Ptr& usergroup, CompatUtility::GetCheckableNotificationUserGroups(service)) {
+ for (const UserGroup::Ptr& usergroup : CompatUtility::GetCheckableNotificationUserGroups(service)) {
contactgroup_names->Add(usergroup->GetName());
}
return service->IsReachable();
}
+
+Value ServicesTable::OriginalAttributesAccessor(const Value& row)
+{
+ Service::Ptr service = static_cast<Service::Ptr>(row);
+
+ if (!service)
+ return Empty;
+
+ return JsonEncode(service->GetOriginalAttributes());
+}