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

Linux: как отправить новые строки в файлах журнала в удаленный системный журнал?

У нас есть несколько приложений, которые генерируют свои собственные файлы журнала в виде простого текста, которые я хотел бы переслать на удаленный сервер системного журнала для централизованного ведения журнала. У меня нет доступа к root на этих машинах я не могу перенастроить syslog для перенаправления вывода на удаленный компьютер.

Я нашел несколько решений в Интернете, но в основном это самодельные сценарии bash, и я ищу что-то более надежное, подходящее для реализации в потенциально крупносерийной производственной среде.

Предпочтительно что-то, разработанное с учетом небольших габаритов, фонового демона, который продолжает работать, может не отставать от большого количества строк и т. Д. - Какие решения доступны в настоящее время?

Вы уже отказались от «чужих сценариев bash», но это довольно распространенное решение - некоторые творческое использование logger команда может следить за файлом и отправлять его содержимое в другое место.
Лично я бы не стал этого делать в производственной среде.


Лучшим вариантом, который требует меньшего количества сценариев, является использование rsyslogd и модуль ввода текстового файла лайк yoonix упомянул - Это довольно приличное решение, хотя есть вероятность потери строк во время ротации файлов, и если вы используете систему Linux с rsyslog в качестве демона системного журнала не требуется много дополнительной работы.

syslog-ng также поддерживает источник ввода файла с функциональностью, аналогичной rsyslogс.


ИМХО Лучший Решение - хотя и требует модификации приложения, генерирующего эти журналы - заключается в прямом входе в системный журнал. Вы не хотите проходить через промежуточные шаги, файлы и т. Д. - syslog это SYStem LOGger, и вещи, которые пишут журналы на платформе Unix должен отправлять их в системный журнал.
К сожалению, реализация этого оставлена ​​в качестве упражнения для читателя (и разработчика приложения) и может оказаться невозможной, если ваши разработчики отсутствуют, ленивы или некомпетентны ...

Вы могли бы использовать logstash с файл ввод и системный журнал вывод.

Например, создайте конфигурацию с файлом (или файлами), который вы хотите отслеживать, и информацией о вашем сервере системного журнала.

файл-в-syslog.conf:

input { file { path => "/var/log/kern.log" } }
output {
    syslog {
        facility => "kernel"
        host => "syslog.example.com"
        port => 514
        severity => "informational"
    }
}

Запуск logstash с

java -jar logstash-1.2.2-flatjar.jar agent -f file-to-syslog.conf

Я взломал вместе tail.c и logger.c в единую, небольшую скомпилированную программу (двоичный файл), легкую, быструю и стабильную. Пока у него есть доступ для чтения к файлам журнала, он работает без прав root.

Я также внес несколько улучшений в собственный журнал и добавил новую (необязательную) возможность вставки текстовой строки в начало каждой строки журнала перед ее отправкой на сервер журнала. В результате получается программа, которую можно запускать отдельно, без необходимости использования каналов оболочки (т. Е. Не нужно tail logfile | logger). Он будет работать вечно, пока не будет явно убит или не обнаружит ошибку записи в сетевой сокет. Он даже продолжает работать, если файл журнала повернут или даже исчезнет (он просто продолжит поиск, чтобы увидеть, появляется ли файл снова).

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

На самом деле я закончил программу еще в декабре, но ждал, пока Yahoo получит авторские права и сделает ее доступной, что они и сделали. (Я написал это как часть моей работы в Yahoo).

Информация о программе filelogger и ссылка для скачивания:

Есть несколько способов решить эту проблему. Но само, очень Первое, что вам нужно сделать, это: переслать журналы, используя сам системный журнал.

Системный журнал (и многие заменители системного журнала) имеют встроенные средства для перенаправления журналов на другой сервер системного журнала по другому адресу. Вы можете легко сделать это, изменив файл конфигурации и добавив адрес для пересылки объекта. Например, добавив эту строку в:

*.*    @192.168.1.1

... переправил бы все на машину по адресу 192.168.1.1, на которой (надеюсь) запущена служба. Пример, который я привожу, относится к rsyslog, который является стандартным сервером системного журнала в Debian, хотя он должен работать для многих других. Обратитесь к документации по реализации системного журнала с помощью man syslog и посмотрите, что там написано о "пересылке".

Удаленный сервер системного журнала может быть любым. Есть даже такие продукты, как Splunk, которые успешно объединяют эти журналы в единое представление с веб-панелью, поиском, уведомлениями, управляемыми событиями, и т. д. и т. д. Вы можете увидеть больше здесь: http://www.splunk.com/ Если это не соответствует вашим потребностям, вы можете использовать что-нибудь еще. Есть даже серверы системного журнала, которые сбрасывают данные в базу данных SQL!

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


Изменить: Итак, я вернулся и перечитал вопрос и заметил несколько комментариев. Это звучит как:

  1. вы хотите объединить журналы приложений
  2. у вас нет доступа к корню
  3. ваше приложение (а) просто выгружает текст куда-нибудь
  4. ваше приложение (а) не знает, как писать в локальный системный журнал
  5. у вас нет контроля над исходным кодом вашего приложения

Итак, давайте обратимся к каждому последовательно:

  1. syslog предназначался для объединения журналов вместе. Вы можете использовать все, что захотите, но есть причина, по которой это существует уже давно. Он хорошо протестирован, отлажен, хорошо документирован, хорошо известен и для большинства платформ * nix почти повсеместно поддерживается в том или ином варианте.
  2. нам не нужен доступ к root настроить ведение журнала. Нам нужен только доступ к API системного журнала. root не является обязательным для записи в системный журнал; если бы это было так, то все те службы, которые отбрасывают привилегии, не смогли бы записывать диагностику в файлы журнала.
  3. Re: текстовые дампы, это нормально. однако вы должны иметь возможность использовать подоболочку для передачи вывода STDERR и STDOUT программе, которая вызывает API системного журнала. Это не ракетостроение, оно далеко не хрупкое и хорошо задокументировано. Фактически, это одна из причин того, что перенаправление вывода вообще существует. Простая команда, которую можно было бы поместить в один сценарий оболочки, была бы такой:

    (мое-приложение 2> & 1 | my-syslog-shunt) &

  4. если у вас есть возможность изменить исходный код вашего приложения, вы должны написать в него шунт, чтобы выгрузить текстовый вывод в syslog вместо обычного текстового файла. Это не должно быть слишком сложно; все, что вам нужно сделать, это взять строки, которые вы хотите вывести, и обернуть их вызовом. Тем не мение....

  5. у вас может вообще не быть доступа к исходному коду, поэтому вы не можете этого сделать. Это означает, что что-то вроде # 3 выше будет работать нормально.

Я отвечаю на свой вопрос.

swatch мог работать, но мне не удалось заставить модуль Perl Sys :: Syslog работать на хосте, а установленный на хосте / usr / bin / logger не поддерживает ведение журнала на удаленный сервер (util-linux-ng- 2.17.2).

Итак, первое, что я сделал, - это загрузил исходный код для util-linux-2.20.1, для которого программа logger поддерживает удаленное ведение журнала. При тестировании стало очевидно, что на количество символов, разрешенных в строке журнала, накладывается ограничение. Покопавшись в исходном коде, я обнаружил жестко заданный предел в 400 символов. (Если вы мне не верите, запустите «strings / usr / bin / logger | grep 400» в любой системе Linux).

Этот предел неприемлем для ведения журнала типа apache (включая nodejs), поэтому я изменил код и увеличил предел до 4096. Пока я был на нем, я также добавил новую опцию командной строки, которая позволяет вставлять необязательный текстовая строка в начале каждой строки журнала. Я сделал это, потому что журналы nodejs не включают имя хоста, как можно было бы увидеть в apache.

На этом этапе я мог запустить сценарий оболочки с «tail -F -n 0 [файл журнала] | ./modified_logger ....», и он сработал. Но у меня были некоторые опасения по поводу запуска этого из supervise (daemontools) или даже в фоновом режиме, потому что, если одна или другая сторона канала завершается, тогда существует риск завершения всего канала. У меня также были проблемы (хотя и непроверенные) по поводу производительности.

поэтому я решил объединить хвостовую функциональность с функциональностью логгера в один исполняемый двоичный файл, который позволит обойти необходимость использования каналов Unix или внешних программ. Я сделал это, взломав tail.c из gnu coreutils и включив то, что мне нужно, в модифицированную программу логгера.

Результатом является новый двоичный файл (размером 117 КБ), который я называю «filelogger», который постоянно отслеживает один или несколько файлов и записывает каждую новую строку в локальный или удаленный системный журнал через UDP или TCP. Работает как часы. Мне удалось провести небольшой тест, и он регистрирует около 17000 строк (1,8 МБ) примерно за 3 секунды в подсетях с vlan и парой физических переключателей между ними на удаленный сервер, на котором запущен syslog-ng.

чтобы запустить программу, вы делаете что-то вроде следующего (на переднем плане, в фоновом режиме или под контролем daemontools):

./filelogger -t 'доступ' -d -p local1.info -n [удаленный лог-хост] -u / tmp / ignored -a $ (имя хоста) / tmp / myfile1 / tmp / myfile2 ...

/ tmp / myfile1 и / tmp / myfile2 - это файлы, за которыми ведется мониторинг.

"-A" - это новая опция, которую я добавил. В этом случае я вставляю локальное имя хоста в начало каждой строки журнала.

Это решение было именно тем решением, которое я искал, когда задавал вопрос, и, как оказалось, не существовало, пока я не сделал его сам. :)