fabric源码解析3——日志系统

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/idsuf698987/article/details/75223986

fabric源码解析3——日志系统

这里所说的日志,是指程序运行过程中打印到终端或日志文件,记录程序运行过程的日志,而非涉及到fabric记录交易数据,账本数据一类的交易日志。其实日志系统机制对于源码研究可以忽略,且相对简单,但是一方面日志系统对于程序运行和调试必不可少,fabric如何形成这个日志系统可以学习学习,日志所打印的内容对阅读源码也是一种提示;另一方面不弄清楚这个日志,在阅读源码的过程中这些到处出现的打印日志总像围绕在源码上面的蚊子一样,闹心。

fabric的日志系统主要使用了第三方包go-logging,可在github.com/op/go-logging下载。很少一部分使用了go语言标准库中的log。在此基础上fabric自己封装出来了flogging,这个f,应该代表fabric吧,意思是说这是fabric的logging。代码集中在fabric/common/flogging目录下,供项目全局使用。

go-logging简介

简单点儿,logging其实就是封装了各种打印格式,包括消息层级上的,如DEBU、消息、注意、警告、错误,包括消息颜色上的,如消息是正常的绿色、错误则是醒目的红色。

基本用法如下:

//创建一个名字为examplename的日志对象log
var log = logging.MustGetLogger("examplename")
//创建一个日志输出格式对象format,也就是用什么格式输出
var format = logging.MustStringFormatter(
    `%{color}%{time:15:04:05.000} %{shortfunc} ▶ %{level:.4s} %{id:03x}%{color:reset} %{message}`,
)
//创建一个日志输出对象backend,也就是日志要打印到哪儿,在此是标准错误输出
backend := logging.NewLogBackend(os.Stderr, "", 0)
//将输出格式与输出对象绑定
backendFormatter := logging.NewBackendFormatter(backend, format)
//将绑定了格式的输出对象设置为日志的输出对象
//这样log打印每一句话都会按格式输出到backendFormatter所代表的对象里,在此即是标准错误输出
logging.SetBackend(backendFormatter)
//log打印依据Info信息
log.Info("info")
//log打印一句Error信息
log.Error("err")

更多详细的用法,请在go doc或库中自行学习。

flogging

在flogging目录下有两个文件,grpclogger.gologging.go

grpclogger.go用于设置grpc的日志,因为grpc默认只是用go语言的标准日志接口,因此将logging封装成go语言的标准日志形式的结构type grpclogger struct {logger *logging.Logger},然后通过initgrpclogger()生成对象供grpc使用,从而实现让grpc也使用flogging的效果。

logging.go文件中,自带一个名为flogging的日志记录者logger,同时规定了默认的日志格式,日志等级,用defaultFormatdefaultLevel常量表示。默认的输出端defaultOutput,并有用于存放所有fabric模块日志的级别映射modules map[string]string,从类型上看其存储的日志级别都字符串化了。最后还有一个存放每个peer启动之时的日志级别的映射peerStartModules map[string]string,由在每个peer启动完成之时调用SetPeerStartupModulesMap()初始化,并可通过调用RevertToPeerStartupLevels()恢复初始值。

init函数

init()函数通过调用Reset()函数等初始化了一系列默认值,如默认的输出端被设置成标准错处输出,默认输出级别这设置成info级别。最后调用initgrpclogger()初始化了grpc的日志对象。

MustGetLogger函数

在许多各级不同模块的源码中,在全局的开始处都有类似一句这样的调用,如在fabric/peer/main.go中:var logger = flogging.MustGetLogger("main")。这就是调用MustGetLogger函数生成一个名为指定了名字的日志对象,用以记录该模块的日志,并用安全的方式(用锁的方式)将该对象记录日志的级别备案到modules中。MustGetLogger函数内部依然用的是go-logging库的相应函数logging.MustGetLogger()生成的日志对象。

其他函数

在logging.go中的其他函数,基本都是了封装go-logging库函数,供fabric全局使用。如SetModuleLevel函数,调用来调用去,其实就是封装了go-logging库中的logging.SetLevel()函数,以达到符合fabric自己使用要求的目的,可谓万变不离其宗。

扫描二维码关注公众号,回复: 3801885 查看本文章

猜你喜欢

转载自blog.csdn.net/idsuf698987/article/details/75223986