Ruby的stdlib Logger类可以安全地处理来自多个进程的编写器吗?

gru*_*ler 13 ruby logging

我正在研究需要进行日志记录的Ruby库.理想情况下,我希望多个工作进程能够登录到同一个文件.Logger从Ruby的标准库查看该类的源代码,我看到我们正在努力将写入从多个线程同步到日志中(正如在Ruby的stdlib Logger类线程安全的答案中所指出的那样).

当多个进程写入同一个日志文件时似乎存在类似的问题:取决于底层如何决定缓冲/拆分写入,每个日志消息可能无法保持其完整性.

那么,是否有一种方法可以使用标准Logger类来允许多个进程安全地登录到单个文件?如果没有,这通常如何在Ruby项目中完成?

这就是'安全'的意思:

  1. 每个日志行都是"原子" - 在下一条消息开始之前不间断地完整显示.例如,没什么[1/1/2013 00:00:00] (PID N) LOGMESS[1/1/2013 00:00:01] (PID M) LOGMESSAGE2\nAGE1
  2. 只要日志中出现的时间戳正确,就不需要跨进程严格排序日志消息.

更新:

我决定接受Tin Man的建议并编写测试,你可以在这里找到:https: //gist.github.com/4370423

简短版本:Winfield是正确的,至少在默认情况下使用Logger它可以安全地同时使用多个进程(对于上面给出的'safe'的定义).

关键因素似乎是如果给定一个文件路径(而不是已经打开的IO对象),Logger将以模式打开文件WRONLY|APPEND,并sync=true在其上设置.这两件事的组合(至少在我对Mac OS X的测试中)似乎可以安全地从多个进程同时记录.如果要传入已打开的IO对象,请确保以相同的方式创建它.

Win*_*eld 10

是的,您可以按照您描述的方式安全地将交错日志数据写入单个日志文件.

但是,最好为每个进程记录单独的日志,或者使用syslog等整合的日志记录系统.以下是几个原因:

  • 日志轮换/管理:当您必须协调信号多个进程时,截断/滚动日志文件很困难
  • 即使您注入PID以消除歧义,交错数据也可能会造成混淆

我目前正在使用单个日志文件管理每个系统的一些Resque工作者,并希望我为每个工作者分隔了一个日志文件.调试问题和正确管理日志很困难.