Replace Echo logger with slog. (#67)

* Replace Echo logger with slog.
This commit is contained in:
Mike Stefanello 2024-06-14 21:01:48 -04:00 committed by GitHub
parent 97bef0257e
commit c8a3d64918
14 changed files with 315 additions and 57 deletions

View file

@ -1,20 +1,80 @@
package middleware
import (
"fmt"
"strconv"
"time"
"github.com/labstack/echo/v4"
"github.com/mikestefanello/pagoda/pkg/log"
)
// LogRequestID includes the request ID in all logs for the given request
// This requires that middleware that includes the request ID first execute
func LogRequestID() echo.MiddlewareFunc {
// SetLogger initializes a logger for the current request and stores it in the context.
// It's recommended to have this executed after Echo's RequestID() middleware because it will add
// the request ID to the logger so that all log messages produced from this request have the
// request ID in it. You can modify this code to include any other fields that you want to always
// appear.
func SetLogger() echo.MiddlewareFunc {
return func(next echo.HandlerFunc) echo.HandlerFunc {
return func(c echo.Context) error {
rID := c.Response().Header().Get(echo.HeaderXRequestID)
format := `{"time":"${time_rfc3339_nano}","id":"%s","level":"${level}","prefix":"${prefix}","file":"${short_file}","line":"${line}"}`
c.Logger().SetHeader(fmt.Sprintf(format, rID))
return next(c)
return func(ctx echo.Context) error {
// Include the request ID in the logger
rID := ctx.Response().Header().Get(echo.HeaderXRequestID)
logger := log.Ctx(ctx).With("request_id", rID)
// TODO include other fields you may want in all logs for this request
log.Set(ctx, logger)
return next(ctx)
}
}
}
// LogRequest logs the current request
// Echo provides middleware similar to this, but we want to use our own logger
func LogRequest() echo.MiddlewareFunc {
return func(next echo.HandlerFunc) echo.HandlerFunc {
return func(ctx echo.Context) (err error) {
req := ctx.Request()
res := ctx.Response()
// Track how long the request takes to complete
start := time.Now()
if err = next(ctx); err != nil {
ctx.Error(err)
}
stop := time.Now()
sub := log.Ctx(ctx).With(
"ip", ctx.RealIP(),
"host", req.Host,
"method", req.Method,
"path", func() string {
p := req.URL.Path
if p == "" {
p = "/"
}
return p
}(),
"referer", req.Referer(),
"status", res.Status,
"bytes_in", func() string {
cl := req.Header.Get(echo.HeaderContentLength)
if cl == "" {
cl = "0"
}
return cl
}(),
"bytes_out", strconv.FormatInt(res.Size, 10),
"latency", stop.Sub(start).String(),
)
// TODO is there a (better) way to log without a message?
if res.Status >= 500 {
sub.Error("")
} else {
sub.Info("")
}
return nil
}
}
}