Skip to content

Commit

Permalink
feat: Migrate to standard library log/slog (#94)
Browse files Browse the repository at this point in the history
* refactor: Migrate from logrus to log/slog

* feat: Simplify usage

* fix: Linter warnings

* refactor: Return ligger from init function
  • Loading branch information
obalunenko committed Sep 17, 2023
1 parent a185569 commit dc746ec
Show file tree
Hide file tree
Showing 393 changed files with 189 additions and 203,615 deletions.
6 changes: 2 additions & 4 deletions context.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,6 @@ package logger

import (
"context"

"github.com/sirupsen/logrus" //nolint:depguard // this is the only place where logrus should be imported.
)

type logCtxKey struct{}
Expand All @@ -16,12 +14,12 @@ func ContextWithLogger(ctx context.Context, l Logger) context.Context {
// FromContext extracts Logger from context. If no instance found - returns Logger from default logInstance.
func FromContext(ctx context.Context) Logger {
if ctx == nil {
return newLogrusWrapper(logrus.NewEntry(logInstance))
return newSlogWrapper(logInstance)
}

if l, ok := ctx.Value(logCtxKey{}).(Logger); ok && l != nil {
return l
}

return newLogrusWrapper(logrus.NewEntry(logInstance))
return newSlogWrapper(logInstance)
}
63 changes: 39 additions & 24 deletions formatter.go
Original file line number Diff line number Diff line change
@@ -1,48 +1,63 @@
package logger

import (
"time"

"github.com/sirupsen/logrus" //nolint:depguard // this is the only place where logrus should be imported.
"io"
"log/slog"
)

const (
jsonFmt = "json"
textFmt = "text"
)

func makeFormatter(format string) logrus.Formatter {
var f logrus.Formatter

func makeFormatter(w io.Writer, format string, lvl Level, source bool, fn ...replaceFn) slog.Handler {
var builder handlerBuildFn
switch format {
case jsonFmt:
f = jsonFormatter()
builder = jsonFormatter()
case textFmt:
f = textFormatter()
builder = textFormatter()
default:
f = textFormatter()
builder = textFormatter()
}

return f
return buildFormatter(builder, w, lvl, source, fn)
}

func jsonFormatter() logrus.Formatter {
f := new(logrus.JSONFormatter)
f.TimestampFormat = time.RFC3339Nano
type replaceFn func(groups []string, a slog.Attr) slog.Attr

f.DataKey = "metadata"
func buildFormatter(builder handlerBuildFn, w io.Writer, level Level, withSource bool, replaceFns []replaceFn) slog.Handler {
replaceAttrs := func(replacenFns []replaceFn) replaceFn {
return func(groups []string, a slog.Attr) slog.Attr {
for _, fn := range replacenFns {
a = fn(groups, a)
}

return f
}
return a
}
}

opts := slog.HandlerOptions{
AddSource: withSource,
Level: level,
ReplaceAttr: replaceAttrs(replaceFns),
}

func textFormatter() logrus.Formatter {
f := new(logrus.TextFormatter)
handler := builder(w, &opts)

f.ForceColors = true
f.DisableColors = false
f.FullTimestamp = true
f.TimestampFormat = "02-01-2006 15:04:05"
f.QuoteEmptyFields = true
return handler
}

func jsonFormatter() handlerBuildFn {
return func(w io.Writer, opts *slog.HandlerOptions) slog.Handler {
return slog.NewJSONHandler(w, opts)
}
}

return f
func textFormatter() handlerBuildFn {
return func(w io.Writer, opts *slog.HandlerOptions) slog.Handler {
return slog.NewTextHandler(w, opts)
}
}

type handlerBuildFn func(w io.Writer, opts *slog.HandlerOptions) slog.Handler
14 changes: 0 additions & 14 deletions go.mod
Original file line number Diff line number Diff line change
@@ -1,17 +1,3 @@
module github.com/obalunenko/logger

go 1.21

toolchain go1.21.0

require (
github.com/evalphobia/logrus_sentry v0.8.2
github.com/sirupsen/logrus v1.9.3
)

require (
github.com/certifi/gocertifi v0.0.0-20210507211836-431795d63e8d // indirect
github.com/getsentry/raven-go v0.2.0 // indirect
github.com/pkg/errors v0.9.1 // indirect
golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8 // indirect
)
23 changes: 0 additions & 23 deletions go.sum
Original file line number Diff line number Diff line change
@@ -1,23 +0,0 @@
github.com/certifi/gocertifi v0.0.0-20210507211836-431795d63e8d h1:S2NE3iHSwP0XV47EEXL8mWmRdEfGscSJ+7EgePNgt0s=
github.com/certifi/gocertifi v0.0.0-20210507211836-431795d63e8d/go.mod h1:sGbDF6GwGcLpkNXPUTkMRoywsNa/ol15pxFe6ERfguA=
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/evalphobia/logrus_sentry v0.8.2 h1:dotxHq+YLZsT1Bb45bB5UQbfCh3gM/nFFetyN46VoDQ=
github.com/evalphobia/logrus_sentry v0.8.2/go.mod h1:pKcp+vriitUqu9KiWj/VRFbRfFNUwz95/UkgG8a6MNc=
github.com/getsentry/raven-go v0.2.0 h1:no+xWJRb5ZI7eE8TWgIq1jLulQiIoLG0IfYxv5JYMGs=
github.com/getsentry/raven-go v0.2.0/go.mod h1:KungGk8q33+aIAZUIVWZDr2OfAEBsO49PX4NzFV5kcQ=
github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/sirupsen/logrus v1.9.3 h1:dueUQJ1C2q9oE3F7wvmSGAaVtTmUizReu6fjN8uqzbQ=
github.com/sirupsen/logrus v1.9.3/go.mod h1:naHLuLoDiP4jHNo9R0sCBMtWGeIprob74mVsIT4qYEQ=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY=
github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8 h1:0A+M6Uqn+Eje4kHMK80dtF3JCXC4ykBgQG4Fe06QRhQ=
golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c h1:dUUwHk2QECo/6vqA44rthZ8ie2QXMNeKRTHCNY2nXvo=
gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
75 changes: 69 additions & 6 deletions level.go
Original file line number Diff line number Diff line change
@@ -1,15 +1,78 @@
package logger

import (
"github.com/sirupsen/logrus"
"fmt"
"log/slog"
"strings"
)

// Level type.
type Level struct {
logrus.Level
type Level = slog.Level

const (
// LevelDebug is a debug level.
LevelDebug = slog.LevelDebug
// LevelInfo is an info level.
LevelInfo = slog.LevelInfo
// LevelWarn is a warn level.
LevelWarn = slog.LevelWarn
// LevelError is an error level.
LevelError = slog.LevelError
// LevelFatal is a fatal level.
LevelFatal = slog.Level(12)
)

// AllLevels is a slice of all levels.
var AllLevels = []Level{
LevelDebug,
LevelInfo,
LevelWarn,
LevelError,
LevelFatal,
}

var levelNames = map[Level]string{
LevelDebug: "DEBUG",
LevelInfo: "INFO",
LevelWarn: "WARN",
LevelError: "ERROR",
LevelFatal: "FATAL",
}

var levelValues = map[string]Level{
"DEBUG": LevelDebug,
"INFO": LevelInfo,
"WARN": LevelWarn,
"ERROR": LevelError,
"FATAL": LevelFatal,
}

// IsDebug checks if level is in debug range.
func (l Level) IsDebug() bool {
return l.Level >= logrus.DebugLevel
func replaceLevelNames(groups []string, a slog.Attr) slog.Attr {
// Customize the name of the level key and the output string, including
// custom level values.
if a.Key == slog.LevelKey {
level, ok := a.Value.Any().(slog.Level)
if !ok {
return a
}

name, ok := levelNames[level]
if !ok {
name = "UNKNOWN"
}

a.Value = slog.StringValue(name)
}

return a
}

// ParseLevel takes a string level and returns the Logrus log level constant.
func ParseLevel(lvl string) (Level, error) {
level, ok := levelValues[strings.ToUpper(lvl)]
if !ok {
return LevelInfo, fmt.Errorf("not a valid log Level: %q", lvl)
}

return level, nil
}
Loading

0 comments on commit dc746ec

Please sign in to comment.