2016-10-12 09:19:02 +02:00
|
|
|
<?php
|
|
|
|
|
|
|
|
namespace Icinga\Module\Director\Objects;
|
|
|
|
|
2018-04-26 13:41:21 +02:00
|
|
|
use Exception;
|
2016-11-04 19:56:56 +01:00
|
|
|
use Icinga\Data\Filter\Filter;
|
2018-10-11 23:13:51 +02:00
|
|
|
use Icinga\Module\Director\Db;
|
2019-02-15 00:48:05 +01:00
|
|
|
use Icinga\Module\Director\Db\Cache\PrefetchCache;
|
2018-10-11 23:13:51 +02:00
|
|
|
use Icinga\Module\Director\DirectorObject\Automation\ExportInterface;
|
2016-11-24 17:39:51 +01:00
|
|
|
use Icinga\Module\Director\Exception\DuplicateKeyException;
|
2016-10-12 09:19:02 +02:00
|
|
|
use Icinga\Module\Director\IcingaConfig\IcingaConfig;
|
2019-02-15 00:48:05 +01:00
|
|
|
use Icinga\Module\Director\Resolver\HostServiceBlacklist;
|
2018-05-29 21:29:38 +02:00
|
|
|
use InvalidArgumentException;
|
2018-10-11 23:13:51 +02:00
|
|
|
use RuntimeException;
|
2016-11-04 20:31:01 +01:00
|
|
|
|
2018-10-11 23:13:51 +02:00
|
|
|
class IcingaServiceSet extends IcingaObject implements ExportInterface
|
2016-10-12 09:19:02 +02:00
|
|
|
{
|
|
|
|
protected $table = 'icinga_service_set';
|
|
|
|
|
|
|
|
protected $defaultProperties = array(
|
|
|
|
'id' => null,
|
|
|
|
'host_id' => null,
|
|
|
|
'object_name' => null,
|
|
|
|
'object_type' => null,
|
|
|
|
'description' => null,
|
2016-10-26 01:01:18 +02:00
|
|
|
'assign_filter' => null,
|
2016-10-12 09:19:02 +02:00
|
|
|
);
|
|
|
|
|
2016-10-12 09:31:00 +02:00
|
|
|
protected $keyName = array('host_id', 'object_name');
|
|
|
|
|
2016-10-12 10:30:10 +02:00
|
|
|
protected $supportsImports = true;
|
|
|
|
|
2016-10-12 09:19:02 +02:00
|
|
|
protected $supportsCustomVars = true;
|
|
|
|
|
|
|
|
protected $supportsApplyRules = true;
|
|
|
|
|
2016-10-13 15:44:53 +02:00
|
|
|
protected $supportedInLegacy = true;
|
|
|
|
|
2016-10-12 09:19:02 +02:00
|
|
|
protected $relations = array(
|
|
|
|
'host' => 'IcingaHost',
|
|
|
|
);
|
|
|
|
|
|
|
|
public function isDisabled()
|
|
|
|
{
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
public function supportsAssignments()
|
|
|
|
{
|
|
|
|
return true;
|
|
|
|
}
|
2016-11-10 14:04:05 +01:00
|
|
|
|
|
|
|
protected function setKey($key)
|
|
|
|
{
|
|
|
|
if (is_int($key)) {
|
2018-11-15 11:14:14 +01:00
|
|
|
$this->set('id', $key);
|
2016-11-10 14:04:05 +01:00
|
|
|
} elseif (is_string($key)) {
|
|
|
|
$keyComponents = preg_split('~!~', $key);
|
|
|
|
if (count($keyComponents) === 1) {
|
|
|
|
$this->set('object_name', $keyComponents[0]);
|
|
|
|
$this->set('object_type', 'template');
|
2017-01-13 19:47:54 +01:00
|
|
|
} else {
|
2018-05-29 21:29:38 +02:00
|
|
|
throw new InvalidArgumentException(sprintf(
|
|
|
|
'Can not parse key: %s',
|
|
|
|
$key
|
|
|
|
));
|
2016-11-10 14:04:05 +01:00
|
|
|
}
|
|
|
|
} else {
|
|
|
|
return parent::setKey($key);
|
|
|
|
}
|
|
|
|
|
|
|
|
return $this;
|
|
|
|
}
|
2016-10-12 09:19:02 +02:00
|
|
|
|
|
|
|
/**
|
2016-11-04 19:56:56 +01:00
|
|
|
* @return IcingaService[]
|
2018-11-15 11:14:14 +01:00
|
|
|
* @throws \Icinga\Exception\NotFoundError
|
2016-10-12 09:19:02 +02:00
|
|
|
*/
|
|
|
|
public function getServiceObjects()
|
|
|
|
{
|
2019-04-10 13:08:30 +02:00
|
|
|
// don't try to resolve services for unstored objects - as in getServiceObjectsForSet()
|
|
|
|
// also for diff in activity log
|
|
|
|
if ($this->get('id') === null) {
|
|
|
|
return [];
|
|
|
|
}
|
|
|
|
|
2016-11-04 19:56:56 +01:00
|
|
|
if ($this->get('host_id')) {
|
2016-10-26 01:01:18 +02:00
|
|
|
$imports = $this->imports()->getObjects();
|
2016-10-20 09:23:49 +02:00
|
|
|
if (empty($imports)) {
|
|
|
|
return array();
|
|
|
|
}
|
2016-10-26 01:01:18 +02:00
|
|
|
return $this->getServiceObjectsForSet(array_shift($imports));
|
|
|
|
} else {
|
|
|
|
return $this->getServiceObjectsForSet($this);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2018-11-15 11:14:14 +01:00
|
|
|
/**
|
|
|
|
* @param IcingaServiceSet $set
|
|
|
|
* @return array
|
|
|
|
* @throws \Icinga\Exception\NotFoundError
|
|
|
|
*/
|
2016-10-26 01:01:18 +02:00
|
|
|
protected function getServiceObjectsForSet(IcingaServiceSet $set)
|
|
|
|
{
|
2016-11-04 19:56:56 +01:00
|
|
|
if ($set->get('id') === null) {
|
2016-10-26 01:01:18 +02:00
|
|
|
return array();
|
|
|
|
}
|
2016-10-20 09:23:49 +02:00
|
|
|
|
2016-10-26 01:01:18 +02:00
|
|
|
$connection = $this->getConnection();
|
|
|
|
$db = $this->getDb();
|
|
|
|
$ids = $db->fetchCol(
|
|
|
|
$db->select()->from('icinga_service', 'id')
|
2016-11-04 19:56:56 +01:00
|
|
|
->where('service_set_id = ?', $set->get('id'))
|
2016-10-26 01:01:18 +02:00
|
|
|
);
|
|
|
|
|
|
|
|
$services = array();
|
|
|
|
foreach ($ids as $id) {
|
|
|
|
$service = IcingaService::load(array(
|
|
|
|
'id' => $id,
|
2016-10-20 09:23:49 +02:00
|
|
|
'object_type' => 'template'
|
2016-10-26 01:01:18 +02:00
|
|
|
), $connection);
|
2016-11-04 20:31:01 +01:00
|
|
|
$service->set('service_set', null);
|
2016-10-26 01:01:18 +02:00
|
|
|
|
2016-11-04 19:56:56 +01:00
|
|
|
$services[$service->getObjectName()] = $service;
|
2016-10-12 09:19:02 +02:00
|
|
|
}
|
|
|
|
|
2016-10-26 01:01:18 +02:00
|
|
|
return $services;
|
2016-10-12 09:19:02 +02:00
|
|
|
}
|
|
|
|
|
2018-10-11 23:13:51 +02:00
|
|
|
public function getUniqueIdentifier()
|
|
|
|
{
|
|
|
|
return $this->getObjectName();
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @return object
|
|
|
|
* @throws \Icinga\Exception\NotFoundError
|
|
|
|
*/
|
2018-10-08 06:30:31 +02:00
|
|
|
public function export()
|
|
|
|
{
|
|
|
|
if ($this->get('host_id')) {
|
|
|
|
return $this->exportSetOnHost();
|
|
|
|
} else {
|
|
|
|
return $this->exportTemplate();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
protected function exportSetOnHost()
|
|
|
|
{
|
|
|
|
// TODO.
|
2018-10-11 23:13:51 +02:00
|
|
|
throw new RuntimeException('Not yet');
|
2018-10-08 06:30:31 +02:00
|
|
|
}
|
|
|
|
|
2018-10-11 23:13:51 +02:00
|
|
|
/**
|
|
|
|
* @return object
|
|
|
|
* @throws \Icinga\Exception\NotFoundError
|
|
|
|
*/
|
2018-10-08 06:30:31 +02:00
|
|
|
protected function exportTemplate()
|
|
|
|
{
|
|
|
|
$props = $this->getProperties();
|
|
|
|
unset($props['id'], $props['host_id']);
|
|
|
|
$props['services'] = [];
|
|
|
|
foreach ($this->getServiceObjects() as $serviceObject) {
|
|
|
|
$props['services'][$serviceObject->getObjectName()] = $serviceObject->export();
|
|
|
|
}
|
|
|
|
ksort($props);
|
|
|
|
|
|
|
|
return (object) $props;
|
|
|
|
}
|
|
|
|
|
2018-10-11 23:13:51 +02:00
|
|
|
/**
|
|
|
|
* @param $plain
|
|
|
|
* @param Db $db
|
|
|
|
* @param bool $replace
|
|
|
|
* @return IcingaServiceSet
|
|
|
|
* @throws DuplicateKeyException
|
|
|
|
* @throws \Icinga\Exception\NotFoundError
|
|
|
|
*/
|
|
|
|
public static function import($plain, Db $db, $replace = false)
|
|
|
|
{
|
|
|
|
$properties = (array) $plain;
|
|
|
|
$name = $properties['object_name'];
|
|
|
|
if (isset($properties['services'])) {
|
|
|
|
$services = $properties['services'];
|
|
|
|
unset($properties['services']);
|
|
|
|
} else {
|
|
|
|
$services = [];
|
|
|
|
}
|
|
|
|
|
|
|
|
if ($properties['object_type'] !== 'template') {
|
|
|
|
throw new InvalidArgumentException(sprintf(
|
|
|
|
'Can import only Templates, got "%s" for "%s"',
|
|
|
|
$properties['object_type'],
|
|
|
|
$name
|
|
|
|
));
|
|
|
|
}
|
|
|
|
if ($replace && static::exists($name, $db)) {
|
|
|
|
$object = static::load($name, $db);
|
|
|
|
} elseif (static::exists($name, $db)) {
|
|
|
|
throw new DuplicateKeyException(
|
|
|
|
'Service Set "%s" already exists',
|
|
|
|
$name
|
|
|
|
);
|
|
|
|
} else {
|
|
|
|
$object = static::create([], $db);
|
|
|
|
}
|
|
|
|
|
|
|
|
$object->setProperties($properties);
|
|
|
|
|
|
|
|
// This is not how other imports work, but here we need an ID
|
|
|
|
if (! $object->hasBeenLoadedFromDb()) {
|
|
|
|
$object->store();
|
|
|
|
}
|
|
|
|
|
|
|
|
$setId = $object->get('id');
|
|
|
|
$sQuery = $db->getDbAdapter()->select()->from(
|
|
|
|
['s' => 'icinga_service'],
|
|
|
|
's.*'
|
|
|
|
)->where('service_set_id = ?', $setId);
|
|
|
|
$existingServices = IcingaService::loadAll($db, $sQuery, 'object_name');
|
|
|
|
foreach ($services as $service) {
|
|
|
|
if (isset($service->fields)) {
|
|
|
|
unset($service->fields);
|
|
|
|
}
|
|
|
|
$name = $service->object_name;
|
|
|
|
if (isset($existingServices[$name])) {
|
|
|
|
$existing = $existingServices[$name];
|
|
|
|
$existing->setProperties((array) $service);
|
|
|
|
$existing->set('service_set_id', $setId);
|
|
|
|
if ($existing->hasBeenModified()) {
|
|
|
|
$existing->store();
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
$new = IcingaService::create((array) $service, $db);
|
|
|
|
$new->set('service_set_id', $setId);
|
|
|
|
$new->store();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return $object;
|
|
|
|
}
|
|
|
|
|
2019-02-13 11:18:04 +01:00
|
|
|
public function beforeDelete()
|
|
|
|
{
|
|
|
|
// check if this is a template, or directly assigned to a host
|
|
|
|
if ($this->get('host_id') === null) {
|
|
|
|
// find all host sets and delete them
|
|
|
|
foreach ($this->fetchHostSets() as $set) {
|
|
|
|
$set->delete();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
parent::beforeDelete();
|
|
|
|
}
|
|
|
|
|
2018-11-15 11:14:14 +01:00
|
|
|
/**
|
|
|
|
* @throws \Icinga\Exception\NotFoundError
|
|
|
|
*/
|
2018-08-13 11:21:54 +02:00
|
|
|
public function onDelete()
|
|
|
|
{
|
|
|
|
$hostId = $this->get('host_id');
|
|
|
|
if ($hostId) {
|
|
|
|
$deleteIds = [];
|
|
|
|
foreach ($this->getServiceObjects() as $service) {
|
|
|
|
$deleteIds[] = (int) $service->get('id');
|
|
|
|
}
|
|
|
|
|
|
|
|
if (! empty($deleteIds)) {
|
|
|
|
$db = $this->getDb();
|
|
|
|
$db->delete(
|
|
|
|
'icinga_host_service_blacklist',
|
|
|
|
$db->quoteInto(
|
|
|
|
sprintf('host_id = %s AND service_id IN (?)', $hostId),
|
|
|
|
$deleteIds
|
|
|
|
)
|
|
|
|
);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
parent::onDelete();
|
|
|
|
}
|
|
|
|
|
2018-11-15 11:14:14 +01:00
|
|
|
/**
|
|
|
|
* @param IcingaConfig $config
|
|
|
|
* @throws \Icinga\Exception\NotFoundError
|
|
|
|
*/
|
2016-10-12 09:19:02 +02:00
|
|
|
public function renderToConfig(IcingaConfig $config)
|
|
|
|
{
|
2019-04-10 13:08:30 +02:00
|
|
|
// always print the header, so you have minimal info present
|
|
|
|
$file = $this->getConfigFileWithHeader($config);
|
|
|
|
|
2016-11-04 19:56:56 +01:00
|
|
|
if ($this->get('assign_filter') === null && $this->isTemplate()) {
|
2016-10-12 09:19:02 +02:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
if ($config->isLegacy()) {
|
2016-11-04 19:56:56 +01:00
|
|
|
$this->renderToLegacyConfig($config);
|
|
|
|
return;
|
2016-10-12 09:19:02 +02:00
|
|
|
}
|
|
|
|
|
2016-11-08 16:23:16 +01:00
|
|
|
$services = $this->getServiceObjects();
|
|
|
|
if (empty($services)) {
|
|
|
|
return;
|
|
|
|
}
|
2016-10-26 01:01:18 +02:00
|
|
|
|
2016-10-12 09:19:02 +02:00
|
|
|
// Loop over all services belonging to this set
|
|
|
|
// add our assign rules and then add the service to the config
|
|
|
|
// eventually clone them beforehand to not get into trouble with caches
|
|
|
|
// figure out whether we might need a zone property
|
2016-11-08 16:23:16 +01:00
|
|
|
foreach ($services as $service) {
|
2016-11-04 19:56:56 +01:00
|
|
|
if ($filter = $this->get('assign_filter')) {
|
|
|
|
$service->set('object_type', 'apply');
|
|
|
|
$service->set('assign_filter', $filter);
|
|
|
|
} elseif ($hostId = $this->get('host_id')) {
|
2019-02-15 00:48:05 +01:00
|
|
|
$host = $this->getRelatedObject('host', $hostId)->getObjectName();
|
|
|
|
if (in_array($host, $this->getBlacklistedHostnames($service))) {
|
|
|
|
continue;
|
|
|
|
}
|
2019-02-26 13:48:58 +01:00
|
|
|
$service->set('object_type', 'object');
|
|
|
|
$service->set('use_var_overrides', 'y');
|
|
|
|
$service->set('host_id', $hostId);
|
2016-10-26 01:01:18 +02:00
|
|
|
} else {
|
2016-11-04 19:56:56 +01:00
|
|
|
// Service set template without assign filter or host
|
|
|
|
continue;
|
2016-10-12 09:19:02 +02:00
|
|
|
}
|
|
|
|
|
2016-11-04 19:56:56 +01:00
|
|
|
$this->copyVarsToService($service);
|
2016-10-12 09:19:02 +02:00
|
|
|
$file->addObject($service);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-02-15 00:48:05 +01:00
|
|
|
/**
|
|
|
|
* @return array
|
|
|
|
*/
|
|
|
|
public function getBlacklistedHostnames($service)
|
|
|
|
{
|
|
|
|
// Hint: if ($this->isApplyRule()) would be nice, but apply rules are
|
|
|
|
// not enough, one might want to blacklist single services from Sets
|
|
|
|
// assigned to single Hosts.
|
|
|
|
if (PrefetchCache::shouldBeUsed()) {
|
|
|
|
$lookup = PrefetchCache::instance()->hostServiceBlacklist();
|
|
|
|
} else {
|
|
|
|
$lookup = new HostServiceBlacklist($this->getConnection());
|
|
|
|
}
|
|
|
|
|
|
|
|
return $lookup->getBlacklistedHostnamesForService($service);
|
|
|
|
}
|
|
|
|
|
2016-10-26 01:01:18 +02:00
|
|
|
protected function getConfigFileWithHeader(IcingaConfig $config)
|
|
|
|
{
|
|
|
|
$file = $config->configFile(
|
|
|
|
'zones.d/' . $this->getRenderingZone($config) . '/servicesets'
|
|
|
|
);
|
|
|
|
|
2018-08-12 13:11:32 +02:00
|
|
|
$file->addContent($this->getConfigHeaderComment($config));
|
2016-10-26 01:01:18 +02:00
|
|
|
return $file;
|
|
|
|
}
|
|
|
|
|
2016-10-12 09:19:02 +02:00
|
|
|
protected function getConfigHeaderComment(IcingaConfig $config)
|
|
|
|
{
|
2019-04-10 13:08:30 +02:00
|
|
|
$name = $this->getObjectName();
|
|
|
|
$assign = $this->get('assign_filter');
|
|
|
|
|
2016-10-12 09:19:02 +02:00
|
|
|
if ($config->isLegacy()) {
|
2019-04-10 13:08:30 +02:00
|
|
|
if ($assign !== null) {
|
|
|
|
return "## applied Service Set '${name}'\n\n";
|
2016-11-07 12:42:27 +01:00
|
|
|
} else {
|
2019-04-10 13:08:30 +02:00
|
|
|
return "## Service Set '${name}' on this host\n\n";
|
2016-11-07 12:42:27 +01:00
|
|
|
}
|
2016-10-12 09:19:02 +02:00
|
|
|
} else {
|
2019-04-10 13:08:30 +02:00
|
|
|
$comment = [
|
|
|
|
"Service Set: ${name}",
|
|
|
|
];
|
2016-10-12 09:19:02 +02:00
|
|
|
|
2019-04-10 13:08:30 +02:00
|
|
|
if (($host = $this->get('host')) !== null) {
|
|
|
|
$comment[] = 'on host ' . $host;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (($description = $this->get('description')) !== null) {
|
|
|
|
$comment[] = '';
|
|
|
|
foreach (preg_split('~\\n~', $description) as $line) {
|
|
|
|
$comment[] = $line;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if ($assign !== null) {
|
|
|
|
$comment[] = '';
|
|
|
|
$comment[] = trim($this->renderAssign_Filter());
|
|
|
|
}
|
|
|
|
|
|
|
|
return "/**\n * " . join("\n * ", $comment) . "\n */\n\n";
|
|
|
|
}
|
2016-10-12 09:19:02 +02:00
|
|
|
}
|
|
|
|
|
2017-01-13 20:48:50 +01:00
|
|
|
public function copyVarsToService(IcingaService $service)
|
2016-10-12 09:19:02 +02:00
|
|
|
{
|
2016-11-04 19:56:56 +01:00
|
|
|
$serviceVars = $service->vars();
|
|
|
|
|
|
|
|
foreach ($this->vars() as $k => $var) {
|
|
|
|
$serviceVars->$k = $var;
|
2016-10-12 09:19:02 +02:00
|
|
|
}
|
|
|
|
|
2016-11-04 19:56:56 +01:00
|
|
|
return $this;
|
|
|
|
}
|
|
|
|
|
2018-11-15 11:14:14 +01:00
|
|
|
/**
|
|
|
|
* @param IcingaConfig $config
|
|
|
|
* @throws \Icinga\Exception\NotFoundError
|
|
|
|
*/
|
2016-11-04 19:56:56 +01:00
|
|
|
public function renderToLegacyConfig(IcingaConfig $config)
|
|
|
|
{
|
2016-11-04 20:31:01 +01:00
|
|
|
if ($this->get('assign_filter') === null && $this->isTemplate()) {
|
2016-10-12 09:19:02 +02:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
// evaluate my assign rules once, get related hosts
|
|
|
|
// Loop over all services belonging to this set
|
2016-11-04 19:56:56 +01:00
|
|
|
// generate every service with host_name host1,host2... -> not yet. And Zones?
|
2016-10-12 09:19:02 +02:00
|
|
|
|
2016-11-04 19:56:56 +01:00
|
|
|
$conn = $this->getConnection();
|
|
|
|
|
|
|
|
// Delegating this to the service would look, but this way it's faster
|
|
|
|
if ($filter = $this->get('assign_filter')) {
|
|
|
|
$filter = Filter::fromQueryString($filter);
|
|
|
|
|
2018-04-26 13:42:42 +02:00
|
|
|
$hostnames = HostApplyMatches::forFilter($filter, $conn);
|
2016-11-04 19:56:56 +01:00
|
|
|
} else {
|
2018-11-15 11:14:14 +01:00
|
|
|
$hostnames = array($this->getRelated('host')->getObjectName());
|
2018-04-26 13:42:42 +02:00
|
|
|
}
|
|
|
|
|
2018-09-20 12:53:21 +02:00
|
|
|
$blacklists = [];
|
|
|
|
|
2018-04-26 13:42:42 +02:00
|
|
|
foreach ($this->mapHostsToZones($hostnames) as $zone => $names) {
|
|
|
|
$file = $config->configFile('director/' . $zone . '/servicesets', '.cfg');
|
|
|
|
$file->addContent($this->getConfigHeaderComment($config));
|
|
|
|
|
2016-11-04 19:56:56 +01:00
|
|
|
foreach ($this->getServiceObjects() as $service) {
|
2018-11-15 11:14:14 +01:00
|
|
|
$object_name = $service->getObjectName();
|
2018-09-20 12:53:21 +02:00
|
|
|
|
|
|
|
if (! array_key_exists($object_name, $blacklists)) {
|
|
|
|
$blacklists[$object_name] = $service->getBlacklistedHostnames();
|
|
|
|
}
|
|
|
|
|
|
|
|
// check if all hosts in the zone ignore this service
|
|
|
|
$zoneNames = array_diff($names, $blacklists[$object_name]);
|
2019-03-06 14:58:35 +01:00
|
|
|
|
|
|
|
$disabled = [];
|
|
|
|
foreach ($zoneNames as $name) {
|
|
|
|
if (IcingaHost::load($name, $this->getConnection())->isDisabled()) {
|
|
|
|
$disabled[] = $name;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
$zoneNames = array_diff($zoneNames, $disabled);
|
|
|
|
|
2018-09-20 12:53:21 +02:00
|
|
|
if (empty($zoneNames)) {
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
|
2016-11-04 19:56:56 +01:00
|
|
|
$service->set('object_type', 'object');
|
2018-04-26 13:42:42 +02:00
|
|
|
$service->set('host_id', $names);
|
|
|
|
|
|
|
|
$this->copyVarsToService($service);
|
|
|
|
|
2016-11-04 19:56:56 +01:00
|
|
|
$file->addLegacyObject($service);
|
|
|
|
}
|
2016-10-12 09:19:02 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
public function getRenderingZone(IcingaConfig $config = null)
|
|
|
|
{
|
2016-11-04 19:56:56 +01:00
|
|
|
if ($this->get('host_id') === null) {
|
2016-10-26 01:01:18 +02:00
|
|
|
return $this->connection->getDefaultGlobalZoneName();
|
|
|
|
} else {
|
2016-11-04 19:56:56 +01:00
|
|
|
$host = $this->getRelatedObject('host', $this->get('host_id'));
|
2016-10-26 01:01:18 +02:00
|
|
|
return $host->getRenderingZone($config);
|
|
|
|
}
|
2016-10-12 09:19:02 +02:00
|
|
|
}
|
2016-11-24 17:39:51 +01:00
|
|
|
|
2017-08-27 18:59:32 +02:00
|
|
|
public function createWhere()
|
|
|
|
{
|
|
|
|
$where = parent::createWhere();
|
|
|
|
if (! $this->hasBeenLoadedFromDb()) {
|
|
|
|
if (null === $this->get('host_id') && null === $this->get('id')) {
|
|
|
|
$where .= " AND object_type = 'template'";
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return $where;
|
|
|
|
}
|
|
|
|
|
2017-09-11 16:02:39 +02:00
|
|
|
/**
|
|
|
|
* @return IcingaService[]
|
|
|
|
*/
|
|
|
|
public function fetchServices()
|
|
|
|
{
|
|
|
|
$connection = $this->getConnection();
|
|
|
|
$db = $connection->getDbAdapter();
|
|
|
|
|
|
|
|
/** @var IcingaService[] $services */
|
|
|
|
$services = IcingaService::loadAll(
|
|
|
|
$connection,
|
|
|
|
$db->select()->from('icinga_service')
|
|
|
|
->where('service_set_id = ?', $this->get('id'))
|
|
|
|
);
|
|
|
|
|
|
|
|
return $services;
|
|
|
|
}
|
|
|
|
|
2018-04-26 13:41:21 +02:00
|
|
|
/**
|
|
|
|
* Fetch IcingaServiceSet that are based on this set and added to hosts directly
|
|
|
|
*
|
|
|
|
* @return IcingaServiceSet[]
|
|
|
|
*/
|
|
|
|
public function fetchHostSets()
|
|
|
|
{
|
2018-11-15 11:14:14 +01:00
|
|
|
$id = $this->get('id');
|
|
|
|
if ($id === null) {
|
2018-04-26 13:41:21 +02:00
|
|
|
return [];
|
|
|
|
}
|
|
|
|
|
|
|
|
$query = $this->db->select()
|
|
|
|
->from(
|
|
|
|
['o' => $this->table]
|
|
|
|
)->join(
|
|
|
|
['ssi' => $this->table . '_inheritance'],
|
|
|
|
'ssi.service_set_id = o.id',
|
|
|
|
[]
|
|
|
|
)->where(
|
|
|
|
'ssi.parent_service_set_id = ?',
|
2018-11-15 11:14:14 +01:00
|
|
|
$id
|
2018-04-26 13:41:21 +02:00
|
|
|
);
|
|
|
|
|
|
|
|
return static::loadAll($this->connection, $query);
|
|
|
|
}
|
|
|
|
|
2018-11-15 11:14:14 +01:00
|
|
|
/**
|
|
|
|
* @throws DuplicateKeyException
|
|
|
|
* @throws \Icinga\Exception\NotFoundError
|
|
|
|
*/
|
2016-11-24 17:39:51 +01:00
|
|
|
protected function beforeStore()
|
|
|
|
{
|
|
|
|
parent::beforeStore();
|
|
|
|
|
|
|
|
$name = $this->getObjectName();
|
|
|
|
|
2017-08-28 06:00:23 +02:00
|
|
|
if ($this->isObject() && $this->get('host_id') === null) {
|
2018-05-29 21:29:38 +02:00
|
|
|
throw new InvalidArgumentException(
|
2017-08-28 06:00:23 +02:00
|
|
|
'A Service Set cannot be an object with no related host'
|
|
|
|
);
|
|
|
|
}
|
2016-11-24 17:39:51 +01:00
|
|
|
// checking if template object_name is unique
|
|
|
|
// TODO: Move to IcingaObject
|
|
|
|
if (! $this->hasBeenLoadedFromDb() && $this->isTemplate() && static::exists($name, $this->connection)) {
|
2017-08-26 10:51:19 +02:00
|
|
|
throw new DuplicateKeyException(
|
|
|
|
'%s template "%s" already existing in database!',
|
|
|
|
$this->getType(),
|
|
|
|
$name
|
|
|
|
);
|
2016-11-24 17:39:51 +01:00
|
|
|
}
|
|
|
|
}
|
2018-04-26 13:41:21 +02:00
|
|
|
|
|
|
|
public function toSingleIcingaConfig()
|
|
|
|
{
|
|
|
|
$config = parent::toSingleIcingaConfig();
|
|
|
|
|
|
|
|
try {
|
|
|
|
foreach ($this->fetchHostSets() as $set) {
|
|
|
|
$set->renderToConfig($config);
|
|
|
|
}
|
|
|
|
} catch (Exception $e) {
|
|
|
|
$config->configFile(
|
|
|
|
'failed-to-render'
|
|
|
|
)->prepend(
|
|
|
|
"/** Failed to render this object **/\n"
|
|
|
|
. '/* ' . $e->getMessage() . ' */'
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
return $config;
|
|
|
|
}
|
2016-10-12 09:19:02 +02:00
|
|
|
}
|