Signed-off-by: Vasiliy Tolstov <v.tolstov@unistack.org>
This commit is contained in:
		| @@ -33,6 +33,8 @@ type Options struct { | ||||
| 	LevelKey string | ||||
| 	// MessageKey is the key used for the message of the log call | ||||
| 	MessageKey string | ||||
| 	// ErrorKey is the key used for the error info | ||||
| 	ErrorKey string | ||||
| 	// SourceKey is the key used for the source file and line of the log call | ||||
| 	SourceKey string | ||||
| 	// StacktraceKey is the key used for the stacktrace | ||||
| @@ -52,10 +54,10 @@ func NewOptions(opts ...options.Option) Options { | ||||
| 		ContextAttrFuncs: DefaultContextAttrFuncs, | ||||
| 	} | ||||
|  | ||||
| 	WithMicroKeys()(&options) | ||||
| 	_ = WithMicroKeys()(&options) | ||||
|  | ||||
| 	for _, o := range opts { | ||||
| 		o(&options) | ||||
| 		_ = o(&options) | ||||
| 	} | ||||
| 	return options | ||||
| } | ||||
| @@ -123,6 +125,9 @@ func WithZapKeys() options.Option { | ||||
| 		if err = options.Set(src, "stacktrace", ".StacktraceKey"); err != nil { | ||||
| 			return err | ||||
| 		} | ||||
| 		if err = options.Set(src, "error", ".ErrorKey"); err != nil { | ||||
| 			return err | ||||
| 		} | ||||
| 		return nil | ||||
| 	} | ||||
| } | ||||
| @@ -145,6 +150,9 @@ func WithZerologKeys() options.Option { | ||||
| 		if err = options.Set(src, "stacktrace", ".StacktraceKey"); err != nil { | ||||
| 			return err | ||||
| 		} | ||||
| 		if err = options.Set(src, "error", ".ErrorKey"); err != nil { | ||||
| 			return err | ||||
| 		} | ||||
| 		return nil | ||||
| 	} | ||||
| } | ||||
| @@ -167,6 +175,9 @@ func WithSlogKeys() options.Option { | ||||
| 		if err = options.Set(src, "stacktrace", ".StacktraceKey"); err != nil { | ||||
| 			return err | ||||
| 		} | ||||
| 		if err = options.Set(src, "error", ".ErrorKey"); err != nil { | ||||
| 			return err | ||||
| 		} | ||||
| 		return nil | ||||
| 	} | ||||
| } | ||||
| @@ -189,6 +200,9 @@ func WithMicroKeys() options.Option { | ||||
| 		if err = options.Set(src, "stacktrace", ".StacktraceKey"); err != nil { | ||||
| 			return err | ||||
| 		} | ||||
| 		if err = options.Set(src, "error", ".ErrorKey"); err != nil { | ||||
| 			return err | ||||
| 		} | ||||
| 		return nil | ||||
| 	} | ||||
| } | ||||
|   | ||||
| @@ -174,6 +174,12 @@ func (s *slogLogger) Log(ctx context.Context, lvl logger.Level, msg string, attr | ||||
| 	for _, fn := range s.opts.ContextAttrFuncs { | ||||
| 		attrs = append(attrs, fn(ctx)...) | ||||
| 	} | ||||
| 	for _, a := range attrs { | ||||
| 		if ve, ok := a.(error); ok && ve != nil { | ||||
| 			attrs = append(attrs, slog.String(s.opts.ErrorKey, ve.Error())) | ||||
| 			break | ||||
| 		} | ||||
| 	} | ||||
| 	if s.opts.Stacktrace && lvl == logger.ErrorLevel { | ||||
| 		stackInfo := make([]byte, 1024*1024) | ||||
| 		if stackSize := runtime.Stack(stackInfo, false); stackSize > 0 { | ||||
| @@ -184,6 +190,15 @@ func (s *slogLogger) Log(ctx context.Context, lvl logger.Level, msg string, attr | ||||
| 		} | ||||
| 	} | ||||
| 	r.Add(attrs...) | ||||
| 	r.Attrs(func(a slog.Attr) bool { | ||||
| 		if a.Key == s.opts.ErrorKey { | ||||
| 			if span, ok := tracer.SpanFromContext(ctx); ok { | ||||
| 				span.SetStatus(tracer.SpanStatusError, a.Value.String()) | ||||
| 				return false | ||||
| 			} | ||||
| 		} | ||||
| 		return true | ||||
| 	}) | ||||
| 	_ = s.slog.Handler().Handle(ctx, r) | ||||
| } | ||||
|  | ||||
| @@ -239,6 +254,12 @@ func (s *slogLogger) Error(ctx context.Context, msg string, attrs ...interface{} | ||||
| 	for _, fn := range s.opts.ContextAttrFuncs { | ||||
| 		attrs = append(attrs, fn(ctx)...) | ||||
| 	} | ||||
| 	for _, a := range attrs { | ||||
| 		if ve, ok := a.(error); ok && ve != nil { | ||||
| 			attrs = append(attrs, slog.String(s.opts.ErrorKey, ve.Error())) | ||||
| 			break | ||||
| 		} | ||||
| 	} | ||||
| 	if s.opts.Stacktrace { | ||||
| 		stackInfo := make([]byte, 1024*1024) | ||||
| 		if stackSize := runtime.Stack(stackInfo, false); stackSize > 0 { | ||||
| @@ -250,7 +271,7 @@ func (s *slogLogger) Error(ctx context.Context, msg string, attrs ...interface{} | ||||
| 	} | ||||
| 	r.Add(attrs...) | ||||
| 	r.Attrs(func(a slog.Attr) bool { | ||||
| 		if a.Key == "error" { | ||||
| 		if a.Key == s.opts.ErrorKey { | ||||
| 			if span, ok := tracer.SpanFromContext(ctx); ok { | ||||
| 				span.SetStatus(tracer.SpanStatusError, a.Value.String()) | ||||
| 				return false | ||||
|   | ||||
| @@ -3,6 +3,7 @@ package slog | ||||
| import ( | ||||
| 	"bytes" | ||||
| 	"context" | ||||
| 	"fmt" | ||||
| 	"log" | ||||
| 	"testing" | ||||
|  | ||||
| @@ -16,7 +17,7 @@ func TestError(t *testing.T) { | ||||
| 	if err := l.Init(); err != nil { | ||||
| 		t.Fatal(err) | ||||
| 	} | ||||
| 	l.Error(ctx, "message") | ||||
| 	l.Error(ctx, "msg", fmt.Errorf("message")) | ||||
| 	if !bytes.Contains(buf.Bytes(), []byte(`"stacktrace":"`)) { | ||||
| 		t.Fatalf("logger stacktrace not works, buf contains: %s", buf.Bytes()) | ||||
| 	} | ||||
|   | ||||
		Reference in New Issue
	
	Block a user