1use super::JsonValueExt;
2use crate::{
3 JsonValue, Map, Record, Uuid,
4 datetime::{self, Date, DateTime, Time},
5 helper,
6 model::Model,
7 validation::Validation,
8};
9use chrono::NaiveDateTime;
10use convert_case::{Case, Casing};
11use rust_decimal::Decimal;
12use std::{
13 borrow::Cow,
14 mem,
15 net::{AddrParseError, IpAddr, Ipv4Addr, Ipv6Addr},
16 num::{ParseFloatError, ParseIntError},
17 str::{FromStr, ParseBoolError},
18 time::Duration,
19};
20use url::Url;
21
22pub trait JsonObjectExt {
24 fn get_bool(&self, key: &str) -> Option<bool>;
26
27 fn get_u8(&self, key: &str) -> Option<u8>;
30
31 fn get_u16(&self, key: &str) -> Option<u16>;
34
35 fn get_u32(&self, key: &str) -> Option<u32>;
38
39 fn get_u64(&self, key: &str) -> Option<u64>;
42
43 fn get_usize(&self, key: &str) -> Option<usize>;
46
47 fn get_i8(&self, key: &str) -> Option<i8>;
50
51 fn get_i16(&self, key: &str) -> Option<i16>;
54
55 fn get_i32(&self, key: &str) -> Option<i32>;
58
59 fn get_i64(&self, key: &str) -> Option<i64>;
61
62 fn get_isize(&self, key: &str) -> Option<isize>;
65
66 fn get_f32(&self, key: &str) -> Option<f32>;
69
70 fn get_f64(&self, key: &str) -> Option<f64>;
72
73 fn get_str(&self, key: &str) -> Option<&str>;
75
76 fn get_uuid(&self, key: &str) -> Option<Uuid>;
79
80 fn get_date(&self, key: &str) -> Option<Date>;
83
84 fn get_time(&self, key: &str) -> Option<Time>;
87
88 fn get_date_time(&self, key: &str) -> Option<DateTime>;
91
92 fn get_naive_date_time(&self, key: &str) -> Option<NaiveDateTime>;
95
96 fn get_duration(&self, key: &str) -> Option<Duration>;
99
100 fn get_array(&self, key: &str) -> Option<&Vec<JsonValue>>;
102
103 fn get_u64_array(&self, key: &str) -> Option<Vec<u64>>;
105
106 fn get_i64_array(&self, key: &str) -> Option<Vec<i64>>;
108
109 fn get_f32_array(&self, key: &str) -> Option<Vec<f32>>;
111
112 fn get_f64_array(&self, key: &str) -> Option<Vec<f64>>;
114
115 fn get_str_array(&self, key: &str) -> Option<Vec<&str>>;
117
118 fn get_map_array(&self, key: &str) -> Option<Vec<&Map>>;
120
121 fn get_object(&self, key: &str) -> Option<&Map>;
123
124 fn get_populated(&self, key: &str) -> Option<&Map>;
126
127 fn get_translated(&self, key: &str) -> Option<&str>;
129
130 fn parse_bool(&self, key: &str) -> Option<Result<bool, ParseBoolError>>;
132
133 fn parse_u8(&self, key: &str) -> Option<Result<u8, ParseIntError>>;
135
136 fn parse_u16(&self, key: &str) -> Option<Result<u16, ParseIntError>>;
138
139 fn parse_u32(&self, key: &str) -> Option<Result<u32, ParseIntError>>;
141
142 fn parse_u64(&self, key: &str) -> Option<Result<u64, ParseIntError>>;
144
145 fn parse_usize(&self, key: &str) -> Option<Result<usize, ParseIntError>>;
147
148 fn parse_i8(&self, key: &str) -> Option<Result<i8, ParseIntError>>;
150
151 fn parse_i16(&self, key: &str) -> Option<Result<i16, ParseIntError>>;
153
154 fn parse_i32(&self, key: &str) -> Option<Result<i32, ParseIntError>>;
156
157 fn parse_i64(&self, key: &str) -> Option<Result<i64, ParseIntError>>;
159
160 fn parse_isize(&self, key: &str) -> Option<Result<isize, ParseIntError>>;
162
163 fn parse_f32(&self, key: &str) -> Option<Result<f32, ParseFloatError>>;
165
166 fn parse_f64(&self, key: &str) -> Option<Result<f64, ParseFloatError>>;
168
169 fn parse_string(&self, key: &str) -> Option<Cow<'_, str>>;
172
173 fn parse_array<T: FromStr>(&self, key: &str) -> Option<Result<Vec<T>, <T as FromStr>::Err>>;
176
177 fn parse_str_array(&self, key: &str) -> Option<Vec<&str>>;
180
181 fn parse_enum_values(&self, key: &str) -> Option<Vec<JsonValue>>;
185
186 fn parse_object(&self, key: &str) -> Option<&Map>;
189
190 fn parse_uuid(&self, key: &str) -> Option<Result<Uuid, uuid::Error>>;
193
194 fn parse_decimal(&self, key: &str) -> Option<Result<Decimal, rust_decimal::Error>>;
196
197 fn parse_date(&self, key: &str) -> Option<Result<Date, chrono::format::ParseError>>;
199
200 fn parse_time(&self, key: &str) -> Option<Result<Time, chrono::format::ParseError>>;
202
203 fn parse_date_time(&self, key: &str) -> Option<Result<DateTime, chrono::format::ParseError>>;
205
206 fn parse_naive_date_time(
208 &self,
209 key: &str,
210 ) -> Option<Result<NaiveDateTime, chrono::format::ParseError>>;
211
212 fn parse_duration(&self, key: &str) -> Option<Result<Duration, datetime::ParseDurationError>>;
214
215 fn parse_url(&self, key: &str) -> Option<Result<Url, url::ParseError>>;
217
218 fn parse_ip(&self, key: &str) -> Option<Result<IpAddr, AddrParseError>>;
220
221 fn parse_ipv4(&self, key: &str) -> Option<Result<Ipv4Addr, AddrParseError>>;
223
224 fn parse_ipv6(&self, key: &str) -> Option<Result<Ipv6Addr, AddrParseError>>;
226
227 fn parse_model<M: Model>(&self, key: &str) -> Option<Result<M, Validation>>;
229
230 fn pointer(&self, pointer: &str) -> Option<&JsonValue>;
236
237 fn pointer_mut(&mut self, pointer: &str) -> Option<&mut JsonValue>;
239
240 fn upsert(&mut self, key: impl Into<String>, value: impl Into<JsonValue>) -> Option<JsonValue>;
244
245 fn clone_from_populated<K: AsRef<str>>(&mut self, key: &str, fields: &[K]);
247
248 fn extract_from_populated<K: AsRef<str>>(&mut self, key: &str, fields: &[K]);
250
251 fn clone_entries<K: AsRef<str>>(&mut self, keys: &[K]) -> Self;
253
254 fn extract_entries<K: AsRef<str>>(&mut self, keys: &[K]) -> Self;
256
257 fn remove_entries<K: AsRef<str>>(&mut self, keys: &[K]);
259
260 fn rename_keys(&mut self, case: Case);
262
263 fn read_as_model<M: Model>(&self) -> Result<M, Validation>;
265
266 fn to_string(&self) -> String;
268
269 fn to_query_string(&self) -> String;
271
272 fn into_avro_record(self) -> Record;
274
275 fn from_entry(key: impl Into<String>, value: impl Into<JsonValue>) -> Self;
277
278 fn from_entries(entries: JsonValue) -> Self;
281
282 fn data_entry(value: Map) -> Self;
284
285 fn data_entries(values: Vec<Map>) -> Self;
287
288 fn data_item(value: impl Into<JsonValue>) -> Self;
290
291 fn data_items<T: Into<JsonValue>>(values: Vec<T>) -> Self;
293}
294
295impl JsonObjectExt for Map {
296 #[inline]
297 fn get_bool(&self, key: &str) -> Option<bool> {
298 self.get(key).and_then(|v| v.as_bool())
299 }
300
301 #[inline]
302 fn get_u8(&self, key: &str) -> Option<u8> {
303 self.get(key)
304 .and_then(|v| v.as_u64())
305 .and_then(|i| u8::try_from(i).ok())
306 }
307
308 #[inline]
309 fn get_u16(&self, key: &str) -> Option<u16> {
310 self.get(key)
311 .and_then(|v| v.as_u64())
312 .and_then(|i| u16::try_from(i).ok())
313 }
314
315 #[inline]
316 fn get_u32(&self, key: &str) -> Option<u32> {
317 self.get(key)
318 .and_then(|v| v.as_u64())
319 .and_then(|i| u32::try_from(i).ok())
320 }
321
322 #[inline]
323 fn get_u64(&self, key: &str) -> Option<u64> {
324 self.get(key).and_then(|v| v.as_u64())
325 }
326
327 #[inline]
328 fn get_usize(&self, key: &str) -> Option<usize> {
329 self.get(key)
330 .and_then(|v| v.as_u64())
331 .and_then(|i| usize::try_from(i).ok())
332 }
333
334 #[inline]
335 fn get_i8(&self, key: &str) -> Option<i8> {
336 self.get(key)
337 .and_then(|v| v.as_i64())
338 .and_then(|i| i8::try_from(i).ok())
339 }
340
341 #[inline]
342 fn get_i16(&self, key: &str) -> Option<i16> {
343 self.get(key)
344 .and_then(|v| v.as_i64())
345 .and_then(|i| i16::try_from(i).ok())
346 }
347
348 #[inline]
349 fn get_i32(&self, key: &str) -> Option<i32> {
350 self.get(key)
351 .and_then(|v| v.as_i64())
352 .and_then(|i| i32::try_from(i).ok())
353 }
354
355 #[inline]
356 fn get_i64(&self, key: &str) -> Option<i64> {
357 self.get(key).and_then(|v| v.as_i64())
358 }
359
360 #[inline]
361 fn get_isize(&self, key: &str) -> Option<isize> {
362 self.get(key)
363 .and_then(|v| v.as_i64())
364 .and_then(|i| isize::try_from(i).ok())
365 }
366
367 #[inline]
368 fn get_f32(&self, key: &str) -> Option<f32> {
369 self.get(key).and_then(|v| v.as_f64()).map(|f| f as f32)
370 }
371
372 #[inline]
373 fn get_f64(&self, key: &str) -> Option<f64> {
374 self.get(key).and_then(|v| v.as_f64())
375 }
376
377 #[inline]
378 fn get_str(&self, key: &str) -> Option<&str> {
379 self.get(key).and_then(|v| v.as_str())
380 }
381
382 #[inline]
383 fn get_uuid(&self, key: &str) -> Option<Uuid> {
384 self.get_str(key).and_then(|s| s.parse().ok())
385 }
386
387 #[inline]
388 fn get_date(&self, key: &str) -> Option<Date> {
389 self.get_str(key).and_then(|s| s.parse().ok())
390 }
391
392 #[inline]
393 fn get_time(&self, key: &str) -> Option<Time> {
394 self.get_str(key).and_then(|s| s.parse().ok())
395 }
396
397 #[inline]
398 fn get_date_time(&self, key: &str) -> Option<DateTime> {
399 self.get_str(key).and_then(|s| s.parse().ok())
400 }
401
402 #[inline]
403 fn get_naive_date_time(&self, key: &str) -> Option<NaiveDateTime> {
404 self.get_str(key).and_then(|s| s.parse().ok())
405 }
406
407 #[inline]
408 fn get_duration(&self, key: &str) -> Option<Duration> {
409 self.get_str(key)
410 .and_then(|s| datetime::parse_duration(s).ok())
411 }
412
413 #[inline]
414 fn get_array(&self, key: &str) -> Option<&Vec<JsonValue>> {
415 self.get(key).and_then(|v| v.as_array())
416 }
417
418 #[inline]
419 fn get_u64_array(&self, key: &str) -> Option<Vec<u64>> {
420 self.get_array(key)
421 .map(|values| values.iter().filter_map(|v| v.as_u64()).collect())
422 }
423
424 #[inline]
425 fn get_i64_array(&self, key: &str) -> Option<Vec<i64>> {
426 self.get_array(key)
427 .map(|values| values.iter().filter_map(|v| v.as_i64()).collect())
428 }
429
430 #[inline]
431 fn get_f32_array(&self, key: &str) -> Option<Vec<f32>> {
432 self.get_array(key).map(|values| {
433 values
434 .iter()
435 .filter_map(|v| v.as_f64().map(|f| f as f32))
436 .collect()
437 })
438 }
439
440 #[inline]
441 fn get_f64_array(&self, key: &str) -> Option<Vec<f64>> {
442 self.get_array(key)
443 .map(|values| values.iter().filter_map(|v| v.as_f64()).collect())
444 }
445
446 #[inline]
447 fn get_str_array(&self, key: &str) -> Option<Vec<&str>> {
448 self.get_array(key)
449 .map(|values| values.iter().filter_map(|v| v.as_str()).collect())
450 }
451
452 #[inline]
453 fn get_map_array(&self, key: &str) -> Option<Vec<&Map>> {
454 self.get_array(key).map(|values| {
455 values
456 .iter()
457 .filter_map(|v| v.as_object())
458 .collect::<Vec<_>>()
459 })
460 }
461
462 #[inline]
463 fn get_object(&self, key: &str) -> Option<&Map> {
464 self.get(key).and_then(|v| v.as_object())
465 }
466
467 #[inline]
468 fn get_populated(&self, key: &str) -> Option<&Map> {
469 let populated_field = [key, "_populated"].concat();
470 self.get_object(&populated_field)
471 }
472
473 #[inline]
474 fn get_translated(&self, key: &str) -> Option<&str> {
475 let translated_field = [key, "_translated"].concat();
476 self.get_str(&translated_field)
477 }
478
479 fn parse_bool(&self, key: &str) -> Option<Result<bool, ParseBoolError>> {
480 let value = self.get(key);
481 value
482 .and_then(|v| v.as_bool())
483 .map(Ok)
484 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
485 }
486
487 fn parse_u8(&self, key: &str) -> Option<Result<u8, ParseIntError>> {
488 let value = self.get(key);
489 value
490 .and_then(|v| v.as_u64())
491 .and_then(|i| u8::try_from(i).ok())
492 .map(Ok)
493 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
494 }
495
496 fn parse_u16(&self, key: &str) -> Option<Result<u16, ParseIntError>> {
497 let value = self.get(key);
498 value
499 .and_then(|v| v.as_u64())
500 .and_then(|i| u16::try_from(i).ok())
501 .map(Ok)
502 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
503 }
504
505 fn parse_u32(&self, key: &str) -> Option<Result<u32, ParseIntError>> {
506 let value = self.get(key);
507 value
508 .and_then(|v| v.as_u64())
509 .and_then(|i| u32::try_from(i).ok())
510 .map(Ok)
511 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
512 }
513
514 fn parse_u64(&self, key: &str) -> Option<Result<u64, ParseIntError>> {
515 let value = self.get(key);
516 value
517 .and_then(|v| v.as_u64())
518 .map(Ok)
519 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
520 }
521
522 fn parse_usize(&self, key: &str) -> Option<Result<usize, ParseIntError>> {
523 let value = self.get(key);
524 value
525 .and_then(|v| v.as_u64())
526 .and_then(|i| usize::try_from(i).ok())
527 .map(Ok)
528 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
529 }
530
531 fn parse_i8(&self, key: &str) -> Option<Result<i8, ParseIntError>> {
532 let value = self.get(key);
533 value
534 .and_then(|v| v.as_i64())
535 .and_then(|i| i8::try_from(i).ok())
536 .map(Ok)
537 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
538 }
539
540 fn parse_i16(&self, key: &str) -> Option<Result<i16, ParseIntError>> {
541 let value = self.get(key);
542 value
543 .and_then(|v| v.as_i64())
544 .and_then(|i| i16::try_from(i).ok())
545 .map(Ok)
546 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
547 }
548
549 fn parse_i32(&self, key: &str) -> Option<Result<i32, ParseIntError>> {
550 let value = self.get(key);
551 value
552 .and_then(|v| v.as_i64())
553 .and_then(|i| i32::try_from(i).ok())
554 .map(Ok)
555 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
556 }
557
558 fn parse_i64(&self, key: &str) -> Option<Result<i64, ParseIntError>> {
559 let value = self.get(key);
560 value
561 .and_then(|v| v.as_i64())
562 .map(Ok)
563 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
564 }
565
566 fn parse_isize(&self, key: &str) -> Option<Result<isize, ParseIntError>> {
567 let value = self.get(key);
568 value
569 .and_then(|v| v.as_i64())
570 .and_then(|i| isize::try_from(i).ok())
571 .map(Ok)
572 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
573 }
574
575 fn parse_f32(&self, key: &str) -> Option<Result<f32, ParseFloatError>> {
576 let value = self.get(key);
577 value
578 .and_then(|v| v.as_f64())
579 .map(|f| Ok(f as f32))
580 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
581 }
582
583 fn parse_f64(&self, key: &str) -> Option<Result<f64, ParseFloatError>> {
584 let value = self.get(key);
585 value
586 .and_then(|v| v.as_f64())
587 .map(Ok)
588 .or_else(|| value.and_then(|v| v.as_str()).map(|s| s.parse()))
589 }
590
591 fn parse_string(&self, key: &str) -> Option<Cow<'_, str>> {
592 self.get(key)
593 .and_then(|v| {
594 v.as_str()
595 .map(|s| Cow::Borrowed(s.trim()))
596 .or_else(|| Some(v.to_string().into()))
597 })
598 .filter(|s| !s.is_empty())
599 }
600
601 fn parse_array<T: FromStr>(&self, key: &str) -> Option<Result<Vec<T>, <T as FromStr>::Err>> {
602 let values = match self.get(key)? {
603 JsonValue::String(s) => helper::parse_str_array(s, ',')
604 .into_iter()
605 .filter_map(|s| (!s.is_empty()).then_some(Cow::Borrowed(s)))
606 .collect::<Vec<_>>(),
607 JsonValue::Array(vec) => vec
608 .iter()
609 .filter(|v| !v.is_null())
610 .filter_map(|v| v.parse_string())
611 .collect::<Vec<_>>(),
612 _ => return None,
613 };
614 let mut vec = Vec::with_capacity(values.len());
615 for value in values {
616 match value.parse() {
617 Ok(v) => vec.push(v),
618 Err(err) => return Some(Err(err)),
619 }
620 }
621 (!vec.is_empty()).then_some(Ok(vec))
622 }
623
624 fn parse_str_array(&self, key: &str) -> Option<Vec<&str>> {
625 self.get(key)
626 .and_then(|v| match v {
627 JsonValue::String(s) => Some(helper::parse_str_array(s, ',')),
628 JsonValue::Array(v) => Some(v.iter().filter_map(|v| v.as_str()).collect()),
629 _ => None,
630 })
631 .and_then(|values| {
632 let vec = values.iter().map(|s| s.trim()).collect::<Vec<_>>();
633 (!vec.is_empty()).then_some(vec)
634 })
635 }
636
637 fn parse_enum_values(&self, key: &str) -> Option<Vec<JsonValue>> {
638 self.get(key)
639 .and_then(|v| match v {
640 JsonValue::String(s) => {
641 let values = helper::parse_str_array(s, '|');
642 let vec = values
643 .iter()
644 .map(|s| {
645 let s = s.trim();
646 if let Ok(integer) = s.parse::<i64>() {
647 JsonValue::Number(integer.into())
648 } else {
649 JsonValue::String(s.to_owned())
650 }
651 })
652 .collect::<Vec<_>>();
653 Some(vec)
654 }
655 JsonValue::Array(vec) => Some(vec.to_owned()),
656 _ => None,
657 })
658 .filter(|vec| !vec.is_empty())
659 }
660
661 #[inline]
662 fn parse_object(&self, key: &str) -> Option<&Map> {
663 self.get_object(key).filter(|o| !o.is_empty())
664 }
665
666 fn parse_uuid(&self, key: &str) -> Option<Result<Uuid, uuid::Error>> {
667 self.get_str(key)
668 .map(|s| s.trim_start_matches("urn:uuid:"))
669 .filter(|s| !s.chars().all(|c| c == '0' || c == '-'))
670 .map(|s| s.parse())
671 }
672
673 #[inline]
674 fn parse_decimal(&self, key: &str) -> Option<Result<Decimal, rust_decimal::Error>> {
675 self.get_str(key).map(|s| s.parse())
676 }
677
678 #[inline]
679 fn parse_date(&self, key: &str) -> Option<Result<Date, chrono::format::ParseError>> {
680 self.get_str(key).map(|s| s.parse())
681 }
682
683 #[inline]
684 fn parse_time(&self, key: &str) -> Option<Result<Time, chrono::format::ParseError>> {
685 self.get_str(key).map(|s| s.parse())
686 }
687
688 #[inline]
689 fn parse_date_time(&self, key: &str) -> Option<Result<DateTime, chrono::format::ParseError>> {
690 self.get_str(key).map(|s| s.parse())
691 }
692
693 #[inline]
694 fn parse_naive_date_time(
695 &self,
696 key: &str,
697 ) -> Option<Result<NaiveDateTime, chrono::format::ParseError>> {
698 self.get_str(key).map(|s| s.parse())
699 }
700
701 #[inline]
702 fn parse_duration(&self, key: &str) -> Option<Result<Duration, datetime::ParseDurationError>> {
703 self.get_str(key).map(datetime::parse_duration)
704 }
705
706 #[inline]
707 fn parse_url(&self, key: &str) -> Option<Result<Url, url::ParseError>> {
708 self.get_str(key).map(|s| s.parse())
709 }
710
711 #[inline]
712 fn parse_ip(&self, key: &str) -> Option<Result<IpAddr, AddrParseError>> {
713 self.get_str(key).map(|s| s.parse())
714 }
715
716 #[inline]
717 fn parse_ipv4(&self, key: &str) -> Option<Result<Ipv4Addr, AddrParseError>> {
718 self.get_str(key).map(|s| s.parse())
719 }
720
721 #[inline]
722 fn parse_ipv6(&self, key: &str) -> Option<Result<Ipv6Addr, AddrParseError>> {
723 self.get_str(key).map(|s| s.parse())
724 }
725
726 fn parse_model<M: Model>(&self, key: &str) -> Option<Result<M, Validation>> {
727 self.get_object(key).map(|data| {
728 let mut model = M::new();
729 let validation = model.read_map(data);
730 if validation.is_success() {
731 Ok(model)
732 } else {
733 Err(validation)
734 }
735 })
736 }
737
738 fn pointer(&self, pointer: &str) -> Option<&JsonValue> {
739 let path = pointer.strip_prefix('/')?;
740 if let Some(position) = path.find('/') {
741 let (key, pointer) = path.split_at(position);
742 self.get(key)?.pointer(pointer)
743 } else {
744 self.get(path)
745 }
746 }
747
748 fn pointer_mut(&mut self, pointer: &str) -> Option<&mut JsonValue> {
749 let path = pointer.strip_prefix('/')?;
750 if let Some(position) = path.find('/') {
751 let (key, pointer) = path.split_at(position);
752 self.get_mut(key)?.pointer_mut(pointer)
753 } else {
754 self.get_mut(path)
755 }
756 }
757
758 #[inline]
759 fn upsert(&mut self, key: impl Into<String>, value: impl Into<JsonValue>) -> Option<JsonValue> {
760 self.insert(key.into(), value.into())
761 }
762
763 fn clone_from_populated<K: AsRef<str>>(&mut self, key: &str, fields: &[K]) {
764 let mut object = Map::new();
765 if let Some(map) = self.get_populated(key) {
766 for field in fields {
767 let field = field.as_ref();
768 if let Some(value) = map.get(field) {
769 object.insert(field.to_owned(), value.to_owned());
770 }
771 }
772 }
773 self.append(&mut object);
774 }
775
776 fn extract_from_populated<K: AsRef<str>>(&mut self, key: &str, fields: &[K]) {
777 let mut object = Map::new();
778 let populated_field = [key, "_populated"].concat();
779 if let Some(&mut ref mut map) = self
780 .get_mut(&populated_field)
781 .and_then(|v| v.as_object_mut())
782 {
783 for field in fields {
784 let field = field.as_ref();
785 if let Some(value) = map.remove(field) {
786 object.insert(field.to_owned(), value);
787 }
788 }
789 }
790 self.append(&mut object);
791 }
792
793 #[inline]
794 fn clone_entries<K: AsRef<str>>(&mut self, keys: &[K]) -> Self {
795 let mut map = Map::new();
796 for key in keys {
797 let field = key.as_ref();
798 if let Some(value) = self.get(field) {
799 map.insert(field.to_owned(), value.to_owned());
800 }
801 }
802 map
803 }
804
805 #[inline]
806 fn extract_entries<K: AsRef<str>>(&mut self, keys: &[K]) -> Self {
807 let mut map = Map::new();
808 for key in keys {
809 let field = key.as_ref();
810 if let Some(value) = self.remove(field) {
811 map.insert(field.to_owned(), value);
812 }
813 }
814 map
815 }
816
817 #[inline]
818 fn remove_entries<K: AsRef<str>>(&mut self, keys: &[K]) {
819 for key in keys {
820 self.remove(key.as_ref());
821 }
822 }
823
824 #[inline]
825 fn rename_keys(&mut self, case: Case) {
826 for (key, value) in mem::take(self) {
827 self.insert(key.to_case(case), value);
828 }
829 }
830
831 fn read_as_model<M: Model>(&self) -> Result<M, Validation> {
832 let mut model = M::new();
833 let validation = model.read_map(self);
834 if validation.is_success() {
835 Ok(model)
836 } else {
837 Err(validation)
838 }
839 }
840
841 #[inline]
842 fn to_string(&self) -> String {
843 serde_json::to_string(&self).unwrap_or_default()
844 }
845
846 #[inline]
847 fn to_query_string(&self) -> String {
848 serde_qs::to_string(&self).unwrap_or_default()
849 }
850
851 fn into_avro_record(self) -> Record {
852 let mut record = Record::with_capacity(self.len());
853 for (field, value) in self.into_iter() {
854 record.push((field, value.into()));
855 }
856 record
857 }
858
859 #[inline]
860 fn from_entry(key: impl Into<String>, value: impl Into<JsonValue>) -> Self {
861 let mut map = Map::new();
862 map.insert(key.into(), value.into());
863 map
864 }
865
866 #[inline]
867 fn from_entries(entries: JsonValue) -> Self {
868 if let JsonValue::Object(map) = entries {
869 map
870 } else {
871 Map::new()
872 }
873 }
874
875 #[inline]
876 fn data_entry(value: Map) -> Self {
877 let mut map = Map::new();
878 map.insert("entry".to_owned(), value.into());
879 map
880 }
881
882 #[inline]
883 fn data_entries(values: Vec<Map>) -> Self {
884 let mut map = Map::new();
885 map.insert("num_entries".to_owned(), values.len().into());
886 map.insert("entries".to_owned(), values.into());
887 map
888 }
889
890 #[inline]
891 fn data_item(value: impl Into<JsonValue>) -> Self {
892 let mut map = Map::new();
893 map.insert("item".to_owned(), value.into());
894 map
895 }
896
897 #[inline]
898 fn data_items<T: Into<JsonValue>>(values: Vec<T>) -> Self {
899 let mut map = Map::new();
900 map.insert("num_items".to_owned(), values.len().into());
901 map.insert("items".to_owned(), values.into());
902 map
903 }
904}
905
906#[cfg(test)]
907mod tests {
908 use crate::{
909 Map,
910 extension::{JsonObjectExt, JsonValueExt},
911 };
912
913 #[test]
914 fn it_parses_str_array() {
915 let mut map = Map::new();
916 map.upsert("roles", vec!["admin", "", "worker"]);
917
918 assert_eq!(
919 map.get_str_array("roles"),
920 Some(vec!["admin", "", "worker"])
921 );
922 assert_eq!(
923 map.parse_str_array("roles"),
924 Some(vec!["admin", "", "worker"])
925 );
926 assert_eq!(
927 map.parse_array::<String>("roles"),
928 Some(Ok(vec!["admin".to_owned(), "worker".to_owned()]))
929 );
930 }
931
932 #[test]
933 fn it_lookups_json_value() {
934 let mut map = Map::new();
935 map.upsert("entries", vec![Map::from_entry("name", "alice")]);
936 map.upsert("total", 1);
937
938 assert_eq!(map.pointer("total"), None);
939 assert_eq!(map.pointer("/total").and_then(|v| v.as_usize()), Some(1));
940 assert_eq!(
941 map.pointer("/entries/0/name").and_then(|v| v.as_str()),
942 Some("alice")
943 );
944 }
945}