logger/slog: fix Clone and Fields methods

Signed-off-by: Vasiliy Tolstov <v.tolstov@unistack.org>
This commit is contained in:
Василий Толстов 2024-11-24 15:31:40 +03:00
parent 7cd7fb0c0a
commit d1c6e121c1
2 changed files with 65 additions and 18 deletions

View File

@ -76,24 +76,19 @@ type slogLogger struct {
func (s *slogLogger) Clone(opts ...logger.Option) logger.Logger { func (s *slogLogger) Clone(opts ...logger.Option) logger.Logger {
s.mu.RLock() s.mu.RLock()
options := s.opts options := s.opts
level := s.leveler.Level()
s.mu.RUnlock() s.mu.RUnlock()
for _, o := range opts { for _, o := range opts {
o(&options) o(&options)
} }
l := &slogLogger{ l := &slogLogger{opts: options}
opts: options,
}
l.leveler = new(slog.LevelVar) l.leveler = new(slog.LevelVar)
handleOpt := &slog.HandlerOptions{ l.leveler.Set(level)
ReplaceAttr: l.renameAttr, attrs, _ := s.argsAttrs(l.opts.Fields)
Level: l.leveler, l.handler = s.handler.WithAttrs(attrs)
AddSource: l.opts.AddSource,
}
l.leveler.Set(loggerToSlogLevel(l.opts.Level))
l.handler = slog.New(slog.NewJSONHandler(options.Out, handleOpt)).With(options.Fields...).Handler()
return l return l
} }
@ -110,7 +105,7 @@ func (s *slogLogger) Options() logger.Options {
return s.opts return s.opts
} }
func (s *slogLogger) Fields(attrs ...interface{}) logger.Logger { func (s *slogLogger) Fields(fields ...interface{}) logger.Logger {
s.mu.RLock() s.mu.RLock()
level := s.leveler.Level() level := s.leveler.Level()
options := s.opts options := s.opts
@ -120,13 +115,8 @@ func (s *slogLogger) Fields(attrs ...interface{}) logger.Logger {
l.leveler = new(slog.LevelVar) l.leveler = new(slog.LevelVar)
l.leveler.Set(level) l.leveler.Set(level)
handleOpt := &slog.HandlerOptions{ attrs, _ := s.argsAttrs(fields)
ReplaceAttr: l.renameAttr, l.handler = s.handler.WithAttrs(attrs)
Level: l.leveler,
AddSource: l.opts.AddSource,
}
l.handler = slog.New(slog.NewJSONHandler(l.opts.Out, handleOpt)).With(attrs...).Handler()
return l return l
} }

View File

@ -15,6 +15,56 @@ import (
"go.unistack.org/micro/v3/logger" "go.unistack.org/micro/v3/logger"
) )
func TestMultipleFieldsWithLevel(t *testing.T) {
ctx := context.TODO()
buf := bytes.NewBuffer(nil)
l := NewLogger(logger.WithLevel(logger.InfoLevel), logger.WithOutput(buf))
if err := l.Init(); err != nil {
t.Fatal(err)
}
l = l.Fields("key", "val")
l.Info(ctx, "msg1")
nl := l.Clone(logger.WithLevel(logger.DebugLevel))
nl.Debug(ctx, "msg2")
l.Debug(ctx, "msg3")
if !bytes.Contains(buf.Bytes(), []byte(`"key":"val"`)) {
t.Fatalf("logger error not works, buf contains: %s", buf.Bytes())
}
if !bytes.Contains(buf.Bytes(), []byte(`"msg1"`)) {
t.Fatalf("logger error not works, buf contains: %s", buf.Bytes())
}
if !bytes.Contains(buf.Bytes(), []byte(`"msg2"`)) {
t.Fatalf("logger error not works, buf contains: %s", buf.Bytes())
}
if bytes.Contains(buf.Bytes(), []byte(`"msg3"`)) {
t.Fatalf("logger error not works, buf contains: %s", buf.Bytes())
}
}
func TestMultipleFields(t *testing.T) {
ctx := context.TODO()
buf := bytes.NewBuffer(nil)
l := NewLogger(logger.WithLevel(logger.InfoLevel), logger.WithOutput(buf))
if err := l.Init(); err != nil {
t.Fatal(err)
}
l = l.Fields("key", "val")
l = l.Fields("key1", "val1")
l.Info(ctx, "msg")
if !bytes.Contains(buf.Bytes(), []byte(`"key":"val"`)) {
t.Fatalf("logger error not works, buf contains: %s", buf.Bytes())
}
if !bytes.Contains(buf.Bytes(), []byte(`"key1":"val1"`)) {
t.Fatalf("logger error not works, buf contains: %s", buf.Bytes())
}
}
func TestError(t *testing.T) { func TestError(t *testing.T) {
ctx := context.TODO() ctx := context.TODO()
buf := bytes.NewBuffer(nil) buf := bytes.NewBuffer(nil)
@ -234,4 +284,11 @@ func Test_WithContextAttrFunc(t *testing.T) {
if !(bytes.Contains(buf.Bytes(), []byte(`"source-service":"Test-System"`))) { if !(bytes.Contains(buf.Bytes(), []byte(`"source-service":"Test-System"`))) {
t.Fatalf("logger info, buf %s", buf.Bytes()) t.Fatalf("logger info, buf %s", buf.Bytes())
} }
buf.Reset()
imd, _ := metadata.FromIncomingContext(ctx)
l.Info(ctx, "test message1")
imd.Set("Source-Service", "Test-System2")
l.Info(ctx, "test message2")
// t.Logf("xxx %s", buf.Bytes())
} }