Централизованный мониторинг дисковых логов с rsyslog и Graylog: настройка, фильтрация и оповещения | AdminWiki

Централизованный мониторинг дисковых логов с rsyslog и Graylog: настройка, фильтрация и оповещения

24 июля 2026 10 мин. чтения

Проверять /var/log/messages или вывод journalctl на каждом сервере вручную - это потеря времени и прямой путь пропустить критическую ошибку диска. Когда серверов больше трёх, администратор физически не способен отследить все предупреждения о сбоях ввода-вывода, росте SMART-ошибок или заполнении раздела. Централизованный сбор логов решает эту проблему: все сообщения о состоянии дисков стекаются в единую панель, где автоматические правила мгновенно оповещают о проблеме через Telegram или email.

В этом руководстве мы построим систему мониторинга дисковых событий на базе rsyslog и Graylog. Настроим фильтрацию сообщений с тегами kernel и disk прямо на источнике, передадим логи в структурированном формате GELF в Graylog, развернутый в Docker, и создадим алерты для немедленной реакции на инциденты. Все конфигурации проверены на практике и готовы к адаптации под вашу среду.

Решение подходит для инфраструктур любого масштаба: от трёх физических хостов до кластеров с десятками нод. Если вы уже используете Docker для изоляции сервисов, логично углубиться в тему управления логами контейнеров - в нашем руководстве по логированию в Docker разобраны драйверы, ротация и интеграция с внешними системами.

Зачем нужен централизованный мониторинг дисковых логов

Типичная ситуация: у вас пять серверов, на каждом крутятся базы данных, веб-приложения, очереди. На одном из них контроллер диска начинает сыпать ошибки, но приложение пока работает. Вы узнаете об этом, когда раздел /var заполнится логами, или когда приложение упадет из-за невозможности записи. Ручной мониторинг не масштабируется.

Централизованная система меняет подход. Вместо реактивного просмотра логов после сбоя вы получаете проактивный инструмент. Graylog агрегирует сообщения со всех источников, индексирует их и позволяет строить поисковые запросы за секунды. Правила алертинга срабатывают автоматически при появлении ключевых фраз: I/O error, disk full, filesystem remounted read-only.

Экономия времени - измеримый результат. Системный администратор, обслуживающий 10 серверов, тратит на проверку логов минимум 15-20 минут в день. За месяц это более 7 часов. Автоматизация через связку rsyslog и Graylog сокращает эти затраты до нуля: система сама фильтрует шум и оповещает только о значимых событиях.

Архитектура решения: rsyslog, Graylog и Docker

Компоненты системы работают в четкой связке. На каждом сервере-источнике работает rsyslog - стандартный демон логирования в Linux. Он читает сообщения ядра через /proc/kmsg или journald, фильтрует их по заданным правилам и отправляет на центральный узел. Фильтрация происходит на стороне клиента: это снижает сетевой трафик и нагрузку на Graylog.

Graylog принимает логи через input GELF (Graylog Extended Log Format). GELF - это JSON-структура с обязательными полями version, host, short_message и timestamp. В отличие от сырого syslog-сообщения, GELF сохраняет структуру, что упрощает парсинг и поиск. Graylog индексирует каждое поле, позволяя строить сложные запросы вида facility:kern AND sda AND level:3.

Docker изолирует Graylog и его зависимости - MongoDB и Elasticsearch. Это упрощает развертывание и обновление: весь стек поднимается одной командой docker-compose up -d. Контейнеризация также решает проблему конфликта версий Java и библиотек, которая часто возникает при установке Graylog на голую ОС.

Для тех, кто строит комплексную систему наблюдаемости, будет полезен материал по маршрутизации логов и метрик в DevOps - там разобран полный конвейер телеметрии от Fluentd и Prometheus до Grafana.

Установка и настройка Graylog в Docker

Для развертывания Graylog подготовьте хост с Docker и Docker Compose. Минимальные требования: 4 ГБ ОЗУ, 2 ядра CPU, 20 ГБ дискового пространства. В продакшене рекомендуется 8 ГБ ОЗУ и SSD-накопитель для Elasticsearch.

Создайте файл docker-compose.yml:

version: '3.8'
services:
  mongodb:
    image: mongo:6.0
    volumes:
      - mongo_data:/data/db
    restart: unless-stopped

  elasticsearch:
    image: docker.elastic.co/elasticsearch/elasticsearch:7.17.18
    environment:
      - discovery.type=single-node
      - ES_JAVA_OPTS=-Xms1g -Xmx1g
      - xpack.security.enabled=false
    volumes:
      - es_data:/usr/share/elasticsearch/data
    restart: unless-stopped

  graylog:
    image: graylog/graylog:5.2
    environment:
      GRAYLOG_PASSWORD_SECRET: your-secret-key-min-16-chars
      GRAYLOG_ROOT_PASSWORD_SHA2: sha256-hash-of-your-password
      GRAYLOG_HTTP_EXTERNAL_URI: http://your-server-ip:9000/
      GRAYLOG_ELASTICSEARCH_HOSTS: http://elasticsearch:9200
      GRAYLOG_MONGODB_URI: mongodb://mongodb:27017/graylog
    ports:
      - "9000:9000"
      - "12201:12201/udp"
      - "1514:1514/tcp"
    volumes:
      - graylog_data:/usr/share/graylog/data
    depends_on:
      - mongodb
      - elasticsearch
    restart: unless-stopped

volumes:
  mongo_data:
  es_data:
  graylog_data:

Сгенерируйте GRAYLOG_PASSWORD_SECRET командой pwgen -N 1 -s 96 или openssl rand -hex 48. Для получения GRAYLOG_ROOT_PASSWORD_SHA2 выполните echo -n "your-password" | sha256sum. Запустите стек: docker-compose up -d. Веб-интерфейс станет доступен на порту 9000 через 30-60 секунд.

Создание GELF input для приема логов

GELF input - это точка входа для структурированных логов от rsyslog. В веб-интерфейсе Graylog перейдите в System → Inputs. В выпадающем списке выберите GELF UDP и нажмите Launch new input.

Заполните поля:

  • Node: оставьте автоматически выбранный узел.
  • Title: укажите понятное имя, например «Disk logs from rsyslog».
  • Bind address: 0.0.0.0 для приема со всех интерфейсов.
  • Port: 12201 - стандартный порт GELF UDP.

Нажмите Save. Input появится в списке с пометкой RUNNING. Graylog готов принимать сообщения. Порт 12201 UDP уже проброшен в docker-compose.yml, дополнительных действий с файрволом на хосте не требуется, если вы не ограничивали трафик правилами iptables.

Настройка rsyslog на серверах-источниках

Rsyslog установлен по умолчанию в большинстве дистрибутивов Linux. Проверьте версию: rsyslogd -v. Для работы с GELF и расширенной фильтрацией требуется версия 8.x или выше. В CentOS 7 может потребоваться обновление из репозитория rsyslog официального сайта.

Конфигурацию разместим в отдельном файле /etc/rsyslog.d/30-disk-monitoring.conf. Такой подход изолирует наши правила от основного конфига и упрощает управление.

Фильтрация сообщений по тегам kernel и disk

Задача фильтра - отобрать сообщения ядра, связанные с дисковыми операциями, и отсечь системный шум. Ядро Linux генерирует тысячи сообщений в час: от подключения USB-устройств до сетевых событий. Нам нужны только те, что касаются блочных устройств, файловых систем и контроллеров хранения.

Базовый фильтр на RainerScript:

if ($syslogfacility-text == "kern") and (
    $msg contains "sda" or
    $msg contains "sdb" or
    $msg contains "sd" or
    $msg contains "nvme" or
    $msg contains "hd" or
    $msg contains "I/O error" or
    $msg contains "disk full" or
    $msg contains "No space left" or
    $msg contains "filesystem" or
    $msg contains "remount" or
    $msg contains "READ FPDMA QUEUED" or
    $msg contains "Buffer I/O error" or
    $msg contains "EXT4-fs error" or
    $msg contains "XFS" or
    $msg contains "md" or
    $msg contains "raid"
) then {
    action(type="omfwd" target="graylog-server-ip" port="12201" protocol="udp" template="gelf_template")
    stop
}

Разберем ключевые элементы. Условие $syslogfacility-text == "kern" отбирает сообщения от ядра. Список проверок $msg contains захватывает типичные паттерны дисковых проблем: имена устройств (sda, nvme0n1), ошибки ввода-вывода, заполнение раздела, проблемы файловых систем ext4 и XFS, события программного RAID. Конструкция stop предотвращает дальнейшую обработку сообщения другими правилами.

Для расширенной фильтрации можно использовать регулярные выражения. Пример отбора сообщений о конкретном разделе:

if ($syslogfacility-text == "kern") and (
    $msg regex "sd[a-z][0-9]" or
    $msg regex "nvme[0-9]n[0-9]p[0-9]"
) then { ... }

Этот фильтр отловит сообщения о конкретных партициях: sda1, sdb3, nvme0n1p2. Полезно, когда нужно мониторить только разделы с данными, исключая системные.

Отправка логов в формате GELF

GELF-шаблон преобразует сырое syslog-сообщение в JSON, который Graylog распарсит без дополнительных экстракторов. Определите шаблон в том же файле /etc/rsyslog.d/30-disk-monitoring.conf перед блоком фильтрации:

template(name="gelf_template" type="list") {
    constant(value="{ \"version\": \"1.1\", ")
    constant(value="\"host\": \"")
    property(name="hostname")
    constant(value="\", \"short_message\": \"")
    property(name="msg" format="json")
    constant(value="\", \"timestamp\": ")
    property(name="timereported" dateFormat="rfc3339" format="json")
    constant(value=", \"facility\": \"")
    property(name="syslogfacility-text")
    constant(value="\", \"severity\": ")
    property(name="syslogseverity")
    constant(value=", \"_tag\": \"")
    property(name="syslogtag" format="json")
    constant(value="\" }\n")
}

Шаблон формирует JSON с обязательными полями GELF: version (строка «1.1»), host (имя сервера-источника), short_message (текст лога), timestamp (время в формате RFC 3339). Дополнительные поля с префиксом подчеркивания - _tag, facility, severity - становятся кастомными полями в Graylog и доступны для поиска.

Финальный конфигурационный файл целиком:

module(load="omfwd")

template(name="gelf_template" type="list") {
    constant(value="{ \"version\": \"1.1\", ")
    constant(value="\"host\": \"")
    property(name="hostname")
    constant(value="\", \"short_message\": \"")
    property(name="msg" format="json")
    constant(value="\", \"timestamp\": ")
    property(name="timereported" dateFormat="rfc3339" format="json")
    constant(value=", \"facility\": \"")
    property(name="syslogfacility-text")
    constant(value="\", \"severity\": ")
    property(name="syslogseverity")
    constant(value=", \"_tag\": \"")
    property(name="syslogtag" format="json")
    constant(value="\" }\n")
}

if ($syslogfacility-text == "kern") and (
    $msg contains "sda" or
    $msg contains "sdb" or
    $msg contains "sd" or
    $msg contains "nvme" or
    $msg contains "I/O error" or
    $msg contains "disk full" or
    $msg contains "No space left" or
    $msg contains "filesystem" or
    $msg contains "remount" or
    $msg contains "Buffer I/O error" or
    $msg contains "EXT4-fs error"
) then {
    action(type="omfwd" target="10.0.1.100" port="12201" protocol="udp" template="gelf_template")
    stop
}

Замените 10.0.1.100 на IP-адрес вашего Graylog-сервера. Примените конфигурацию: systemctl restart rsyslog. Проверьте статус: systemctl status rsyslog. Ошибки в конфигурации отобразятся в выводе команды.

Создание алертов и оповещений в Graylog

Система алертов Graylog строится на двух сущностях: Event Definitions (условия срабатывания) и Notifications (каналы доставки). Event Definition описывает поисковый запрос и временное окно, Notification определяет, куда отправить оповещение.

Перейдите в Alerts → Event Definitions и нажмите Create event definition. Заполните поля:

  • Title: «Disk I/O Error Detected»
  • Description: «Срабатывает при появлении ошибок ввода-вывода диска»
  • Priority: High

В секции Condition задайте поисковый запрос: short_message:"I/O error" OR short_message:"Buffer I/O error". Укажите поток, в который попадают ваши логи (по умолчанию - All messages). Временное окно: 5 минут, срабатывание при появлении хотя бы одного сообщения.

Создайте аналогичные Event Definitions для других критических событий:

  • Disk Space Critical: запрос short_message:"No space left" OR short_message:"disk full"
  • Filesystem Remounted Read-Only: запрос short_message:"remount" AND short_message:"read-only"
  • RAID Degraded: запрос short_message:"md" AND short_message:"degraded"

Интеграция с Telegram

Создайте бота через @BotFather в Telegram. Получите токен вида 123456:ABC-DEF1234ghikl-zyx57W2v1u123ew11. Добавьте бота в целевой чат или начните с ним диалог. Чтобы узнать chat_id, отправьте боту сообщение и выполните запрос: curl -s "https://api.telegram.org/bot/getUpdates". В ответе найдите "chat":{"id":-123456789}.

В Graylog перейдите в Alerts → Notifications, нажмите Create Notification. Выберите тип HTTP Notification. URL: https://api.telegram.org/bot/sendMessage. Метод: POST. Тело запроса в формате JSON:

{
  "chat_id": "-123456789",
  "text": "[${event_definition_title}]\n\nMessage: ${event.message}\nSource: ${source}\nTimestamp: ${event.timestamp}",
  "parse_mode": "HTML"
}

Graylog подставляет переменные ${event_definition_title}, ${event.message} и другие при отправке. Протестируйте уведомление кнопкой Test.

Интеграция с email

Email остается резервным каналом, который не зависит от доступности мессенджеров. Настройте SMTP в System → Configurations: укажите адрес сервера, порт (587 для TLS), логин и пароль. Для Яндекс.Почты используйте smtp.yandex.ru:587, для Gmail - smtp.gmail.com:587 с паролем приложения.

Создайте Notification типа Email Notification. Укажите получателей через запятую, тему письма: Disk Alert: ${event_definition_title} on ${source}. В теле письма продублируйте ключевую информацию: хост, сообщение, время.

Привяжите Notifications к Event Definitions в секции Notifications каждого определения события. Один Event Definition может отправлять оповещения в несколько каналов одновременно.

Проверка и отладка системы мониторинга

Сгенерируйте тестовое сообщение на сервере-источнике: logger -p kern.err "TEST: I/O error on sda5". Утилита logger отправляет сообщение в syslog с указанным facility и severity. Через несколько секунд сообщение должно появиться в Graylog в поиске по запросу short_message:"TEST: I/O error".

Если сообщение не пришло, проверьте цепочку передачи:

  1. Локальный лог rsyslog: tail -f /var/log/syslog | grep TEST. Сообщение должно быть видно.
  2. Сетевой трафик: tcpdump -i any udp port 12201 -A на сервере-источнике. Вы увидите уходящие UDP-пакеты с JSON.
  3. Файрвол на Graylog-сервере: iptables -L -n | grep 12201. Порт должен быть открыт.
  4. Логи Graylog: docker logs graylog_graylog_1. Ошибки парсинга GELF или проблемы с Elasticsearch отобразятся здесь.

Типичная ошибка - неверный формат JSON в шаблоне. Проверьте валидность: скопируйте отправляемый JSON и прогоните через jq или онлайн-валидатор. Лишняя запятая или незакрытая кавычка ломают парсинг.

Другая частая проблема - расхождение версий GELF. Graylog ожидает строку "version":"1.1". Если в шаблоне указано число 1.1 без кавычек, сообщение будет отброшено.

Обеспечение отказоустойчивости и советы по эксплуатации

В продакшене Graylog может быть недоступен: перезагрузка, сбой сети, высокая нагрузка. Rsyslog должен буферизовать сообщения, а не терять их. Добавьте параметры очереди в конфигурацию действия:

action(type="omfwd" target="10.0.1.100" port="12201" protocol="udp" template="gelf_template"
    queue.type="LinkedList"
    queue.size="10000"
    queue.filename="disk-log-queue"
    queue.maxdiskspace="500m"
    queue.saveonshutdown="on"
    action.resumeRetryCount="-1"
    action.resumeInterval="10"
)

Эти параметры создают очередь в оперативной памяти (LinkedList) с сохранением на диск при заполнении 500 МБ. При недоступности Graylog rsyslog будет повторять попытки бесконечно (resumeRetryCount="-1") с интервалом 10 секунд. После восстановления связи все накопленные сообщения уйдут в Graylog.

Мониторьте сам Graylog. Встроенный health check доступен по адресу http://graylog-server:9000/api/system/lbstatus. Он возвращает ALIVE или DEAD в зависимости от состояния Elasticsearch и MongoDB. Настройте проверку этого эндпоинта в вашей системе мониторинга.

Регулярно обновляйте Docker-образы: docker-compose pull && docker-compose up -d. Перед обновлением делайте бэкап томов MongoDB и Elasticsearch. Управляйте дисковым пространством Elasticsearch через политики ротации индексов: в Graylog перейдите в System → Indices, выберите индекс-сет и настройте максимальное количество индексов или срок хранения в днях. Для дисковой телеметрии обычно достаточно 30 дней хранения.

Построенная система интегрируется в общий конвейер наблюдаемости. Если вы планируете расширить мониторинг на метрики и алертинг по аномалиям, обратитесь к нашему руководству по мониторингу и алертингу на основе логов - там разобраны готовые конфигурации Watcher и LogQL для Elasticsearch и Grafana Loki.

Поделиться:
Сохранить гайд? В закладки браузера