1
|
|
|
package middleware |
2
|
|
|
|
3
|
|
|
import ( |
4
|
|
|
"io" |
5
|
|
|
"net" |
6
|
|
|
"net/http" |
7
|
|
|
|
8
|
|
|
"github.com/gorilla/handlers" |
9
|
|
|
"github.com/muonsoft/openapi-mock/pkg/logcontext" |
10
|
|
|
"github.com/sirupsen/logrus" |
11
|
|
|
) |
12
|
|
|
|
13
|
|
|
type ContextLogger struct { |
14
|
|
|
logger *logrus.Logger |
15
|
|
|
next http.Handler |
16
|
|
|
} |
17
|
|
|
|
18
|
|
|
func NewContextLogger(logger *logrus.Logger, next http.Handler) *ContextLogger { |
19
|
|
|
middleware := &ContextLogger{logger: logger} |
20
|
|
|
middleware.next = handlers.CustomLoggingHandler(io.Discard, next, middleware.logRequest) |
21
|
|
|
|
22
|
|
|
return middleware |
23
|
|
|
} |
24
|
|
|
|
25
|
|
|
func (handler *ContextLogger) ServeHTTP(responseWriter http.ResponseWriter, request *http.Request) { |
26
|
|
|
requestContext := request.Context() |
27
|
|
|
|
28
|
|
|
logger := handler.logger.WithFields(logrus.Fields{ |
29
|
|
|
"requestId": RequestIDFromContext(requestContext), |
30
|
|
|
}) |
31
|
|
|
|
32
|
|
|
loggerContext := logcontext.WithLogger(requestContext, logger) |
33
|
|
|
contextualRequest := request.WithContext(loggerContext) |
34
|
|
|
|
35
|
|
|
handler.next.ServeHTTP(responseWriter, contextualRequest) |
36
|
|
|
} |
37
|
|
|
|
38
|
|
|
func (handler *ContextLogger) logRequest(_ io.Writer, params handlers.LogFormatterParams) { |
39
|
|
|
requestID := RequestIDFromContext(params.Request.Context()) |
40
|
|
|
host, _, err := net.SplitHostPort(params.Request.RemoteAddr) |
41
|
|
|
if err != nil { |
42
|
|
|
host = params.Request.RemoteAddr |
43
|
|
|
} |
44
|
|
|
|
45
|
|
|
fields := logrus.Fields{ |
46
|
|
|
"requestID": requestID, |
47
|
|
|
"proto": params.Request.Proto, |
48
|
|
|
"method": params.Request.Method, |
49
|
|
|
"userAgent": params.Request.UserAgent(), |
50
|
|
|
"referrer": params.Request.Referer(), |
51
|
|
|
"host": host, |
52
|
|
|
"uri": params.URL.RequestURI(), |
53
|
|
|
"statusCode": params.StatusCode, |
54
|
|
|
"size": params.Size, |
55
|
|
|
} |
56
|
|
|
|
57
|
|
|
handler.logger. |
58
|
|
|
WithTime(params.TimeStamp). |
59
|
|
|
WithFields(fields). |
60
|
|
|
Infof("request completed: %s %s", params.Request.Method, params.Request.URL.Path) |
61
|
|
|
} |
62
|
|
|
|