-
Notifications
You must be signed in to change notification settings - Fork 4
/
Copy pathnull_interface.go
164 lines (142 loc) · 3.88 KB
/
null_interface.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
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
package typ
import (
"database/sql/driver"
"encoding/json"
)
// InterfaceCommon represents an interface{} that may be null.
type InterfaceCommon struct {
P interface{}
Error error
}
// Set saves value into current struct
func (n *InterfaceCommon) Set(value interface{}) {
n.P = value
}
// V returns value of underlying type if it was set, otherwise default value
func (n InterfaceCommon) V() interface{} {
return n.P
}
// Present determines whether a value has been set
func (n InterfaceCommon) Present() bool {
return n.P != nil
}
// Valid determines whether a value has been valid
func (n InterfaceCommon) Valid() bool {
return n.Err() == nil
}
// Value implements the sql driver Valuer interface.
func (n InterfaceCommon) Value() (driver.Value, error) {
if n.Err() == nil && !driver.IsValue(n.V()) {
return nil, ErrConvert
}
return n.V(), nil
}
// Scan implements the sql Scanner interface.
func (n *InterfaceCommon) Scan(value interface{}) error {
n.P, n.Error = nil, nil
if !driver.IsValue(value) {
n.Error = ErrInvalidArgument
return n.Err()
}
n.P = value
return nil
}
// UnmarshalJSON implements the json Unmarshaler interface.
func (n *InterfaceCommon) UnmarshalJSON(b []byte) error {
n.P, n.Error = nil, nil
var value interface{}
if err := json.Unmarshal(b, &value); err != nil {
n.Error = err
return err
}
if value == nil {
return nil
}
n.P = value
return nil
}
// MarshalJSON implements the json Marshaler interface.
func (n InterfaceCommon) MarshalJSON() ([]byte, error) {
return json.Marshal(n.V())
}
// Typ returns new instance with himself value.
// If current value is invalid, nil *Type returned
func (n InterfaceCommon) Typ(options ...Option) *Type {
if n.Err() != nil {
return NewType(nil, n.Err())
}
return NewType(n.V(), n.Err(), options...)
}
// Err returns underlying error.
func (n InterfaceCommon) Err() error {
return n.Error
}
// InterfaceAccessor accessor of interface{} type.
type InterfaceAccessor interface {
Common
V() interface{}
Set(value interface{})
Clone() InterfaceAccessor
}
// NullInterface represents an interface{} that may be null.
type NullInterface struct {
InterfaceCommon
}
// Value implements the sql driver Valuer interface.
func (n NullInterface) Value() (driver.Value, error) {
if n.Err() == nil && !driver.IsValue(n.V()) {
return nil, ErrConvert
}
if n.Err() != nil || !n.Present() {
return nil, n.Err()
}
return n.InterfaceCommon.Value()
}
// MarshalJSON implements the json Marshaler interface.
func (n NullInterface) MarshalJSON() ([]byte, error) {
if n.Err() != nil || !n.Present() {
return json.Marshal(nil)
}
return n.InterfaceCommon.MarshalJSON()
}
// Clone returns new instance of NullInterface with preserved value & error
func (n NullInterface) Clone() InterfaceAccessor {
nv := &NullInterface{}
if n.Present() {
nv.Set(n.V())
}
nv.Error = n.Error
return nv
}
// NInterface returns NullInterface under InterfaceAccessor from interface{}
func NInterface(value interface{}) InterfaceAccessor {
return &NullInterface{InterfaceCommon{P: value}}
}
// NotNullInterface represents an interface{} that may be null.
type NotNullInterface struct {
InterfaceCommon
}
// Clone returns new instance of NotNullInterface with preserved value & error
func (n NotNullInterface) Clone() InterfaceAccessor {
nv := &NotNullInterface{}
if n.Present() {
nv.Set(n.V())
}
nv.Error = n.Error
return nv
}
// NNInterface returns NotNullInterface under InterfaceAccessor from interface{}
func NNInterface(value interface{}) InterfaceAccessor {
return &NotNullInterface{InterfaceCommon{P: value}}
}
// InterfaceSlice returns slice of interface{} with filled values from slice of InterfaceAccessor
func InterfaceSlice(null []InterfaceAccessor, valid bool) []interface{} {
slice := make([]interface{}, 0, len(null))
for _, v := range null {
if valid && v.Err() != nil {
continue
}
slice = append(slice, v.V())
}
return slice
}