/** * Checks that none of the given triggers is inherited from a template. * * @throws APIException if one of the triggers is inherited * * @param array $triggerIds */ protected function checkNotInherited(array $triggerIds) { $trigger = DBfetch(DBselect('SELECT t.triggerid,t.description,t.expression' . ' FROM triggers t' . ' WHERE ' . dbConditionInt('t.triggerid', $triggerIds) . 'AND t.templateid IS NOT NULL', 1)); if ($trigger) { self::exception(ZBX_API_ERROR_PARAMETERS, _s('Cannot delete templated trigger "%1$s:%2$s".', $trigger['description'], CMacrosResolverHelper::resolveTriggerExpression($trigger['expression']))); } }
/** * Delete existing trigger prototypes. * * @see https://www.zabbix.com/documentation/3.0/manual/api/reference/triggerprototype/delete * * @param array $triggerPrototypeIds * @param bool $nopermissions * * @throws APIException * * @return array */ public function delete(array $triggerPrototypeIds, $nopermissions = false) { if (!$triggerPrototypeIds) { self::exception(ZBX_API_ERROR_PARAMETERS, _('Empty input parameter.')); } // TODO: remove $nopermissions hack if (!$nopermissions) { $dbTriggerPrototypes = $this->get(['triggerids' => $triggerPrototypeIds, 'output' => ['description', 'expression', 'templateid'], 'editable' => true, 'preservekeys' => true]); foreach ($triggerPrototypeIds as $triggerPrototypeId) { if (!isset($dbTriggerPrototypes[$triggerPrototypeId])) { self::exception(ZBX_API_ERROR_PARAMETERS, _('No permissions to referred object or it does not exist!')); } $dbTriggerPrototype = $dbTriggerPrototypes[$triggerPrototypeId]; if ($dbTriggerPrototype['templateid'] != 0) { self::exception(ZBX_API_ERROR_PARAMETERS, _s('Cannot delete templated trigger "%1$s:%2$s".', $dbTriggerPrototype['description'], CMacrosResolverHelper::resolveTriggerExpression($dbTriggerPrototype['expression']))); } } } // get child trigger prototypes $parentTriggerPrototypeIds = $triggerPrototypeIds; do { $dbTriggerPrototypes = DBselect('SELECT triggerid' . ' FROM triggers' . ' WHERE ' . dbConditionInt('templateid', $parentTriggerPrototypeIds)); $parentTriggerPrototypeIds = []; while ($dbTriggerPrototype = DBfetch($dbTriggerPrototypes)) { $parentTriggerPrototypeIds[] = $dbTriggerPrototype['triggerid']; $triggerPrototypeIds[$dbTriggerPrototype['triggerid']] = $dbTriggerPrototype['triggerid']; } } while ($parentTriggerPrototypeIds); // delete triggers created from this prototype $createdTriggerIds = DBfetchColumn(DBselect('SELECT triggerid' . ' FROM trigger_discovery' . ' WHERE ' . dbConditionInt('parent_triggerid', $triggerPrototypeIds)), 'triggerid'); if ($createdTriggerIds) { API::Trigger()->delete($createdTriggerIds, true); } // select all trigger prototypes which are deleted (include children) $dbTriggerPrototypes = $this->get(['triggerids' => $triggerPrototypeIds, 'output' => ['triggerid', 'description', 'expression'], 'nopermissions' => true, 'preservekeys' => true, 'selectHosts' => ['name']]); // TODO: REMOVE info foreach ($dbTriggerPrototypes as $dbTriggerPrototype) { info(_s('Deleted: Trigger prototype "%1$s" on "%2$s".', $dbTriggerPrototype['description'], implode(', ', zbx_objectValues($dbTriggerPrototype['hosts'], 'name')))); add_audit_ext(AUDIT_ACTION_DELETE, AUDIT_RESOURCE_TRIGGER_PROTOTYPE, $dbTriggerPrototype['triggerid'], $dbTriggerPrototype['description'] . ':' . $dbTriggerPrototype['expression'], null, null, null); } DB::delete('triggers', ['triggerid' => $triggerPrototypeIds]); return ['triggerids' => $triggerPrototypeIds]; }
} } } //------------------------ <FORM> --------------------------- if (hasRequest('sform')) { $widget = (new CWidget())->setTitle(_('Trigger')); $form = (new CForm())->setName('sform')->addVar('sform', '1')->addVar('itemid', $itemid); if (hasRequest('triggerid')) { $form->addVar('triggerid', getRequest('triggerid')); } $form_list = new CFormList(); if (hasRequest('triggerid') && !hasRequest('form_refresh')) { $result = DBselect('SELECT t.expression,t.description,t.priority,t.comments,t.url,t.status,t.type' . ' FROM triggers t' . ' WHERE t.triggerid=' . zbx_dbstr(getRequest('triggerid')) . ' AND EXISTS (' . 'SELECT NULL' . ' FROM functions f,items i' . ' WHERE t.triggerid=f.triggerid' . ' AND f.itemid=i.itemid ' . ' AND i.value_type IN (' . ITEM_VALUE_TYPE_LOG . ',' . ITEM_VALUE_TYPE_TEXT . ',' . ITEM_VALUE_TYPE_STR . ')' . ')'); if ($row = DBfetch($result)) { $description = $row['description']; $expression = CMacrosResolverHelper::resolveTriggerExpression($row['expression']); $type = $row['type']; $priority = $row['priority']; $comments = $row['comments']; $url = $row['url']; $status = $row['status']; } // break expression into parts $expressions = $constructor->getPartsFromExpression($expression); } else { $description = getRequest('description', ''); $expressions = getRequest('expressions', []); $type = getRequest('type', 0); $priority = getRequest('priority', 0); $comments = getRequest('comments', ''); $url = getRequest('url', '');
if (!hasRequest('groupid')) { $_REQUEST['groupid'] = 0; } } else { if ($source == EVENT_SOURCE_TRIGGERS) { // try to find matching trigger when host is changed // use the host ID from the page filter since it may not be present in the request // if all hosts are selected, preserve the selected trigger if ($triggerId != 0 && $pageFilter->hostid != 0) { $old_triggers = API::Trigger()->get(['output' => ['description', 'expression'], 'selectHosts' => ['hostid', 'host'], 'triggerids' => [$triggerId]]); $old_trigger = reset($old_triggers); $old_trigger['hosts'] = zbx_toHash($old_trigger['hosts'], 'hostid'); // if the trigger doesn't belong to the selected host - find a new one on that host if (!array_key_exists($pageFilter->hostid, $old_trigger['hosts'])) { $triggerId = 0; $old_expression = CMacrosResolverHelper::resolveTriggerExpression($old_trigger['expression']); $new_triggers = API::Trigger()->get(['output' => ['triggerid', 'description', 'expression'], 'selectHosts' => ['hostid', 'host'], 'filter' => ['description' => $old_trigger['description']], 'hostids' => [$pageFilter->hostid]]); $new_triggers = CMacrosResolverHelper::resolveTriggerExpressions($new_triggers); foreach ($new_triggers as $new_trigger) { $new_trigger['hosts'] = zbx_toHash($new_trigger['hosts'], 'hostid'); foreach ($old_trigger['hosts'] as $old_host) { $new_expression = triggerExpressionReplaceHost($new_trigger['expression'], $new_trigger['hosts'][$pageFilter->hostid]['host'], $old_host['host']); if ($old_expression === $new_expression) { CProfile::update('web.events.filter.triggerid', $new_trigger['triggerid'], PROFILE_TYPE_ID); $triggerId = $new_trigger['triggerid']; break 2; } } } } }
/** * Checks that no trigger with the same description and expression as $trigger exist on the given host. * Assumes the given trigger is valid. * * @throws APIException if at least one trigger exists * * @param array $trigger a trigger with an exploded expression * @param null $hostid * * @return void */ protected function checkIfExistsOnHost(array $trigger, $hostId = null) { // skip the check if the description and expression haven't been changed if (!isset($trigger['description']) && !isset($trigger['expression'])) { return; } // make sure we have all the required data if (!isset($trigger['description']) || !isset($trigger['expression'])) { $explodeExpression = !isset($trigger['expression']); $trigger = $this->extendObject($this->tableName(), $trigger, ['description', 'expression']); if ($explodeExpression) { $trigger['expression'] = CMacrosResolverHelper::resolveTriggerExpression($trigger['expression']); } } $filter = ['description' => $trigger['description']]; if ($hostId) { $filter['hostid'] = $hostId; } else { $expressionData = new CTriggerExpression($trigger['expression']); $expressionData->parse($trigger['expression']); $expressionHosts = $expressionData->getHosts(); $filter['host'] = reset($expressionHosts); } $triggers = $this->get(['filter' => $filter, 'output' => ['expression', 'triggerid'], 'nopermissions' => true]); $triggers = CMacrosResolverHelper::resolveTriggerExpressions($triggers); foreach ($triggers as $dbTrigger) { // check if the expressions are also equal and that this is a different trigger $differentTrigger = !isset($trigger['triggerid']) || !idcmp($trigger['triggerid'], $dbTrigger['triggerid']); if ($dbTrigger['expression'] === $trigger['expression'] && $differentTrigger) { $options = ['output' => ['name'], 'templated_hosts' => true, 'nopermissions' => true, 'limit' => 1]; if (isset($filter['host'])) { $options['filter'] = ['host' => $filter['host']]; } else { $options['hostids'] = $hostId; } $host = API::Host()->get($options); $host = reset($host); self::exception(ZBX_API_ERROR_PARAMETERS, _s('Trigger "%1$s" already exists on "%2$s".', $trigger['description'], $host['name'])); } } }
function make_trigger_details($trigger) { $hostNames = []; $config = select_config(); $hostIds = zbx_objectValues($trigger['hosts'], 'hostid'); $hosts = API::Host()->get(['output' => ['name', 'hostid', 'status'], 'hostids' => $hostIds, 'selectScreens' => API_OUTPUT_COUNT, 'selectGraphs' => API_OUTPUT_COUNT]); if (count($hosts) > 1) { order_result($hosts, 'name', ZBX_SORT_UP); } $scripts = API::Script()->getScriptsByHosts($hostIds); foreach ($hosts as $host) { $hostName = new CSpan($host['name'], ZBX_STYLE_LINK_ACTION); $hostName->setMenuPopup(CMenuPopupHelper::getHost($host, $scripts[$host['hostid']])); $hostNames[] = $hostName; $hostNames[] = ', '; } array_pop($hostNames); $expression = CMacrosResolverHelper::resolveTriggerExpression($trigger['expression'], ['html' => true, 'resolve_usermacros' => true, 'resolve_macros' => true]); $table = (new CTableInfo())->addRow([new CCol(_n('Host', 'Hosts', count($hosts))), new CCol($hostNames)])->addRow([new CCol(_('Trigger')), new CCol(CMacrosResolverHelper::resolveTriggerName($trigger))])->addRow([_('Severity'), getSeverityCell($trigger['priority'], $config)])->addRow([new CCol(_('Expression')), new CCol($expression)])->addRow([_('Event generation'), _('Normal') . (TRIGGER_MULT_EVENT_ENABLED == $trigger['type'] ? SPACE . '+' . SPACE . _('Multiple PROBLEM events') : '')])->addRow([_('Disabled'), TRIGGER_STATUS_ENABLED == $trigger['status'] ? (new CCol(_('No')))->addClass(ZBX_STYLE_GREEN) : (new CCol(_('Yes')))->addClass(ZBX_STYLE_RED)]); return $table; }