diff --git a/convert.go b/convert.go index 36f015d..8e6f264 100644 --- a/convert.go +++ b/convert.go @@ -92,8 +92,7 @@ func ByteSize(bytes uint64) string { // ToString Change arg to string func ToString(arg any, timeFormat ...string) string { - var tmp = reflect.Indirect(reflect.ValueOf(arg)).Interface() - switch v := tmp.(type) { + switch v := arg.(type) { case int: return strconv.Itoa(v) case int8: @@ -134,6 +133,12 @@ func ToString(arg any, timeFormat ...string) string { case fmt.Stringer: return v.String() default: + // Check if the type is a pointer by using reflection + rv := reflect.ValueOf(arg) + if rv.Kind() == reflect.Ptr && !rv.IsNil() { + // Dereference the pointer and recursively call ToString + return ToString(rv.Elem().Interface(), timeFormat...) + } return "" } } diff --git a/convert_test.go b/convert_test.go index 722d53f..a295408 100644 --- a/convert_test.go +++ b/convert_test.go @@ -5,7 +5,9 @@ package utils import ( + "reflect" "testing" + "time" "github.com/stretchr/testify/require" ) @@ -68,18 +70,76 @@ func Test_CopyString(t *testing.T) { func Test_ToString(t *testing.T) { t.Parallel() - res := ToString([]byte("Hello, World!")) - require.Equal(t, "Hello, World!", res) - res = ToString(true) - require.Equal(t, "true", res) - res = ToString(uint(100)) - require.Equal(t, "100", res) + + tests := []struct { + input interface{} + expected string + }{ + {[]byte("Hello, World!"), "Hello, World!"}, + {true, "true"}, + {uint(100), "100"}, + {int(42), "42"}, + {int8(42), "42"}, + {int16(42), "42"}, + {int32(42), "42"}, + {int64(42), "42"}, + {uint8(100), "100"}, + {uint16(100), "100"}, + {uint32(100), "100"}, + {uint64(100), "100"}, + {"test string", "test string"}, + {float32(3.14), "3.14"}, + {float64(3.14159), "3.14159"}, + {time.Date(2000, 1, 1, 12, 34, 56, 0, time.UTC), "2000-01-01 12:34:56"}, + {struct{ Name string }{"John"}, ""}, // Assuming default case returns an empty string + } + + for _, tc := range tests { + t.Run(reflect.TypeOf(tc.input).String(), func(t *testing.T) { + res := ToString(tc.input) + require.Equal(t, tc.expected, res) + }) + } + + // Testing pointer to int + intPtr := 42 + testsPtr := []struct { + input interface{} + expected string + }{ + {&intPtr, "42"}, + } + for _, tc := range testsPtr { + t.Run("pointer to "+reflect.TypeOf(tc.input).Elem().String(), func(t *testing.T) { + res := ToString(tc.input) + require.Equal(t, tc.expected, res) + }) + } } // go test -v -run=^$ -bench=ToString -benchmem -count=2 func Benchmark_ToString(b *testing.B) { - hello := []byte("Hello, World!") + values := []interface{}{ + 42, + int8(42), + int16(42), + int32(42), + int64(42), + uint(42), + uint8(42), + uint16(42), + uint32(42), + uint64(42), + "Hello, World!", + []byte("Hello, World!"), + true, + float32(3.14), + float64(3.14), + time.Now(), + } for n := 0; n < b.N; n++ { - ToString(hello) + for _, value := range values { + _ = ToString(value) + } } }