-
-
Notifications
You must be signed in to change notification settings - Fork 186
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: add handler for log/slog in go1.21 (#548)
- Loading branch information
1 parent
e376aa8
commit 7fea5c7
Showing
2 changed files
with
100 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,18 @@ | ||
package main | ||
|
||
import ( | ||
"github.com/pterm/pterm" | ||
"log/slog" | ||
) | ||
|
||
func main() { | ||
handler := pterm.NewSlogHandler(&pterm.DefaultLogger) | ||
logger := slog.New(handler) | ||
|
||
logger.Debug("This is a debug message that won't show") | ||
pterm.DefaultLogger.Level = pterm.LogLevelDebug // Enable debug messages | ||
logger.Debug("This is a debug message", "changedLevel", true) | ||
logger.Info("This is an info message") | ||
logger.Warn("This is a warning message") | ||
logger.Error("This is an error message") | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,82 @@ | ||
package pterm | ||
|
||
import ( | ||
"context" | ||
"log/slog" | ||
) | ||
|
||
type SlogHandler struct { | ||
logger *Logger | ||
attrs []slog.Attr | ||
} | ||
|
||
// Enabled returns true if the given level is enabled. | ||
func (s *SlogHandler) Enabled(ctx context.Context, level slog.Level) bool { | ||
switch level { | ||
case slog.LevelDebug: | ||
return s.logger.CanPrint(LogLevelDebug) | ||
case slog.LevelInfo: | ||
return s.logger.CanPrint(LogLevelInfo) | ||
case slog.LevelWarn: | ||
return s.logger.CanPrint(LogLevelWarn) | ||
case slog.LevelError: | ||
return s.logger.CanPrint(LogLevelError) | ||
} | ||
return false | ||
} | ||
|
||
// Handle handles the given record. | ||
func (s *SlogHandler) Handle(ctx context.Context, record slog.Record) error { | ||
level := record.Level | ||
message := record.Message | ||
|
||
// Convert slog Attrs to a map. | ||
keyValsMap := make(map[string]interface{}) | ||
|
||
record.Attrs(func(attr slog.Attr) bool { | ||
keyValsMap[attr.Key] = attr.Value | ||
return true | ||
}) | ||
|
||
for _, attr := range s.attrs { | ||
keyValsMap[attr.Key] = attr.Value | ||
} | ||
|
||
args := s.logger.ArgsFromMap(keyValsMap) | ||
|
||
// Wrapping args inside another slice to match [][]LoggerArgument | ||
argsWrapped := [][]LoggerArgument{args} | ||
|
||
switch level { | ||
case slog.LevelDebug: | ||
s.logger.Debug(message, argsWrapped...) | ||
case slog.LevelInfo: | ||
s.logger.Info(message, argsWrapped...) | ||
case slog.LevelWarn: | ||
s.logger.Warn(message, argsWrapped...) | ||
case slog.LevelError: | ||
s.logger.Error(message, argsWrapped...) | ||
default: | ||
s.logger.Print(message, argsWrapped...) | ||
} | ||
|
||
return nil | ||
} | ||
|
||
// WithAttrs returns a new handler with the given attributes. | ||
func (s *SlogHandler) WithAttrs(attrs []slog.Attr) slog.Handler { | ||
newS := *s | ||
newS.attrs = attrs | ||
return &newS | ||
} | ||
|
||
// WithGroup is not yet supported. | ||
func (s *SlogHandler) WithGroup(name string) slog.Handler { | ||
// Grouping is not yet supported by pterm. | ||
return s | ||
} | ||
|
||
// NewSlogHandler returns a new logging handler that can be intrgrated with log/slog. | ||
func NewSlogHandler(logger *Logger) *SlogHandler { | ||
return &SlogHandler{logger: logger} | ||
} |