diff --git a/framework/database/marshaler.go b/framework/database/marshaler.go index f05f5a70..215058ee 100644 --- a/framework/database/marshaler.go +++ b/framework/database/marshaler.go @@ -3,6 +3,7 @@ package database import ( "context" "fmt" + "github.com/unionj-cloud/go-doudou/v2/toolkit/maputils" "reflect" "github.com/bytedance/sonic" @@ -58,16 +59,20 @@ func (c *Marshaler) Set(ctx context.Context, key, object any, options ...store.O source := reflectutils.ValueOf(query.Dest).Interface() t := fmt.Sprintf("%T", source) if t == "map[string]interface {}" { - query.Dest = lo.OmitBy[string, interface{}](source.(map[string]interface{}), func(key string, value interface{}) bool { + compactMap := lo.OmitBy[string, interface{}](source.(map[string]interface{}), func(key string, value interface{}) bool { return value == nil || reflect.ValueOf(value).IsZero() }) + maputils.ConvertInt642String(compactMap) + query.Dest = compactMap } else if t == "[]map[string]interface {}" { rows := source.([]map[string]interface{}) _rows := make([]map[string]interface{}, len(rows)) lo.ForEach[map[string]interface{}](rows, func(item map[string]interface{}, index int) { - _rows[index] = lo.OmitBy[string, interface{}](item, func(key string, value interface{}) bool { + compactMap := lo.OmitBy[string, interface{}](item, func(key string, value interface{}) bool { return value == nil || reflect.ValueOf(value).IsZero() }) + maputils.ConvertInt642String(compactMap) + _rows[index] = compactMap }) query.Dest = _rows } diff --git a/toolkit/caches/reflection.go b/toolkit/caches/reflection.go index cececda3..cda21929 100644 --- a/toolkit/caches/reflection.go +++ b/toolkit/caches/reflection.go @@ -11,7 +11,7 @@ import ( ) func SetPointedValue(dest interface{}, src interface{}) { - copier.DeepCopy(src, dest) + copier.DeepCopyAsJson(src, dest) } func deepCopy(src, dst interface{}) error { diff --git a/toolkit/copier/copier.go b/toolkit/copier/copier.go index 5566cc34..ec67557d 100644 --- a/toolkit/copier/copier.go +++ b/toolkit/copier/copier.go @@ -15,6 +15,21 @@ import ( var json = sonic.ConfigDefault +// DeepCopyAsJson src to target with json marshal and unmarshal +func DeepCopyAsJson(src, target interface{}) error { + if src == nil || target == nil { + return nil + } + b, err := json.Marshal(src) + if err != nil { + return errors.WithStack(err) + } + if reflect.ValueOf(target).Kind() != reflect.Ptr { + return errors.New("Target should be a pointer") + } + return json.Unmarshal(b, target) +} + // DeepCopy src to target with json marshal and unmarshal func DeepCopy(src, target interface{}) error { if src == nil || target == nil { diff --git a/toolkit/maputils/maputils.go b/toolkit/maputils/maputils.go index d8740327..1dfbb353 100644 --- a/toolkit/maputils/maputils.go +++ b/toolkit/maputils/maputils.go @@ -2,6 +2,8 @@ package maputils import ( "github.com/goccy/go-reflect" + "github.com/samber/lo" + "strconv" "github.com/unionj-cloud/go-doudou/v2/toolkit/sliceutils" ) @@ -152,3 +154,40 @@ func mapify(i interface{}) (map[string]interface{}, bool) { } return map[string]interface{}{}, false } + +func ConvertInt642String(data map[string]interface{}) { + lo.ForEach(lo.Entries(data), func(item lo.Entry[string, interface{}], index int) { + if item.Value != nil { + data[item.Key] = convertInt642String(item.Value) + } + }) +} + +func convertInt642String(data interface{}) interface{} { + switch v := data.(type) { + case int64: + return strconv.FormatInt(v, 10) + case *int64: + if v != nil { + return lo.ToPtr(strconv.FormatInt(*v, 10)) + } else { + return (*string)(nil) + } + case []int64: + return lo.Map[int64, string](v, func(item int64, index int) string { + return strconv.FormatInt(item, 10) + }) + case []*int64: + return lo.Map[*int64, *string](v, func(item *int64, index int) *string { + if item != nil { + return lo.ToPtr(strconv.FormatInt(*item, 10)) + } + return (*string)(nil) + }) + case []interface{}: + return lo.Map[interface{}, interface{}](v, func(item interface{}, index int) interface{} { + return convertInt642String(item) + }) + } + return data +}