node.js/expressでgraylogにsyslog送信する方法

はじめに

node/expressのログは一般的にはローカルのストレージに出力・保存しますが、サーバー台数が増えた場合は1サーバーに集約したい場合があります。

方法としてはrsyslogで集約する、fluentdで集約するなどの方法が有名ですが、私はアプリ側で実装してしまうことにしました。
UDPのsyslogで飛ばしてしまえばrsyslog用にファイルを出力する必要もありませんし、fluentdで解析させる負荷もかからなくなるためです。

方法案

log4js + log4js-syslog-appender

log4jsを使用しているので第一候補だったのですが動作せず。
アプリ側からパケットが出ていませんでした。
メンテナンスもされていないので廃案

log4js + log4js-fluent-appender

パケットは出ていたのですがgraylogの方での受信方法が分からず廃案

posix

使用しているとの記事があったのですがスマートじゃないなと思い廃案

winston + winston-graylog2

ロガーにwinston、送信系にgraylog形式(GELF)を使用する方式です
動作し、かなり良さそうに見えたのですが、送信されるパラメーターが少なくカスタマイズの方法が分からなかったため廃止
さすがにX-Fowarded-forくらいは欲しい。

winston-graylog2
A graylog2 transport for winston. Latest version: 2.1.2, last published: 6 years ago. Start using winston-graylog2 in yo...

パスと応答時間程度しか出力されない状態:

winston + winston-syslog

これを採用

winston から syslog 形式で送信する方式です。
今どきsyslogかーと思いつつも、期待するデータがログとして送信されたためこれを採用しました。

GitHub - namshi/winston-graylog2: Graylog2 transport for winston, a nodejs logging module
Graylog2 transport for winston, a nodejs logging module - namshi/winston-graylog2

コード

最終的には次のようになりました。
なお、ファイルログはjsonだと見づらいのでlog4jsを継続しています。

var winston = require('winston')
var expressWinston = require('express-winston');
require('winston-syslog').Syslog;

app.use(expressWinston.logger({
  transports: [
    //new winston.transports.Console(),
    new winston.transports.Syslog({
      host: "xxx.xxx.xxx.xxx",
      port: "3514",
    }),
  ],
  format: winston.format.combine(
    winston.format.json()
  ),
  meta: true,
  msg: "HTTP {{req.method}} {{req.url}}",
  expressFormat: true,
  ignoreRoute: function (req, res) { return false; }
}));

graylog側の設定

・System -> Inputs から Syslog UDP を追加


・Manage Extoractor にて、[Split & index] を選択。Split by に「]:」を設定

 ※ プロセス名などが出力されるため分割します。winston-syslog の仕様?

・Manage Extoractor にて[JSON] を選択。Sorce に「json」を設定
 前回splitしたものをjson解析します。

結果

これが

こう!

なります。

ひとこと

今回初めてgraylogの設定をやってみたのですが、想像以上にopensearch(elasticsearch)が重いです。
サーバー6台(秒間最大300ログくらい)で、Core3つのVPSのCPU使用率が26%に達しています。ログ飛ばしてるだけなのに。

   PID USER      PR  NI    VIRT    RES    SHR S  %CPU  %MEM     TIME+ COMMAND
 240712 opensea+  20   0 4964028 256492   9256 S  26.0  14.6  26:07.49 java         

rsyslogだとこんなに重くないため、驚きの負荷でした。
まだ処理可能な範囲ですが、そのうちスペックは変えないといけないかもしれません。
graylog(というよりOpenSearch)は意外と高コスト体質のようです。


同様のことをやっている方の記事がほとんど見つからなかったので書いてみました。
ご参考まで。

コメント

タイトルとURLをコピーしました