diff --git a/logger/unwrap/unwrap.go b/logger/unwrap/unwrap.go index 30c647e1..1c25112d 100644 --- a/logger/unwrap/unwrap.go +++ b/logger/unwrap/unwrap.go @@ -235,12 +235,71 @@ func (f *unwrap) format(v reflect.Value) { return } - // Handle pointers specially. - if kind == reflect.Ptr { + if (kind == reflect.Ptr) && (!reflect.Indirect(v).IsValid()) { f.formatPtr(v) return } + // Handle pointers specially. + if kind == reflect.Ptr { + fmt.Printf("AAAA %s\n", reflect.Indirect(v).Type().String()) + switch reflect.Indirect(v).Type().String() { + case "sql.NullBool": + if eva := reflect.Indirect(v).FieldByName("Valid"); eva.IsValid() && eva.Bool() { + v = reflect.Indirect(v).FieldByName("Bool") + kind = v.Kind() + } + case "sql.NullByte": + if eva := reflect.Indirect(v).FieldByName("Valid"); eva.IsValid() && eva.Bool() { + v = reflect.Indirect(v).FieldByName("Byte") + kind = v.Kind() + } + case "sql.NullFloat64": + if eva := reflect.Indirect(v).FieldByName("Valid"); eva.IsValid() && eva.Bool() { + v = reflect.Indirect(v).FieldByName("Float64") + kind = v.Kind() + } + case "sql.NullInt16": + if eva := reflect.Indirect(v).FieldByName("Valid"); eva.IsValid() && eva.Bool() { + v = reflect.Indirect(v).FieldByName("Int16") + kind = v.Kind() + } + case "sql.NullInt32": + if eva := reflect.Indirect(v).FieldByName("Valid"); eva.IsValid() && eva.Bool() { + v = reflect.Indirect(v).FieldByName("Int32") + kind = v.Kind() + } + case "sql.NullInt64": + if eva := reflect.Indirect(v).FieldByName("Valid"); eva.IsValid() && eva.Bool() { + v = reflect.Indirect(v).FieldByName("Int64") + kind = v.Kind() + } + case "sql.NullString": + fmt.Printf("AAAAAAAAAA") + if eva := reflect.Indirect(v).FieldByName("Valid"); eva.IsValid() && eva.Bool() { + v = reflect.Indirect(v).FieldByName("String") + kind = v.Kind() + } + case "sql.NullTime": + if eva := reflect.Indirect(v).FieldByName("Valid"); eva.IsValid() && eva.Bool() { + v = reflect.Indirect(v).FieldByName("Time") + kind = v.Kind() + } + case "wrapperspb.BoolValue", "wrapperspb.BytesValue", + "wrapperspb.DoubleValue", "wrapperspb.FloatValue", + "wrapperspb.Int32Value", "wrapperspb.Int64Value", + "wrapperspb.UInt32Value", "wrapperspb.UInt64Value", + "wrapperspb.StringValue": + if eva := reflect.Indirect(v).FieldByName("Value"); eva.IsValid() { + v = eva + kind = v.Kind() + } + default: + f.formatPtr(v) + return + } + } + // get type information unless already handled elsewhere. if !f.ignoreNextType && f.s.Flag('#') { if v.Type().Kind() != reflect.Map && diff --git a/logger/unwrap/unwrap_test.go b/logger/unwrap/unwrap_test.go index b24fe0e9..07e18d51 100644 --- a/logger/unwrap/unwrap_test.go +++ b/logger/unwrap/unwrap_test.go @@ -1,6 +1,7 @@ package unwrap import ( + "database/sql" "fmt" "strings" "testing" @@ -8,6 +9,15 @@ import ( "go.unistack.org/micro/v3/codec" ) +func TestSql(t *testing.T) { + type val struct { + S sql.NullString + } + v := &val{S: sql.NullString{Valid: true, String: "test"}} + buf := fmt.Sprintf("%#v", Unwrap(v)) + t.Logf(buf) +} + func TestUnwrap(t *testing.T) { string1 := "string1" string2 := "string2" @@ -22,8 +32,9 @@ func TestUnwrap(t *testing.T) { v1 := &val1{ar: []*string{&string1, &string2}, str: &string1, val: &val1{str: &string2}, mp: map[string]string{"key": "val"}} buf := fmt.Sprintf("%#v", Unwrap(v1)) - if strings.Compare(buf, `&unwrap.val1{mp:map[string]string{"key":"val"}, val:(*unwrap.val1){mp:map[string]string, val:(*unwrap.val1), str:(*string)"string2", ar:[]*string}, str:(*string)"string1", ar:[]*string{<*>, <*>"string2"}}`) != 0 { - t.Fatalf("not proper written %s", buf) + chk := `&unwrap.val1{mp:map[string]string{"key":"val"}, val:(*unwrap.val1){mp:map[string]string, val:(*unwrap.val1), str:(*string)"string2", ar:[]*string}, str:(*string)"string1", ar:[]*string{<*>, <*>"string2"}}` + if strings.Compare(buf, chk) != 0 { + t.Fatalf("not proper written\n%s\n%s", buf, chk) } type val2 struct {