glog 日志库简介与测试【GO 常用的库】

〇、前言

golang/glog 是 C++ 版本 google/glog 的 Go 版本实现,基本实现了原生 glog 的日志格式。

在 Kuberntes 中,glog 是默认日志库。因此需要详细了解下。下面列举下 glog 的特点:

  • 高效性:glog 采用了异步写入日志的方式,这意味着日志记录操作不会阻塞主程序的执行。它还使用了缓冲区来收集日志消息,并在后台线程中将它们写入磁盘。这种异步写入机制可以显著提高应用程序的性能。
  • 灵活配置:glog 允许您通过命令行参数或配置文件来自定义日志输出的行为。可以指定要记录的日志级别、日志文件的路径、是否同时输出到标准错误流等。这使得 glog 非常适合于不同环境和需求的应用程序。
  • 日志级别控制:glog 支持不同的日志级别,包括 INFO、WARNING、ERROR、FATAL 等。可以根据需要,选择要记录的日志级别,以便及时发现关键的日志信息。
  • 日志格式化:glog 提供了丰富的日志格式化选项,允许您按照自己的喜好定义日志的输出格式。您可以指定时间戳、源代码位置、日志级别等信息的显示方式,以及自定义的文本和变量的输出。
  • 日志回滚:glog 支持日志文件的自动回滚功能,可以根据文件大小或日期来切分日志文件。这样可以避免单个日志文件过大导致难以管理和分析。
  • 跨平台支持:glog 是一个跨平台的日志库,可以在不同的操作系统上使用。它提供了对 Unix、Linux 和 Windows 等主流操作系统的支持。

强大功能且简单易用的 glog 日志库,为 GO 语言开发者提供了一种高效、灵活和可定制的日志记录解决方案。无论是小型项目还是大规模应用程序,glog 都能满足日常的日志需求,也能协助开发者更好地理解和调试代码。

glog 的基本实现逻辑就是,在 buffer 中写入格式化的内容并定期刷入文件中。

一、glog 详细介绍

1.1 日志级别与测试

glog 将日志级别分为 4 种,分别是:

  • INFO:一般日志,可用于记录程序运行状态;
  • WARNING:警告日志,记录潜在的问题或错误;
  • ERROR:错误日志,记录程序运行中一些可恢复的错误,可能导致程序功能受限或出现异常情况,但是不会导致系统崩溃;
  • FATAL:严重错误日志,程序遇到一个不可恢复的错误,在打印完日志后程序将会自动退出(os.Exit()

开始测试之前,准备工作:

复制代码
// 1.创建文件夹和文件:./src/glog/main.go
// 2.初始化和整理当前模块(添加或删除)
go mod init
go mod tidy
// 3.拉取必要的库 glog
go get github.com/golang/glog

如下为 main.go 文件中的代码:

复制代码
package main

import (
	"flag"

	"github.com/golang/glog"
)

func main() {
    // 用于解析命令行中 - 横线后边的参数和值,如下示例中的:-log_dir=log -alsologtostderr
    // go run main.go -log_dir=log -alsologtostderr
	flag.Parse()
    // defer() 退出前执行,清空缓存区,将日志写入文件
	defer glog.Flush()

	glog.Info("This is info message")
	glog.Infof("This is info message: %v", 12345)
	glog.InfoDepth(1, "This is info message", 12345)

	glog.Warning("This is warning message")
	glog.Warningf("This is warning message: %v", 12345)
	glog.WarningDepth(1, "This is warning message", 12345)

	glog.Error("This is error message")
	glog.Errorf("This is error message: %v", 12345)
	glog.ErrorDepth(1, "This is error message", 12345)

	glog.Fatal("This is fatal message")
	glog.Fatalf("This is fatal message: %v", 12345)
	glog.FatalDepth(1, "This is fatal message", 12345)
}

然后就是执行代码:

复制代码
// 1.创建 log 文件夹,必须先创建,否则无法以文件形式输出日志
mkdir log
// 2.将日志写入到 log 文件夹下
go run main.go -log_dir=log -alsologtostderr
// log_dir:用来指定日志文件夹名
// alsologtostderr:表示既在标准窗口输出也在文件中记录

记录日志的其他配置项简介:

  • -stderrthreshold=ERROR 达到或高于此严重程度的日志事件被记录为标准错误以及文件。
  • -log_backtrace_at="" 设置保存一般日志的文件和行号,例如:-log_backtrace_at = gopherflakes.go:234,默认堆栈跟踪都会写入 Info 日志,文件名的后缀可以不为 .go。
  • -v=0 在指定级别上启用 v 级日志记录。
  • -vmodule="" 通过数字指定文件的记录日志级别,可以同时配置多个文件的不同级别,用','分隔。例如:-vmodule=recordio=2,file=1,gfs*=3,最后一个代表所有以'gfs'开头的文件记录 3 级以下的日志。文件名的后缀必须为 .go,且可省略。

下面看下 Warning 级别的日志文件记录的内容:

1.2 vmodule 配置

vmodule 参数通过 -v=int 来自由配置输出级别,int 代表级别的数字,默认为 0。如下示例:

复制代码
package main

import (
	"flag"

	"github.com/golang/glog"
)

func main() {
	// 用于解析命令行中 - 横线后边的参数和值,如下示例中的:-log_dir=log -alsologtostderr
	// go run main.go -log_dir=log -alsologtostderr
	flag.Parse()
	// defer() 退出前执行,清空缓存区,将日志写入文件
	defer glog.Flush()

	glog.V(0).Info("LEVEL 0 message") // 使用日志级别 0
	glog.V(3).Info("LEVEL 3 message") // 使用日志级别 3
	glog.V(4).Info("LEVEL 4 message") // 使用日志级别 4
	glog.V(5).Info("LEVEL 5 message") // 使用日志级别 5
	glog.V(8).Info("LEVEL 8 message") // 使用日志级别 8
}

如下测试结果,当不加 -v 配置项时,只输出了默认级别为 0 的日志 ,当配置为 4 时,输出 <=4 级别的日志:

1.3 vmodule 多文件配置不同的日志级别

通过该功能,可以对指定模块采用不同日志级别的输出 ,可有效提升调试效率

main.go 文件内容:

复制代码
package main

import (
	"flag"

	"github.com/golang/glog"
)

func main() {
	// 用于解析命令行中 - 横线后边的参数和值,如下示例中的:-log_dir=log -alsologtostderr
	// go run main.go -log_dir=log -alsologtostderr
	flag.Parse()
	// defer() 退出前执行,清空缓存区,将日志写入文件
	defer glog.Flush()
	bar()
	bar2()
	glog.V(0).Info("LEVEL 0 message") // 使用日志级别 3
	glog.V(3).Info("LEVEL 3 message") // 使用日志级别 3
	glog.V(4).Info("LEVEL 4 message") // 使用日志级别 4
	glog.V(5).Info("LEVEL 5 message") // 使用日志级别 5
	glog.V(8).Info("LEVEL 8 message") // 使用日志级别 8
}

bar.go、bar2.go 文件内容:

复制代码
package main

import "github.com/golang/glog"

func bar() {
	glog.V(3).Info("LEVEL 3: level 3 message in bar.go")
	glog.V(4).Info("LEVEL 4: level 4 message in bar.go")
}

package main

import "github.com/golang/glog"

func bar2() {
	glog.V(4).Info("LEVEL 4: level 4 message in bar2.go")
}

如下运行语句,相关的三个文件都需要列出,全局配置为 -v=3,bar.go 文件中配置为 3 级,bar2.go 文件配置为 4 级,多文件间用','分隔

复制代码
go run main.go bar.go bar2.go -log_dir=log -alsologtostderr -v=3 -vmodule=bar=3,bar2=4

如下图为输出结果,bar.go 文件中大于 3 级的日志未输出,main.go 中 3 级及以下的日志输出:

对于文件名还可以使用通配符 *,如下测试:

复制代码
go run main.go bar.go bar2.go -log_dir=log -alsologtostderr -v=3 -vmodule=bar*=4

1.4 traceLocation 功能(log_backtrace_at 参数配置)

traceLocation 的命令格式为-log_backtrace_at=bar.go:6(文件全名:行号),当运行到指定代码处时,将把该代码的栈信息打印出来。

如下语句运行代码,在文件 bar.go 中的第 6 行,输出栈信息:

复制代码
go run main.go bar.go bar2.go -log_dir=log -alsologtostderr -v=3 -vmodule=bar=3,bar2=4 -log_backtrace_at=bar.go:6

1.5 日志格式简介

从前边几节中可知,日志默认的格式为:<header>] <message>,日志头信息和详细信息通过中括号 ] 来分隔。

header 的默认格式:Lmmdd hh:mm:ss.uuuuuu threadid file:line。其中开头的字母 L 代表的是日志级别 level,如下对应关系:

复制代码
I -> INFO
W -> WARNING
E -> ERROR
F -> FATAL

threadid 是进程 PID,即 os.Getpid() 的调用结果。

参考:https://cloud.tencent.com/developer/article/1683448

相关推荐
BlockChain8887 小时前
Solidity 实战【二】:手写一个「链上资金托管合约」
go·区块链
BlockChain88815 小时前
Solidity 实战【三】:重入攻击与防御(从 0 到 1 看懂 DAO 事件)
go·区块链
剩下了什么20 小时前
Gf命令行工具下载
go
地球没有花21 小时前
tw引发的对redis的深入了解
数据库·redis·缓存·go
BlockChain8881 天前
字符串最后一个单词的长度
算法·go
龙井茶Sky1 天前
通过higress AI统计插件学gjson表达式的分享
go·gjson·higress插件
宇宙帅猴2 天前
【Ubuntu踩坑及解决方案(一)】
linux·运维·ubuntu·go
SomeBottle3 天前
【小记】解决校园网中不同单播互通子网间 LocalSend 的发现问题
计算机网络·go·网络编程·学习笔记·计算机基础
且去填词4 天前
深入理解 GMP 模型:Go 高并发的基石
开发语言·后端·学习·算法·面试·golang·go
大厂技术总监下海4 天前
向量数据库“卷”向何方?从Milvus看“全功能、企业级”的未来
数据库·分布式·go·milvus·增强现实