Вопрос или проблема
У меня есть сервер syslog, который принимает различные виды логов от нескольких клиентов, либо через выделенный порт, либо через UDP 514. При получении логи записываются в директорию, предназначенную для определенного типа лога, который определяется либо по выделенному порту, либо, если отправлено через UDP514, по исходному IP. Структура .conf файла следующая:
module(load="imudp")
template(name="logtype1" type="string" string="/path/to/var/log/logtype1/%fromhost%/%fromhost%.log")
template(name="logtype2" type="string" string="/path/to/var/log/logtype2/%fromhost%/%fromhost%.log")
#...другие аналогичные шаблоны для каждого типа лога
ruleset(name="logtype1") {
action(... dynafile="logtype1")
}
#...другие наборы правил для логов, отправленных через выделенный порт
ruleset(name="general") {
if ($fromhost-ip=='<IP1>') or ($fromhost-ip=='<IP2>')
then {
action(... dynafile="logtype2")
}
else if ($fromhost-ip=='<IP3>') or ($fromhost-ip=='<IP4>') or ($fromhost-ip=='<IP5>') or ($fromhost-ip=='<IP6>') #...или 20 других явных IP
then {
action(... dynafile="logtype3")
}
#...другие условия else-if
}
input(type="imudp" port="<DEDICATED_PORT>" ruleset="logtype1")
#...другие входы для выделенных портов
input(type="imudp" port="514" ruleset="general")
Есть ли лучший способ написать набор правил general
? Меня устраивает этот метод, если это несколько IP для типа лога, но я хочу избежать длинных условий else-if
, которые содержат 10 и более адресов. Например, реализовав логику “если fromhost-ip
соответствует любому значению из списка IP в firewall_srcip.txt
, записывать логи в путь, определенный в template3
“.
Ответ или решение
Для оптимизации правилет general
в вашем конфигурационном файле Rsyslog, вместо использования длинных цепочек условий else if
, вы можете использовать внешний файл с IP-адресами и оператор pmfromfile
для фильтрации. Это избавит вас от необходимости перечислять каждое IP-адрес в своем конфигурационном файле и упростит его поддержку.
Вот как можно реализовать ваш запрос:
-
Создайте файл с IP-адресами: Например, создайте файл
/etc/rsyslog/firewall_srcip.txt
, который будет содержать ваши IP-адреса. Строки могут выглядеть так:<IP1> <IP2> <IP3> ... <IPn>
-
Измените конфигурацию Rsyslog: Обновите ваш файл конфигурации Rsyslog, чтобы использовать этот файл с IP-адресами. Вы можете использовать модуль
pmfromfile
для создания списка фильтров.
Вот пример того, как можно настроить вашу конфигурацию:
# Загрузка необходимых модулей
module(load="imudp")
module(load="pmfromfile")
# Установка шаблонов для логов
template(name="logtype1" type="string" string="/path/to/var/log/logtype1/%fromhost%/%fromhost%.log")
template(name="logtype2" type="string" string="/path/to/var/log/logtype2/%fromhost%/%fromhost%.log")
template(name="logtype3" type="string" string="/path/to/var/log/logtype3/%fromhost%/%fromhost%.log")
# Загрузка IP-адресов из файла
property(name="fromhost-ip" condition="startswith" file="/etc/rsyslog/firewall_srcip.txt")
# Определение правилета для логов
ruleset(name="general") {
if ($fromhost-ip in $inputname) then {
action(type="omfile" file="/path/to/var/log/logtype3/%fromhost%/%fromhost%.log")
}
}
# Определение входных данных
input(type="imudp" port="514" ruleset="general")
Объяснение структуры конфигурации:
- Загрузка модуля
pmfromfile
: Это позволяет Rsyslog загружать данные из заданного файла – в нашем случае, списка IP-адресов. - Определение правила с помощью
$fromhost-ip in $inputname
: Это условие проверяет, соответствует ли текущий IP-адрес из источника какому-либо из адресов в файлеfirewall_srcip.txt
. - Запись журналов: Если условие выполнено, Rsyslog записывает журналы в определенное местоположение, используя нужный шаблон.
Примечания:
- Убедитесь, что файл
firewall_srcip.txt
имеет корректные права доступа для чтения, чтобы Rsyslog мог его считывать. - После изменения конфигурации не забудьте перезапустить Rsyslog для применения новых правил.
Таким образом, используя внешний файл для хранения IP-адресов, вы значительно упростите конфигурацию и сделаете ее более читаемой и легкой в поддержке.