diff options
Diffstat (limited to 'library/Toplevelview/Tree/TLVServiceNode.php')
-rw-r--r-- | library/Toplevelview/Tree/TLVServiceNode.php | 143 |
1 files changed, 143 insertions, 0 deletions
diff --git a/library/Toplevelview/Tree/TLVServiceNode.php b/library/Toplevelview/Tree/TLVServiceNode.php new file mode 100644 index 0000000..2036714 --- /dev/null +++ b/library/Toplevelview/Tree/TLVServiceNode.php @@ -0,0 +1,143 @@ +<?php +/* Copyright (C) 2017 Icinga Development Team <info@icinga.com> */ + +namespace Icinga\Module\Toplevelview\Tree; + +use Icinga\Application\Benchmark; +use Icinga\Exception\NotFoundError; +use Icinga\Module\Toplevelview\Monitoring\Servicestatus; + +class TLVServiceNode extends TLVIcingaNode +{ + protected $type = 'service'; + + protected $key = '{host}!{service}'; + + public function getTitle() + { + return sprintf( + '%s: %s', + $this->get('host'), + $this->get('service') + ); + } + + public function register() + { + // also register host, because that's what we fetch data with + $hostDummy = new TLVHostNode(); + $this->root->registerObject($hostDummy->getType(), $this->get('host'), get_class($hostDummy)); + + // register myself + return parent::register(); + } + + public function getKey() + { + return sprintf('%s!%s', $this->properties['host'], $this->properties['service']); + } + + public static function fetch(TLVTree $root) + { + Benchmark::measure('Begin fetching services'); + + if (! array_key_exists('service', $root->registeredObjects) or empty($root->registeredObjects['service'])) { + throw new NotFoundError('No services registered to fetch!'); + } + + $names = array_keys($root->registeredObjects['host']); + + $columns = array( + 'host_name', + 'service_description', + 'service_hard_state', + 'service_handled', + 'service_handled_wo_host', + 'service_notifications_enabled', + 'service_notification_period', + 'service_is_flapping', + 'service_in_downtime', + ); + + $options = []; + foreach (['notification_periods', 'host_never_unhandled', 'ignored_notification_periods'] as $opt) { + $options[$opt] = $root->get($opt); + } + + if ($root->get('notification_periods') === true) { + $columns[] = 'service_in_notification_period'; + } + + // Note: this uses a patched version of Servicestatus / ServicestatusQuery ! + $services = new Servicestatus($root->getBackend(), $columns, $options); + $services->where('host_name', $names); + + foreach ($services as $service) { + $key = sprintf('%s!%s', $service->host_name, $service->service_description); + if (array_key_exists($key, $root->registeredObjects['service'])) { + $root->registeredObjects['service'][$key] = $service; + } + } + + Benchmark::measure('Finished fetching services'); + } + + public function getStatus() + { + if ($this->status === null) { + $this->status = $status = new TLVStatus(); + $key = $this->getKey(); + + if (($data = $this->root->getFetched($this->type, $key)) !== null) { + $status->zero(); + $status->add('total'); + + $state = $data->service_hard_state; + + if ($this->getRoot()->get('notification_periods') === true) { + $notInPeriod = $data->service_in_notification_period === '0'; + } else { + $notInPeriod = false; + } + + if ($this->getRoot()->get('host_never_unhandled') === true) { + $isHandled = $data->service_handled_wo_host === '1'; + } else { + $isHandled = $data->service_handled === '1'; + } + $isHandled = $isHandled || $data->service_is_flapping === '1'; + + if ($data->service_in_downtime > 0 + || $data->service_notifications_enabled === '0' + || $notInPeriod + ) { + $status->add('downtime_active'); + if ($state !== '0') { + $state = '10'; + } + } + + if ($isHandled) { + $handled = '_handled'; + } else { + $handled = '_unhandled'; + } + + if ($state === '0' || $state === '99') { + $status->add('ok', 1); + } elseif ($state === '1') { + $status->add('warning' . $handled, 1); + } elseif ($state === '2') { + $status->add('critical' . $handled, 1); + } elseif ($state === '10') { + $status->add('downtime_handled'); + } else { + $status->add('unknown' . $handled, 1); + } + } else { + $status->add('missing', 1); + } + } + return $this->status; + } +} |