blob: c44ef5c989a46a629432c809faed5f77c0b676b8 [file] [log] [blame]
Zack Williamse940c7a2019-08-21 14:25:39 -07001package jsoniter
2
3import (
4 "reflect"
5 "unsafe"
6)
7
8type objectLazyAny struct {
9 baseAny
10 cfg *frozenConfig
11 buf []byte
12 err error
13}
14
15func (any *objectLazyAny) ValueType() ValueType {
16 return ObjectValue
17}
18
19func (any *objectLazyAny) MustBeValid() Any {
20 return any
21}
22
23func (any *objectLazyAny) LastError() error {
24 return any.err
25}
26
27func (any *objectLazyAny) ToBool() bool {
28 return true
29}
30
31func (any *objectLazyAny) ToInt() int {
32 return 0
33}
34
35func (any *objectLazyAny) ToInt32() int32 {
36 return 0
37}
38
39func (any *objectLazyAny) ToInt64() int64 {
40 return 0
41}
42
43func (any *objectLazyAny) ToUint() uint {
44 return 0
45}
46
47func (any *objectLazyAny) ToUint32() uint32 {
48 return 0
49}
50
51func (any *objectLazyAny) ToUint64() uint64 {
52 return 0
53}
54
55func (any *objectLazyAny) ToFloat32() float32 {
56 return 0
57}
58
59func (any *objectLazyAny) ToFloat64() float64 {
60 return 0
61}
62
63func (any *objectLazyAny) ToString() string {
64 return *(*string)(unsafe.Pointer(&any.buf))
65}
66
67func (any *objectLazyAny) ToVal(obj interface{}) {
68 iter := any.cfg.BorrowIterator(any.buf)
69 defer any.cfg.ReturnIterator(iter)
70 iter.ReadVal(obj)
71}
72
73func (any *objectLazyAny) Get(path ...interface{}) Any {
74 if len(path) == 0 {
75 return any
76 }
77 switch firstPath := path[0].(type) {
78 case string:
79 iter := any.cfg.BorrowIterator(any.buf)
80 defer any.cfg.ReturnIterator(iter)
81 valueBytes := locateObjectField(iter, firstPath)
82 if valueBytes == nil {
83 return newInvalidAny(path)
84 }
85 iter.ResetBytes(valueBytes)
86 return locatePath(iter, path[1:])
87 case int32:
88 if '*' == firstPath {
89 mappedAll := map[string]Any{}
90 iter := any.cfg.BorrowIterator(any.buf)
91 defer any.cfg.ReturnIterator(iter)
92 iter.ReadMapCB(func(iter *Iterator, field string) bool {
93 mapped := locatePath(iter, path[1:])
94 if mapped.ValueType() != InvalidValue {
95 mappedAll[field] = mapped
96 }
97 return true
98 })
99 return wrapMap(mappedAll)
100 }
101 return newInvalidAny(path)
102 default:
103 return newInvalidAny(path)
104 }
105}
106
107func (any *objectLazyAny) Keys() []string {
108 keys := []string{}
109 iter := any.cfg.BorrowIterator(any.buf)
110 defer any.cfg.ReturnIterator(iter)
111 iter.ReadMapCB(func(iter *Iterator, field string) bool {
112 iter.Skip()
113 keys = append(keys, field)
114 return true
115 })
116 return keys
117}
118
119func (any *objectLazyAny) Size() int {
120 size := 0
121 iter := any.cfg.BorrowIterator(any.buf)
122 defer any.cfg.ReturnIterator(iter)
123 iter.ReadObjectCB(func(iter *Iterator, field string) bool {
124 iter.Skip()
125 size++
126 return true
127 })
128 return size
129}
130
131func (any *objectLazyAny) WriteTo(stream *Stream) {
132 stream.Write(any.buf)
133}
134
135func (any *objectLazyAny) GetInterface() interface{} {
136 iter := any.cfg.BorrowIterator(any.buf)
137 defer any.cfg.ReturnIterator(iter)
138 return iter.Read()
139}
140
141type objectAny struct {
142 baseAny
143 err error
144 val reflect.Value
145}
146
147func wrapStruct(val interface{}) *objectAny {
148 return &objectAny{baseAny{}, nil, reflect.ValueOf(val)}
149}
150
151func (any *objectAny) ValueType() ValueType {
152 return ObjectValue
153}
154
155func (any *objectAny) MustBeValid() Any {
156 return any
157}
158
159func (any *objectAny) Parse() *Iterator {
160 return nil
161}
162
163func (any *objectAny) LastError() error {
164 return any.err
165}
166
167func (any *objectAny) ToBool() bool {
168 return any.val.NumField() != 0
169}
170
171func (any *objectAny) ToInt() int {
172 return 0
173}
174
175func (any *objectAny) ToInt32() int32 {
176 return 0
177}
178
179func (any *objectAny) ToInt64() int64 {
180 return 0
181}
182
183func (any *objectAny) ToUint() uint {
184 return 0
185}
186
187func (any *objectAny) ToUint32() uint32 {
188 return 0
189}
190
191func (any *objectAny) ToUint64() uint64 {
192 return 0
193}
194
195func (any *objectAny) ToFloat32() float32 {
196 return 0
197}
198
199func (any *objectAny) ToFloat64() float64 {
200 return 0
201}
202
203func (any *objectAny) ToString() string {
204 str, err := MarshalToString(any.val.Interface())
205 any.err = err
206 return str
207}
208
209func (any *objectAny) Get(path ...interface{}) Any {
210 if len(path) == 0 {
211 return any
212 }
213 switch firstPath := path[0].(type) {
214 case string:
215 field := any.val.FieldByName(firstPath)
216 if !field.IsValid() {
217 return newInvalidAny(path)
218 }
219 return Wrap(field.Interface())
220 case int32:
221 if '*' == firstPath {
222 mappedAll := map[string]Any{}
223 for i := 0; i < any.val.NumField(); i++ {
224 field := any.val.Field(i)
225 if field.CanInterface() {
226 mapped := Wrap(field.Interface()).Get(path[1:]...)
227 if mapped.ValueType() != InvalidValue {
228 mappedAll[any.val.Type().Field(i).Name] = mapped
229 }
230 }
231 }
232 return wrapMap(mappedAll)
233 }
234 return newInvalidAny(path)
235 default:
236 return newInvalidAny(path)
237 }
238}
239
240func (any *objectAny) Keys() []string {
241 keys := make([]string, 0, any.val.NumField())
242 for i := 0; i < any.val.NumField(); i++ {
243 keys = append(keys, any.val.Type().Field(i).Name)
244 }
245 return keys
246}
247
248func (any *objectAny) Size() int {
249 return any.val.NumField()
250}
251
252func (any *objectAny) WriteTo(stream *Stream) {
253 stream.WriteVal(any.val)
254}
255
256func (any *objectAny) GetInterface() interface{} {
257 return any.val.Interface()
258}
259
260type mapAny struct {
261 baseAny
262 err error
263 val reflect.Value
264}
265
266func wrapMap(val interface{}) *mapAny {
267 return &mapAny{baseAny{}, nil, reflect.ValueOf(val)}
268}
269
270func (any *mapAny) ValueType() ValueType {
271 return ObjectValue
272}
273
274func (any *mapAny) MustBeValid() Any {
275 return any
276}
277
278func (any *mapAny) Parse() *Iterator {
279 return nil
280}
281
282func (any *mapAny) LastError() error {
283 return any.err
284}
285
286func (any *mapAny) ToBool() bool {
287 return true
288}
289
290func (any *mapAny) ToInt() int {
291 return 0
292}
293
294func (any *mapAny) ToInt32() int32 {
295 return 0
296}
297
298func (any *mapAny) ToInt64() int64 {
299 return 0
300}
301
302func (any *mapAny) ToUint() uint {
303 return 0
304}
305
306func (any *mapAny) ToUint32() uint32 {
307 return 0
308}
309
310func (any *mapAny) ToUint64() uint64 {
311 return 0
312}
313
314func (any *mapAny) ToFloat32() float32 {
315 return 0
316}
317
318func (any *mapAny) ToFloat64() float64 {
319 return 0
320}
321
322func (any *mapAny) ToString() string {
323 str, err := MarshalToString(any.val.Interface())
324 any.err = err
325 return str
326}
327
328func (any *mapAny) Get(path ...interface{}) Any {
329 if len(path) == 0 {
330 return any
331 }
332 switch firstPath := path[0].(type) {
333 case int32:
334 if '*' == firstPath {
335 mappedAll := map[string]Any{}
336 for _, key := range any.val.MapKeys() {
337 keyAsStr := key.String()
338 element := Wrap(any.val.MapIndex(key).Interface())
339 mapped := element.Get(path[1:]...)
340 if mapped.ValueType() != InvalidValue {
341 mappedAll[keyAsStr] = mapped
342 }
343 }
344 return wrapMap(mappedAll)
345 }
346 return newInvalidAny(path)
347 default:
348 value := any.val.MapIndex(reflect.ValueOf(firstPath))
349 if !value.IsValid() {
350 return newInvalidAny(path)
351 }
352 return Wrap(value.Interface())
353 }
354}
355
356func (any *mapAny) Keys() []string {
357 keys := make([]string, 0, any.val.Len())
358 for _, key := range any.val.MapKeys() {
359 keys = append(keys, key.String())
360 }
361 return keys
362}
363
364func (any *mapAny) Size() int {
365 return any.val.Len()
366}
367
368func (any *mapAny) WriteTo(stream *Stream) {
369 stream.WriteVal(any.val)
370}
371
372func (any *mapAny) GetInterface() interface{} {
373 return any.val.Interface()
374}