我正试图找到一种方法,在我们的项目中添加日志的相关性/请求id,以便在发生某些问题时更容易导航和调试。我找到了这篇文章。从上面的示例中,有一个中间件可以添加correlationID,然后在某个处理程序函数中检索它。
中间件功能:
const ContextKeyRequestID ContextKey = "requestID"
func reqIDMiddleware1(next http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
ctx := r.Context()
id := uuid.New()
ctx = context.WithValue(ctx, ContextKeyRequestID, id.String())
r = r.WithContext(ctx)
log.Debugf("Incoming request %s %s %s %s", r.Method, r.RequestURI, r.RemoteAddr, id.String())
next.ServeHTTP(w, r)
log.Debugf("Finished handling http req. %s", id.String())
})
}
处理程序:
const LogFieldKeyRequestID = "requestID"
func handleSomeRequest() http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
ctx := r.Context()
reqIDRaw := ctx.Value(ContextKeyRequestID) // reqIDRaw at this point is of type 'interface{}'
reqID, ok := reqIDRaw.(string)
if !ok {
// handler error
}
// if reached here, reqID is ready to be used
// let's use it with logrus FieldLogger!
logger := log.WithField(LogFieldKeyRequestID, reqID)
// Do something, then log what you did
logger.Debugf("What I just did!")
// Do more, log more. Handle this request seriously
}
}
但是我想知道是否有一种方法可以实现这一点,而不必重构所有现有的处理程序和改变日志功能,通过一些自动配置,为每个日志添加id,在我的情况下,我们的项目相当大,以上述方式完成它将需要大量的更改。
你看过WithContext
和Hooks
吗?
你仍然需要修改你的代码,但是你可以集中一些行为。
https://go.dev/play/p/4YxJMK6Zl5D