刚开始接触log4go项目时,没有注意到配置的重要性。
阅读了log4j、log4net、log4cpp、log4cplus的部分代码,发现它们都是以xml配置来驱动日志系统运行的。
多个源文件共享一个logger
最简单的方式是新建一个logger.go文件。
package main
import (
l4g "github.com/ccpaging/nxlog4go"
"github.com/ccpaging/nxlog4go/color"
"github.com/ccpaging/nxlog4go/file"
"github.com/ccpaging/nxlog4go/socket"
)
var log = l4g.GetLogger()
l4g.GetLogger()
从nxlog4go中取出预定义的logger。
或者用l4g.New(l4g.DEBUG)
新建全局 Logger。
var log = l4g.New(l4g.DEBUG)
初始化logger
可以在新建时直接链接配置函数。
var log = l4g.GetLogger().SetCaller(false).SetPattern("[%T] [%L] (%s) %M\n")
或者在init()中配置,如果不使用配置文件的话。
var log = l4g.GetLogger()
init() {
log = log.SetCaller(false).SetPattern("[%T] [%L] (%s) %M\n")
}
准备 xml 配置文件
准备xml配置文件。详见:config.xml
方便的办法是参照以上文件进行修改。
以 color term appender 为例
<logging>
<filter enabled="true">
<tag>color</tag>
<level>DEBUG</level>
<property name="pattern">[%D %T] [%L] (%s) %M%R</property>
</filter>
</logging>
enabled - filter attribute
Filter或称为 Appender的使能属性。enabled = true,打开。enabled = false,关闭。
tag
在log4go里用了两个字段——tag和type。在 nxlog4go 中合并成一个,标识 Appender 的类型。
在程序中,nxlog4go预装载(Preload)所有可能用到的 Appender,指定每个 Appender 的 tag。
然后装载配置文件,用 tag 字段匹配 Appender。
通过 Preload - tag - Load 机制,nxlog4go 可以用配置驱动未知的扩展 Appender。
level
日志过滤级别。nxlog4go仅处理大于等于 level 的日志。
property - attribute
每种 Appender 都有自己的 Options。
例如上例中设置 PatternLayout 的Pattern。“%R”表示回车换行,即程序中的“\n”。
通过参看源文件可以获得详细的信息。例如:filelog.go
func (fa *FileAppender) SetOption(name string, v interface{}) error {
fa.mu.Lock()
defer fa.mu.Unlock()
switch name {
case "filename":
...
case "flush":
...
case "maxbackup":
...
case "cycle":
...
case "clock", "delay0":
...
case "daily":
...
case "maxsize":
...
case "pattern", "format", "utc":
...
case "head":
...
case "foot":
...
default:
return l4g.ErrBadOption
}
return nil
}
装载 xml 配置驱动nxlog4go运行
func main() {
// 打开xml配置文件
fd, err := os.Open(filename)
if err != nil {
panic(fmt.Sprintf("Can't load xml config file: %s %v", filename, err))
}
// 读取xml内容到buf
buf, err := ioutil.ReadAll(fd)
if err != nil {
fmt.Fprintf(os.Stderr, "Could not read %q: %s\n", filename, err)
os.Exit(1)
}
// 关闭配置文件
fd.Close()
// 新建logger config, 具体结构详见filters.go, appender.go
xc := new(l4g.LoggerConfig)
if err := xml.Unmarshal(buf, xc); err != nil {
fmt.Fprintf(os.Stderr, "Could not parse XML configuration. %s\n", err)
os.Exit(1)
}
// 新建filters
fs := l4g.NewFilters()
// 预装载所有可能用到的 Appender
fs.Preload("color", colorlog.NewAppender())
fs.Preload("file", filelog.NewAppender("_test.log", 0))
fs.Preload("socket", socketlog.NewAppender("udp", "127.0.0.1:12124"))
// 预装载 xml 格式日志文件
xa := filelog.NewAppender("_test.log", 0)
xa.SetOption("head","<log created=\"%D %T\">%R")
xa.SetOption("pattern",
` <record level="%L">
<timestamp>%D %T</timestamp>
<source>%S</source>
<message>%M</message>
</record>%R`)
xa.SetOption("foot", "</log>%R")
fs.Preload("xml", xa)
fmt.Println(len(*fs), "appenders pre-installed")
// 装载配置并自动删除未用的appender
fs.LoadConfiguration(xc.Filters)
if filt, isExist := (*fs)["color"]; isExist {
// 已有 color term appender. 关闭缺省的 writer
log.SetOutput(nil)
}
log.SetFilters(fs)
fmt.Println(len(*fs), "appenders configured ok")
// And now we're ready!
log.Finest("This will only go to those of you really cool UDP kids! If you change enabled=true.")
log.Debug("Oh no! %d + %d = %d!", 2, 2, 2+2)
log.Trace("Oh no! %d + %d = %d!", 2, 2, 2+2)
log.Info("About that time, eh chaps?")
log.Shutdown()
// 或者分步执行
// 卸载filters
// log.SetFilters(nil)
// 关闭全部filters
// fs.Close()
}
xml 格式的日志文件
附带实现了xml格式的日志文件。简单的设置 Head, Foot, 和PatternLayout就可以。例如:
xa := filelog.NewAppender("_test.log", 0)
xa.SetOption("head","<log created=\"%D %T\">%R")
xa.SetOption("pattern",
` <record level="%L">
<timestamp>%D %T</timestamp>
<source>%S</source>
<message>%M</message>
</record>%R`)
xa.SetOption("foot", "</log>%R")
生成的日志文件内容如下:
<log created="2018/03/26 13:50:25">
<record level="TRAC">
<timestamp>2018/03/26 13:50:25</timestamp>
<source>f:/go/src/github.com/ccpaging/nxlog4go/examples/xmlconfig.go</source>
<message>Oh no! 2 + 2 = 4!</message>
</record>
<record level="INFO">
<timestamp>2018/03/26 13:50:25</timestamp>
<source>f:/go/src/github.com/ccpaging/nxlog4go/examples/xmlconfig.go</source>
<message>About that time, eh chaps?</message>
</record>
- 只有滚动日志文件时才会写入 Foot