如何让 svlogd 通过 UDP 发送日志

如何让 svlogd 通过 UDP 发送日志

我目前正在使用runit + svlogd用于监督某些应用程序,但是当部署到多台机器时,我需要将日志集中/统一到一个地方以简化事情,否则登录到每台机器会使事情变得非常复杂。

而不是通过 syslog 发送所有主机日志,例如:

*.* remote.log.host

我想只发送与应用程序相关的日志,理论上 svlogd 可以做到这一点,从文档

ua.b.c.d[:port]
    tells svlogd to transmit the first len characters of selected log messages to the IP address a.b.c.d, port number port. If port isn’t set, the default port for syslog is used (514). len can be set through the -l option, see below. If svlogd has trouble sending udp packets, it writes error messages to the log directory. Attention: logging through udp is unreliable, and should be used in private networks only.
Ua.b.c.d[:port]
    is the same as the u line above, but the log messages are no longer written to the log directory, but transmitted through udp only. Error messages from svlogd concerning sending udp packages still go to the log directory.

我的配置文件的内容 /service/my-service/log/main/config

u127.0.0.1:5514 

或者

U127.0.0.1:5514

为了测试我创建了一个非常基本的UDP 服务器/客户端,但由于未知原因svlogd没有发送日志,我也尝试netcat使用这个:

nc -ul 5514

我为此使用的日志运行脚本/service/my-service/log/run

#!/bin/sh

exec svlogd -tt ./main

我收到的唯一错误消息是:

warning: failure sending through udp: 

我一直在使用的一个解决方法是在日志运行脚本中调用logger,例如:

#!/bin/sh

exec chpst -u nobody logger -i -h remote.host.tld -P 42060 -t my-app

但是使用这种方法,我失去了 svlogd 的所有优势,除了sv status .始终开启/关闭(1,0),因为记录器不像守护进程那样运行。

最后,我想继续获取来自 svlogd 的日志,但可以选择工作ua.b.c.d[:port]

更新:执行 ktrace 后我得到以下结果:

  4909 svlogd   CALL  socket(PF_INET,SOCK_DGRAM,IPPROTO_IP)
  4909 svlogd   RET   socket 7
  4909 svlogd   CALL  fcntl(0x7,F_GETFL,0)
  4909 svlogd   RET   fcntl 2
  4909 svlogd   CALL  fcntl(0x7,F_SETFL,0x6<O_RDWR|O_NONBLOCK>)
  4909 svlogd   RET   fcntl 0
  4909 svlogd   CALL  sendto(0x7,0x609580,0x3c,0,0x609c3c,0x10)
  4909 svlogd   STRU  struct sockaddr { AF_UNSPEC, unknown address family }
  4909 svlogd   RET   sendto -1 errno 47 Address family not supported by protocol family
  4909 svlogd   CALL  write(0x6,0x609760,0x62)
  4909 svlogd   GIO   fd 6 wrote 98 bytes
       "warning: failure sending through udp:

STRU struct sockaddr { AF_UNSPEC, unknown address family }

有任何想法吗 ?

答案1

添加ld->udpaddr.sin_family =AF_INET;svlogd.c

http://skarnet.org/cgi-bin/archive.cgi?2:mss:1163:201602:gpiglpbjdemlioaeabbn

FreeBSD补丁: https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=207747

修补:

--- src/svlogd.c.orig   2016-03-06 13:48:35 UTC
+++ src/svlogd.c
@@ -430,6 +430,7 @@ unsigned int logdir_open(struct logdir *
   ld->name =(char*)fn;
   ld->ppid =0;
   ld->match ='+';
+  ld->udpaddr.sin_family =AF_INET;
   ld->udpaddr.sin_port =0;
   ld->udponly =0;
   while (! stralloc_copys(&ld->prefix, "")) pause_nomem();

更新:作为解决此问题的替代方案,目前使用https://immortal.run

相关内容