logrus 模型比内置库复杂一点:
- 多了 formatter 结构,可以输出成多种结构化文本,如
JSONFormatter
。但是社区还是没有类似 Python 的格式字符串 formatter - 多了 hook 机制,可以按各消息不同的 loglevel 做逻辑,比如 ERROR 消息写
error.log
,DEBUG 消息写debug.log
- 可以带 context 输出,
logrus.WithFields()
- 可以判断 writer 是不是终端,如果是,给漂亮的带颜色输出;否则给普通输出
- 不提供 log rotation 能力
基本用法
参考 Github。
默认 context 参数
logger = logger.WithFields(logrus.Fields{"reqId": requestId, "command": c.Command.Name})
logger.Debugf("...")
logger.Fetalf("...")
多个输出端
rifflock/lfshook 提供了不同 log level 写不同文件的 hook,可以实现同时输出到文件和 stdout:
l := logrus.New()
ex, _ := os.Executable()
logFile := filepath.Dir(ex) + "/tsf-instance-agent.log"
writer := os.Open(logFile, os.O_CREATE|os.O_RDWR|os.O_APPEND, 0755)
l.Hooks.Add(lfshook.NewHook(
lfshook.WriterMap{
logrus.DebugLevel: writer,
},
&logrus.TextFormatter{},
))
l.Out = os.Stdout
logger = logrus.NewEntry(l)
l.Out = io.MultiWriter(writer, os.Stdout)
时,stdout 的带颜色输出就不生效了。logrus 没有原生的支持多 writer(也可能是 Go 内置的 log 库带了节奏)。看看这个 Github issue 有无新动态。
Log Rotation
用 lestrrat-go/file-rotatelogs 实现 log rotation。Log rotation 整合多端输出:
func SetupLogging() {
l := logrus.New()
l.SetLevel(logrus.DebugLevel)
ex, _ := os.Executable()
logFile := filepath.Dir(ex) + "/tsf-instance-agent.log"
writer, _ := rotatelogs.New(
logFile+".%Y%m%d",
rotatelogs.WithLinkName(logFile),
rotatelogs.WithMaxAge(time.Hour*24*30),
rotatelogs.WithRotationTime(time.Hour*24),
)
l.Hooks.Add(lfshook.NewHook(
lfshook.WriterMap{
logrus.DebugLevel: writer,
},
&logrus.TextFormatter{},
))
l.Out = os.Stdout
logger = logrus.NewEntry(l)
}