fox/mapstruct/mapstruct_test.go

94 lines
2.0 KiB
Go

package mapstruct
import (
"fmt"
"reflect"
"strings"
"testing"
"time"
)
type User struct {
Name string `json:"name"`
Age int `json:"age"`
CreatedAt time.Time `json:"created_at"`
UpdatedAt *time.Time `json:"updated_at"`
Active bool `json:"active"`
Score float64 `json:"score"`
Address struct {
City string `json:"city"`
Country string `json:"country"`
} `json:"address"`
}
func TestStruct2Map(t *testing.T) {
// 1. Struct to map
user := User{
Name: "Alice",
Age: 25,
CreatedAt: time.Now(),
Active: true,
Score: 95.5,
}
user.Address.City = "New York"
user.Address.Country = "USA"
time2stringHook := func(v reflect.Value, _ reflect.StructField) (any, error) {
if v.Type() == reflect.TypeOf(time.Time{}) {
if t, ok := v.Interface().(time.Time); ok {
return t.Format("2006-01-02 15:04:05"), nil
}
}
return v, nil
}
result, err := ToMap(user, WithTypeHook(reflect.TypeOf(time.Time{}), time2stringHook))
if err != nil {
panic(err)
}
fmt.Printf("Struct to map:\n%+v\n", result)
// 2. Map to struct
data := map[string]string{
"name": "Bob",
"age": "30",
"created_at": "2025-06-04 21:07:10",
"active": "true",
"score": "88.5",
"address.city": "Los Angeles",
"address.country": "USA",
}
var user2 User
err = ToStruct(data, &user2)
if err != nil {
panic(err)
}
fmt.Printf("\nMap to struct:\n%+v\n", user2)
// 3. With custom hooks
timeHook := func(s string, _ reflect.StructField) (any, error) {
return time.Parse("2006/01/02", s)
}
nameHook := func(v reflect.Value, _ reflect.StructField) (any, error) {
return strings.ToUpper(v.String()), nil
}
data2 := map[string]string{
"name": "charlie",
"created_at": "2025/06/04",
}
var user3 User
err = ToStruct(data2, &user3,
WithTagName("json"),
WithStringTypeHook(reflect.TypeOf(time.Time{}), timeHook),
WithFieldHook("Name", nameHook),
)
if err != nil {
panic(err)
}
fmt.Printf("\nWith custom hooks:\n%+v\n", user3)
}