Ad Widget

Collapse

Хочется странного

Collapse
This topic has been answered.
X
X
 
  • Time
  • Show
Clear All
new posts
  • frofis
    Junior Member
    • Apr 2025
    • 17

    #1

    Хочется странного

    Приветствую.
    Создал выборку eventlog по eventid вход пользователя,
    в предобработке нашёл имя пользователя
    Добавил его через {ITEM.LASTVALUE} в заголовок проблемы
    Все получилось. Если событие единственное то просто класс. Но если события несколько, и даже если {ITEM.LASTVALUE} другое, проблема сворачивается в историю.
    Я понимаю это поведение zabbix по умолчанию, но хотелось бы для этого события получить несколько проблем.
    Никто не посоветует как реализовать данное извращение?​​
  • Answer selected by teddy at 29-07-2025, 13:04.
    teddy
    Senior Member
    • Dec 2017
    • 234

    Все достаточно просто.
    1. делаете триггер в режиме Multiple
    2. делаете выражение восстановления на такой тригер - NONE
    3. разрешаете ручное закрытие.

    Что имеем? Срабатывает триггер на все входы. но висит "вечно", пока руками не закроешь. Не всегда удобно. Если придумаете на что реагировать чтоб закрыть - вписываем в
    условие закрытия. Я не придумал.

    Потому чтоб убрать "вечные" алерты я делаю следующее:
    в разделе Alerts - Scripts у меня есть такой скрипт "close trigger by API v.2.1" выполнение которого закрывает текущий алерт через API.
    на выше описаный тригер я вешаю tag c названием autoclose и значением 24h
    в разделе Alerts - Trigger actions создаю action с названием Trigger auto close over 24h by tag AUTOCLOSE.
    Click image for larger version  Name:	image.png Views:	0 Size:	22.9 KB ID:	505676
    Click image for larger version  Name:	image.png Views:	0 Size:	34.8 KB ID:	505677
    таким образом через 24h такой алерт сам закроется. можно сделать пачку аналогичных triger action на 6h, 12h и т.д. Но мне хватает одного на 24

    Сам скрипт autoclose ниже ( для версии 6.4+, для более старших есть в интернете и тут на форуме. он чуть отличется )
    Click image for larger version  Name:	image.png Views:	0 Size:	30.2 KB ID:	505678

    Code:
    try {
        var req = new HttpRequest(),
            params = JSON.parse(value),
            eventid = params.eventid,
            token = params.token,
            url = params.url,
            body,
            resp;
    
        Zabbix.log(4, '[Closing problem] starts: eventid=' + eventid + '", url="' + url + '".');
    
        //Validation
        if (typeof eventid !== 'string' || eventid.trim() === '') {
            throw 'The eventid must be defined in macro "{EVENT.ID}".';
        }
    
        if (typeof token !== 'string' || token.trim() === '') {
            throw 'The token must be defined in macro "{$Z_API_TOKEN}".';
        }
    
        if (typeof url !== 'string' || !(url.startsWith('http://') || url.startsWith('https://'))) {
            throw 'The URL (starting with "http://" or "https://") must be defined in macro "{$Z_API_PHP}".';
        }
    
        if (typeof params.HTTPProxy === 'string' && params.HTTPProxy.trim() !== '') {
            req.SetProxy(params.HTTPProxy);
        }
    
        //Processing logic
        req.addHeader('Authorization: Bearer ' + token.trim());
        req.addHeader('Content-Type: application/json');
        body = {
            'jsonrpc': '2.0',
            'method': 'event.acknowledge',
            'params': {
                'eventids': eventid.trim(),
                'action': 1,
                'message': 'Problem auto-closed.'
            },
            'id': 1
        };
        resp = req.post(url.trim(),
            JSON.stringify(body)
        );
    
        if (req.getStatus() != 200) {
            throw 'Response code: ' + req.getStatus();
        }
    
        Zabbix.log(4, '[Closing problem] returned: ' + resp);
        resp = JSON.parse(resp);
        if ('error' in resp) {
            throw ('API error: ' + resp.error.message + '; ' + resp.error.data);
        }
    
    } catch (error) {
        Zabbix.log(3, '[Closing problem] cannot close event "' + eventid + '": ' + error);
        throw 'Cannot close event ' + eventid + ': ' + error;
    }
    
    return 'OK';
    Макросы лучше задать глобально в разделе Administartion - Macros тогда фичу с автозакрытием алерта по времени жизни можно использовать и в других триггерах
    {$Z_API_PHP} - URL https://вашзаббикс//api_jsonrpc.php
    {$Z_API_TOKEN} - токен для API. как его получить написано в документации чтоб не повторятся. лучше для API создать отдельного пользователя. но тут уже на ваш вкус.
    Last edited by teddy; 28-07-2025, 18:19.

    Comment

    • teddy
      Senior Member
      • Dec 2017
      • 234

      #2
      Все достаточно просто.
      1. делаете триггер в режиме Multiple
      2. делаете выражение восстановления на такой тригер - NONE
      3. разрешаете ручное закрытие.

      Что имеем? Срабатывает триггер на все входы. но висит "вечно", пока руками не закроешь. Не всегда удобно. Если придумаете на что реагировать чтоб закрыть - вписываем в
      условие закрытия. Я не придумал.

      Потому чтоб убрать "вечные" алерты я делаю следующее:
      в разделе Alerts - Scripts у меня есть такой скрипт "close trigger by API v.2.1" выполнение которого закрывает текущий алерт через API.
      на выше описаный тригер я вешаю tag c названием autoclose и значением 24h
      в разделе Alerts - Trigger actions создаю action с названием Trigger auto close over 24h by tag AUTOCLOSE.
      Click image for larger version  Name:	image.png Views:	0 Size:	22.9 KB ID:	505676
      Click image for larger version  Name:	image.png Views:	0 Size:	34.8 KB ID:	505677
      таким образом через 24h такой алерт сам закроется. можно сделать пачку аналогичных triger action на 6h, 12h и т.д. Но мне хватает одного на 24

      Сам скрипт autoclose ниже ( для версии 6.4+, для более старших есть в интернете и тут на форуме. он чуть отличется )
      Click image for larger version  Name:	image.png Views:	0 Size:	30.2 KB ID:	505678

      Code:
      try {
          var req = new HttpRequest(),
              params = JSON.parse(value),
              eventid = params.eventid,
              token = params.token,
              url = params.url,
              body,
              resp;
      
          Zabbix.log(4, '[Closing problem] starts: eventid=' + eventid + '", url="' + url + '".');
      
          //Validation
          if (typeof eventid !== 'string' || eventid.trim() === '') {
              throw 'The eventid must be defined in macro "{EVENT.ID}".';
          }
      
          if (typeof token !== 'string' || token.trim() === '') {
              throw 'The token must be defined in macro "{$Z_API_TOKEN}".';
          }
      
          if (typeof url !== 'string' || !(url.startsWith('http://') || url.startsWith('https://'))) {
              throw 'The URL (starting with "http://" or "https://") must be defined in macro "{$Z_API_PHP}".';
          }
      
          if (typeof params.HTTPProxy === 'string' && params.HTTPProxy.trim() !== '') {
              req.SetProxy(params.HTTPProxy);
          }
      
          //Processing logic
          req.addHeader('Authorization: Bearer ' + token.trim());
          req.addHeader('Content-Type: application/json');
          body = {
              'jsonrpc': '2.0',
              'method': 'event.acknowledge',
              'params': {
                  'eventids': eventid.trim(),
                  'action': 1,
                  'message': 'Problem auto-closed.'
              },
              'id': 1
          };
          resp = req.post(url.trim(),
              JSON.stringify(body)
          );
      
          if (req.getStatus() != 200) {
              throw 'Response code: ' + req.getStatus();
          }
      
          Zabbix.log(4, '[Closing problem] returned: ' + resp);
          resp = JSON.parse(resp);
          if ('error' in resp) {
              throw ('API error: ' + resp.error.message + '; ' + resp.error.data);
          }
      
      } catch (error) {
          Zabbix.log(3, '[Closing problem] cannot close event "' + eventid + '": ' + error);
          throw 'Cannot close event ' + eventid + ': ' + error;
      }
      
      return 'OK';
      Макросы лучше задать глобально в разделе Administartion - Macros тогда фичу с автозакрытием алерта по времени жизни можно использовать и в других триггерах
      {$Z_API_PHP} - URL https://вашзаббикс//api_jsonrpc.php
      {$Z_API_TOKEN} - токен для API. как его получить написано в документации чтоб не повторятся. лучше для API создать отдельного пользователя. но тут уже на ваш вкус.
      Last edited by teddy; 28-07-2025, 18:19.

      Comment

      • frofis
        Junior Member
        • Apr 2025
        • 17

        #3
        Приветствую, teddy!

        Спасибо ОГРОМНОЕ. Я попробую.
        Multiple я пробовал, но он реагирует не только на второе, третье событие, но даже если было одно событие по нескольку раз, или я что-то не понял.
        Last edited by frofis; 28-07-2025, 08:10.

        Comment

        • Semiadmin
          Senior Member
          • Oct 2014
          • 1625

          #4
          Если закрытием проблемы с входом пользователя является его выход, то можно применить Trigger-based event correlation. В доке есть пример с остановкой/запуском сервисов, аналогично можно сделать для пользователей.

          Comment

          • frofis
            Junior Member
            • Apr 2025
            • 17

            #5
            Спасибо, Semiadmin!

            Multiple реагирует на одно и то же событие по нескольку раз, это правильно?

            Comment

            • Semiadmin
              Senior Member
              • Oct 2014
              • 1625

              #6
              Если настроить триггер правильно, в режиме multiple он будет срабатывать на разные события, но не ждать завершения предыдущей проблемы, чтобы создать новую

              Comment

              • frofis
                Junior Member
                • Apr 2025
                • 17

                #7
                Спасибо, Semiadmin!
                Помогите, что я делаю не так?

                Данные
                Имя: Вход пользователя
                Тип: Zabbix агент (активный)
                Ключ: eventlog[Security,"Тип входа:\s*(2|10)",,,4624,,skip]
                Тип информации: Журнал (лог)
                Предобработка:
                Регулярное выражение (?s)Вход.*)Имя учетной записи.*)Домен(.*)User32(.*) \2
                все остальное по умолчанию

                Тригер
                Имя: Вход пользователя: {ITEM.LASTVALUE}
                Выражение: logseverity(/Template Windows Event Logs/eventlog[Security,"Тип входа:\s*(2|10)",,,4624,,skip])>1 and nodata(/Template Windows Event Logs/eventlog[Security,"Тип входа:\s*(2|10)",,,4624,,skip],12h)<>1
                все остальное по умолчанию

                Comment

                • Semiadmin
                  Senior Member
                  • Oct 2014
                  • 1625

                  #8
                  nodata не стоит использовать в multiple режиме, т.к. триггер будет пересчитываться не только при получении записи из лога, но и каждые полминуты, и каждый раз будет генериться проблема, пока не истекут эти 12 часов со времени получения последней записи

                  Comment

                  • frofis
                    Junior Member
                    • Apr 2025
                    • 17

                    #9
                    Спасибо, Semiadmin!

                    Убрал nodata
                    Установил Множественный
                    Все равно сворачивается в историю

                    Нужно еще что-то сделать?

                    Comment

                    • frofis
                      Junior Member
                      • Apr 2025
                      • 17

                      #10
                      Дошло
                      2. делаете выражение восстановления на такой тригер - NONE

                      Comment

                      • Semiadmin
                        Senior Member
                        • Oct 2014
                        • 1625

                        #11
                        попробовать сделать по образцу из доки, если подходит схема с закрытием проблемы по выходу юзера

                        Comment

                        • frofis
                          Junior Member
                          • Apr 2025
                          • 17

                          #12
                          Спасибо, Semiadmin!
                          Вроде получилось.
                          Возможно я сделаю как посоветовал teddy

                          Comment

                          • frofis
                            Junior Member
                            • Apr 2025
                            • 17

                            #13
                            teddy, спасибо!
                            Все заработало

                            Comment

                            Working...