go - go微服务中如何给每个日志添加trace id
问题描述
我想将跟踪 id 添加到对微服务的每个请求的日志记录中。我希望这与 springboot 应用程序类似,我们可以在 MDC 中设置跟踪 id 并获取它并在记录时使用它。
我做了一些研究,发现 go lang 中的 MDC 等价物是上下文。所以,我已经在我的上下文中设置了跟踪 ID。现在的问题是我必须使用跟踪 id 登录的地方,我需要将上下文传递给该函数,这是非常丑陋的方式。我正在为这个问题寻找更好的解决方案。
func HandlerFunction(f gin.HandlerFunc) gin.HandlerFunc{
return func(cxt *gin.Context) {
reqraceId := cxt.Request.Header.Get("trace-id")
requid , _ := uuid.NewRandom()
if reqTraceId == "" {
c.Request.Header.Set("trace-id", requid.String())
}
f(c)
}
}
解决方案
context.Context
特别是这篇文章可能值得一读,其中有一节说:
在 Google,我们要求 Go 程序员将 Context 参数作为第一个参数传递给传入和传出请求之间调用路径上的每个函数。
TL;DR - 传递上下文很好,但最好的方法是什么?
有两种主要模式
- 询问上下文给你一个记录器
- 为记录器提供上下文
上下文可用于存储值:
context.WithValue(ctx, someKey, someValue)
这意味着我们可以这样做:
somepackage.Log(ctx).Info("hello world")
// or
sompackage.Info(ctx, "hello world")
这两个示例 API 的实现可以与上下文交互以检索所需的值,而无需担心任何日志调用站点的 MDC 中可能存在的额外信息。
推荐阅读
- javascript - Amazon S3 响应不返回日期标头
- c++ - 自身的成员 STL deque
- vba - 如何让 Listbox.List 保留类型信息?
- ruby-on-rails - Rails 请求中的 JWT 验证
- php - 在 PHP 中使用字符串作为单元测试名称
- github - Git页面没有更新
- android - Dagger2 - 未生成应用程序组件
- python - 如何使用 Beautiful soup 从网页中抓取表格
- angular - ngModel 的角度选择默认值不在选择元素上工作,而是在另一个元素上工作
- node.js - 根据常见的 json 模式返回响应