From 1b4655573a715ec6b4247727e50deb4e4436921d Mon Sep 17 00:00:00 2001 From: Ethan Dickson Date: Thu, 3 Jul 2025 05:45:58 +0000 Subject: [PATCH 1/3] fix!: handle sql/driver.Valuer types properly in slogjson --- map.go | 9 +++++++++ map_test.go | 2 +- sloggers/slogjson/slogjson_test.go | 25 ++++++++++++++++++++++++- 3 files changed, 34 insertions(+), 2 deletions(-) diff --git a/map.go b/map.go index 636f4ee..cbf2991 100644 --- a/map.go +++ b/map.go @@ -2,6 +2,7 @@ package slog import ( "bytes" + "database/sql/driver" "encoding/json" "fmt" "reflect" @@ -70,6 +71,14 @@ func marshalList(rv reflect.Value) []byte { } func encode(v interface{}) []byte { + if vr, ok := v.(driver.Valuer); ok { + var err error + v, err = vr.Value() + if err != nil { + return encodeJSON(fmt.Sprintf("error calling Value: %v", err)) + } + } + switch v := v.(type) { case json.Marshaler: return encodeJSON(v) diff --git a/map_test.go b/map_test.go index fce13b5..88c4281 100644 --- a/map_test.go +++ b/map_test.go @@ -93,7 +93,7 @@ func TestMap(t *testing.T) { { "msg": "failed to marshal to JSON", "fun": "cdr.dev/slog.encodeJSON", - "loc": "`+mapTestFile+`:131" + "loc": "`+mapTestFile+`:141" }, "json: error calling MarshalJSON for type slog_test.complexJSON: json: unsupported type: complex128" ], diff --git a/sloggers/slogjson/slogjson_test.go b/sloggers/slogjson/slogjson_test.go index 79a46e7..cb02122 100644 --- a/sloggers/slogjson/slogjson_test.go +++ b/sloggers/slogjson/slogjson_test.go @@ -3,6 +3,7 @@ package slogjson_test import ( "bytes" "context" + "database/sql" "fmt" "runtime" "testing" @@ -33,7 +34,29 @@ func TestMake(t *testing.T) { l.Error(ctx, "line1\n\nline2", slog.F("wowow", "me\nyou")) j := entryjson.Filter(b.String(), "ts") - exp := fmt.Sprintf(`{"level":"ERROR","msg":"line1\n\nline2","caller":"%v:33","func":"cdr.dev/slog/sloggers/slogjson_test.TestMake","logger_names":["named"],"trace":"%v","span":"%v","fields":{"wowow":"me\nyou"}} + exp := fmt.Sprintf(`{"level":"ERROR","msg":"line1\n\nline2","caller":"%v:34","func":"cdr.dev/slog/sloggers/slogjson_test.TestMake","logger_names":["named"],"trace":"%v","span":"%v","fields":{"wowow":"me\nyou"}} `, slogjsonTestFile, span.SpanContext().TraceID().String(), span.SpanContext().SpanID().String()) assert.Equal(t, "entry", exp, j) } + +func TestNoDriverValue(t *testing.T) { + t.Parallel() + + b := &bytes.Buffer{} + l := slog.Make(slogjson.Sink(b)) + l = l.Named("named") + validField := sql.NullString{ + String: "cat", + Valid: true, + } + invalidField := sql.NullString{ + String: "dog", + Valid: false, + } + l.Error(bg, "error!", slog.F("inval", invalidField), slog.F("val", validField)) + + j := entryjson.Filter(b.String(), "ts") + exp := fmt.Sprintf(`{"level":"ERROR","msg":"error!","caller":"%v:56","func":"cdr.dev/slog/sloggers/slogjson_test.TestNoDriverValue","logger_names":["named"],"fields":{"inval":null,"val":"cat"}} +`, slogjsonTestFile) + assert.Equal(t, "entry", exp, j) +} From 3a87b053038b8c889424afa2b5c50a67df825c46 Mon Sep 17 00:00:00 2001 From: Ethan Dickson Date: Thu, 3 Jul 2025 05:54:30 +0000 Subject: [PATCH 2/3] fixup --- map_test.go | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/map_test.go b/map_test.go index 88c4281..c89adf0 100644 --- a/map_test.go +++ b/map_test.go @@ -62,12 +62,12 @@ func TestMap(t *testing.T) { { "msg": "wrap1", "fun": "cdr.dev/slog_test.TestMap.func2", - "loc": "`+mapTestFile+`:41" + "loc": "`+mapTestFile+`:41" }, { "msg": "wrap2", "fun": "cdr.dev/slog_test.TestMap.func2", - "loc": "`+mapTestFile+`:42" + "loc": "`+mapTestFile+`:42" }, "EOF" ], @@ -93,7 +93,7 @@ func TestMap(t *testing.T) { { "msg": "failed to marshal to JSON", "fun": "cdr.dev/slog.encodeJSON", - "loc": "`+mapTestFile+`:141" + "loc": "`+mapTestFile+`:140" }, "json: error calling MarshalJSON for type slog_test.complexJSON: json: unsupported type: complex128" ], From d25bca5f74c0d9b561a66561255046f4edd419f0 Mon Sep 17 00:00:00 2001 From: Ethan Dickson Date: Thu, 3 Jul 2025 05:56:15 +0000 Subject: [PATCH 3/3] fixup --- sloggers/slogjson/slogjson_test.go | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/sloggers/slogjson/slogjson_test.go b/sloggers/slogjson/slogjson_test.go index cb02122..cdbffee 100644 --- a/sloggers/slogjson/slogjson_test.go +++ b/sloggers/slogjson/slogjson_test.go @@ -53,10 +53,14 @@ func TestNoDriverValue(t *testing.T) { String: "dog", Valid: false, } - l.Error(bg, "error!", slog.F("inval", invalidField), slog.F("val", validField)) + validInt := sql.NullInt64{ + Int64: 42, + Valid: true, + } + l.Error(bg, "error!", slog.F("inval", invalidField), slog.F("val", validField), slog.F("int", validInt)) j := entryjson.Filter(b.String(), "ts") - exp := fmt.Sprintf(`{"level":"ERROR","msg":"error!","caller":"%v:56","func":"cdr.dev/slog/sloggers/slogjson_test.TestNoDriverValue","logger_names":["named"],"fields":{"inval":null,"val":"cat"}} + exp := fmt.Sprintf(`{"level":"ERROR","msg":"error!","caller":"%v:60","func":"cdr.dev/slog/sloggers/slogjson_test.TestNoDriverValue","logger_names":["named"],"fields":{"inval":null,"val":"cat","int":42}} `, slogjsonTestFile) assert.Equal(t, "entry", exp, j) }