我会像这样编写一个自定义元帅函数:操场
package main
import (
"encoding/json"
"fmt"
"reflect"
"strings"
)
type Alpha struct {
Name string `json:"name"`
SkipWhenMarshal string `json:"SkipWhenMarshal,skip"`
}
func main() {
var a Alpha
a.Name = "John"
a.SkipWhenMarshal = "Snow"
out, _ := marshal(a)
fmt.Println(string(out))
var b Alpha
json.Unmarshal([]byte(`{"Name":"Samwell","SkipWhenMarshal":"Tarly"}`), &b)
fmt.Println(b)
}
// custom marshaling function for json that accepts an additional tag named skip to ignore the field
func marshal(v Alpha) ([]byte, error) {
m := map[string]interface{}{}
ut := reflect.TypeOf(v)
uv := reflect.ValueOf(v)
for i := 0; i < ut.NumField(); i++ {
field := ut.Field(i)
js, ok := field.Tag.Lookup("json")
if !ok || !strings.Contains(js, "skip") {
intf := uv.Field(i).Interface()
switch val := intf.(type) {
case int, int8, uint8:
m[field.Name] = val
case string:
m[field.Name] = val
}
}
}
return json.Marshal(m)
}
它基本上将结构重建为没有跳过字段的映射,并将其传递给原始的 Marshal 函数。
现在只需将 SKIP 标签添加到任何字段,它应该可以工作。
你只需要改进这部分:
switch val := intf.(type) {
因为这仅假设您只有字符串或整数作为字段。处理更多类型会更理想。