Назад | Перейти на главную страницу

Захват многострочного вывода grep по конвейеру в переменную

Я использую Zabbix zabbix_sender.sh скрипт для отправки трассировки стека исключений на мой удаленный сервер мониторинга Zabbix.

zabbix_sender.sh требует ключ и значение для любых данных, которые он отправляет. Он может читать данные из stdin, но это отменяет любую указанную ключевую переменную. Потому что мой stdin данные отформатированы не так, как ожидает Zabbix, мне нужно передать "значение" в качестве аргумента. Надеюсь, это дает некоторый контекст.

Я хочу получить многострочный результат из grep в переменную, сохраняя символы новой строки, чтобы я мог вызвать zabbix_sender.sh скрипт с этой переменной в качестве аргумента.

То, что я пробовал до сих пор, выглядит так:

tail -Fn0 /var/log/uwsgi.log | grep "Exception:" -A 100 | (read tback; /usr/local/zabbix/bin/zabbix_sender -z myzserver.com -s MyHostName -k uwsgi_traceback -o $tback)

Насколько я могу судить, это никогда не вызывает zabbix_sender.sh.

Для проверки я пробовал использовать эту команду, которая, похоже, тоже не работает:

tail -Fn0 /var/log/uwsgi.log | grep "Exception:" -A 100 | (read errorlines; echo "$errorlines" > /tmp/errorlines.txt)

В /tmp/errorlines.txt файл никогда не создается.

Как я могу запечатлеть grepстроки вывода в переменную, чтобы я мог вызвать другой сценарий с этой переменной в качестве аргумента?

Вот мой подход.

  1. Используйте ключ типа "log" в zabbix для отслеживания шаблонов ошибок в файле журнала (здесь /var/log/uwsgi.log).
  2. вызвать удаленную команду zabbix, инициированную указанным выше 1. Эта удаленная команда извлекает строки, окружающие ошибку хвостом команды linux (1).

Преимущества такого подхода:

  1. Нет необходимости устанавливать и настраивать специальный скрипт на стороне агента и хоста (например, zabbix_sender.sh, описанный выше). Элемент типа 'log' в zabbix уже предназначен для такого рода целей.
  2. отсутствие сценария, подобного zabbix_sender.sh, на хосте агента означает, что нет дополнительного потребления ресурсов ЦП и памяти. Извлечение нескольких строк с ошибкой в ​​журнале происходит только при триггере.

Позвольте мне подробно объяснить, как настроить ниже:

  1. зарегистрируйте регулярное выражение в zabbix, выбрав Администрирование> Общие> Регулярные выражения> [Новое регулярное выражение], например «ошибка | сбой | фатальный». Предположим, что имя переменной - @uwsgi_error_pattern.
  2. зарегистрируйте элемент из Конфигурация> Хосты> строка [Целевой хост]> Элементы> [Создать элемент] со следующими атрибутами:
    • Описание: [любое имя]
    • Тип: Zabbix агент (активный)
    • Ключ: журнал [/var/log/uwsgi.log,@uwsgi_error_pattern]
    • Тип информации: Журнал
  3. зарегистрируйте 2-й элемент из Конфигурация> Хосты> Строка [Целевой хост]> Элементы> [Создать элемент] со следующими атрибутами, чтобы принять флаг извлеченного журнала, отправленный удаленной командой zabbix (упоминается позже):
    • Описание: [любое имя]
    • Тип: Zabbix траппер
    • Ключ: my_app.fetch_uwsgi_log
    • Тип информации: текст
  4. зарегистрируйте триггер из Конфигурация> Хосты> строка [Целевой хост]> Триггеры> [Создать триггер] со следующими атрибутами:
    • Имя: монитор журнала uwsgi на {HOSTNAME}
    • Выражение ({[Целевой хост]: log [/var/log/uwsgi.log,@uwsgi_error_pattern] .iregexp (@uwsgi_error_pattern)}) # 0 & ({[Целевой хост]: log [/var/log/uwsgi.log, @uwsgi_error_pattern] .nodata (300)}) = 0
  5. действие регистрации, которое удаленно выполняется для получения данных, окружающих строку ошибки файла журнала, следующим образом:
    • Имя: Получить последнюю ошибку журнала uwsgi
    • Действия Операции:
      • Тип операции: дистанционная команда
      • Удаленная команда: {HOSTNAME}: zabbix_sender -z [zabbix-server] -s {HOSTNAME} -k my_app.fetch_uwsgi_log -o "` tail -200 / var / log / uwsgi.log` "

ПРИМЕЧАНИЕ-1: имя ключа «my_app.fetch_uwsgi_log» на шаге выше является всего лишь примером. Мы можем определить любое уникальное имя для привязки zabbix_sender и элемента.

ПРИМЕЧАНИЕ-2: Вам может потребоваться AllowRoot = 1 в /etc/zabbix/zabbix_agentd.conf, чтобы разрешить zabbix-agent читать uwsgi.log.

Вы должны выключить разбиение слов в bash, например, очистив IFS:

export IFS=""
set NEWVAR=`your tail|grep expression`

Сейчас echo $NEWVAR есть символы новой строки.

Проблема в хвостовой части; поскольку он находится в непрерывном режиме, он никогда не выдаст что-нибудь для «чтения».

Это должно работать:

#!/bin/bash
echo "0" >/tmp/numberoflines
IFS=''
while [ 1 ]
do
    NUMBER=$(cat /tmp/numberoflines)
    LINES=$(wc -l < /var/log/uwsgi.log)
    DIFFERENCE=$(($LINES-$NUMBER))

    if [ $DIFFERENCE != 0 ]; then
            exception=$(tail -n $DIFFERENCE /var/log/uwsgi.log | grep "Exception:" -A 100)
           /zabbix/bin/zabbix_sender -z myzserver.com -s MyHostName -k uwsgi_traceback -o $tback) $exception;
    fi

sleep 5;
echo "$LINES" >/tmp/numberoflines
done