-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathfield.go
78 lines (70 loc) · 1.77 KB
/
field.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
package godiff
import (
"github.com/viant/structology"
"github.com/viant/xunsafe"
"reflect"
"strings"
)
type (
field struct {
name string
from accessor
to accessor
Kind reflect.Kind
tag *Tag
differ *Differ
}
matcher struct {
index map[string]*accessor
}
)
func newField(fromField *xunsafe.Field, fromAccessor accessor, toAccessor accessor, tag *Tag) *field {
aField := &field{
name: fromField.Name,
from: fromAccessor,
to: toAccessor,
tag: tag,
differ: nil,
}
if tag.Name != "" {
aField.name = tag.Name
}
if structType(fromField.Type) != nil && !isTimeType(fromField.Type) {
aField.Kind = reflect.Struct
} else if sliceType(fromField.Type) != nil {
aField.Kind = reflect.Slice
} else if interfaceType(fromField.Type) != nil {
aField.Kind = reflect.Interface
} else if mapType(fromField.Type) != nil {
aField.Kind = reflect.Map
}
return aField
}
func (m *matcher) build(xStruct *xunsafe.Struct, config *Config) {
m.index = make(map[string]*accessor, 3*len(xStruct.Fields))
for i := range xStruct.Fields {
xField := &xStruct.Fields[i]
tag, _ := ParseTag(string(xField.Tag))
tag.init(config)
tag.PresenceMarker = structology.IsSetMarker(xField.Tag)
fieldAccessor := newAccessor(i, xField, tag)
m.index[xField.Name] = &fieldAccessor
m.index[strings.ToLower(xField.Name)] = &fieldAccessor
m.index[m.normKey(xField.Name)] = &fieldAccessor
}
}
func (m *matcher) match(name string) *accessor {
if result, ok := m.index[name]; ok {
return result
}
if result, ok := m.index[strings.ToLower(name)]; ok {
return result
}
if result, ok := m.index[m.normKey(name)]; ok {
return result
}
return nil
}
func (m *matcher) normKey(key string) string {
return strings.ReplaceAll(strings.ToLower(key), "_", "")
}