1use alloc::boxed::Box;
6use alloc::string::{String, ToString};
7
8use crate::google::protobuf::{value::Kind, ListValue, NullValue, Struct, Value};
9
10impl Value {
11 pub fn null() -> Self {
13 Self {
14 kind: Some(Kind::NullValue(buffa::EnumValue::from(
15 NullValue::NULL_VALUE,
16 ))),
17 ..Default::default()
18 }
19 }
20
21 pub fn is_null(&self) -> bool {
23 matches!(self.kind, Some(Kind::NullValue(_)))
24 }
25
26 pub fn as_number(&self) -> Option<f64> {
28 match &self.kind {
29 Some(Kind::NumberValue(n)) => Some(*n),
30 _ => None,
31 }
32 }
33
34 pub fn as_str(&self) -> Option<&str> {
36 match &self.kind {
37 Some(Kind::StringValue(s)) => Some(s.as_str()),
38 _ => None,
39 }
40 }
41
42 pub fn as_bool(&self) -> Option<bool> {
44 match &self.kind {
45 Some(Kind::BoolValue(b)) => Some(*b),
46 _ => None,
47 }
48 }
49
50 pub fn as_struct(&self) -> Option<&Struct> {
52 match &self.kind {
53 Some(Kind::StructValue(s)) => Some(s),
54 _ => None,
55 }
56 }
57
58 pub fn as_list(&self) -> Option<&ListValue> {
60 match &self.kind {
61 Some(Kind::ListValue(l)) => Some(l),
62 _ => None,
63 }
64 }
65
66 pub fn as_struct_mut(&mut self) -> Option<&mut Struct> {
68 match &mut self.kind {
69 Some(Kind::StructValue(s)) => Some(s),
70 _ => None,
71 }
72 }
73
74 pub fn as_list_mut(&mut self) -> Option<&mut ListValue> {
76 match &mut self.kind {
77 Some(Kind::ListValue(l)) => Some(l),
78 _ => None,
79 }
80 }
81}
82
83impl From<f64> for Value {
84 fn from(n: f64) -> Self {
85 Self {
86 kind: Some(Kind::NumberValue(n)),
87 ..Default::default()
88 }
89 }
90}
91
92impl From<String> for Value {
93 fn from(s: String) -> Self {
94 Self {
95 kind: Some(Kind::StringValue(s)),
96 ..Default::default()
97 }
98 }
99}
100
101impl From<&str> for Value {
102 fn from(s: &str) -> Self {
103 Self {
104 kind: Some(Kind::StringValue(s.to_string())),
105 ..Default::default()
106 }
107 }
108}
109
110impl From<f32> for Value {
111 fn from(n: f32) -> Self {
116 Self::from(n as f64)
117 }
118}
119
120impl From<bool> for Value {
121 fn from(b: bool) -> Self {
122 Self {
123 kind: Some(Kind::BoolValue(b)),
124 ..Default::default()
125 }
126 }
127}
128
129impl From<i32> for Value {
130 fn from(n: i32) -> Self {
134 Self::from(n as f64)
135 }
136}
137
138impl From<u32> for Value {
139 fn from(n: u32) -> Self {
143 Self::from(n as f64)
144 }
145}
146
147impl From<i64> for Value {
148 fn from(n: i64) -> Self {
155 Self::from(n as f64)
156 }
157}
158
159impl From<u64> for Value {
160 fn from(n: u64) -> Self {
167 Self::from(n as f64)
168 }
169}
170
171impl From<Struct> for Value {
172 fn from(s: Struct) -> Self {
173 Self {
174 kind: Some(Kind::StructValue(Box::new(s))),
175 ..Default::default()
176 }
177 }
178}
179
180impl From<ListValue> for Value {
181 fn from(l: ListValue) -> Self {
182 Self {
183 kind: Some(Kind::ListValue(Box::new(l))),
184 ..Default::default()
185 }
186 }
187}
188
189impl ListValue {
190 pub fn from_values(values: impl IntoIterator<Item = impl Into<Value>>) -> Self {
192 Self {
193 values: values.into_iter().map(Into::into).collect(),
194 ..Default::default()
195 }
196 }
197
198 #[inline]
200 pub fn len(&self) -> usize {
201 self.values.len()
202 }
203
204 #[inline]
206 pub fn is_empty(&self) -> bool {
207 self.values.is_empty()
208 }
209
210 #[inline]
212 pub fn iter(&self) -> core::slice::Iter<'_, Value> {
213 self.values.iter()
214 }
215}
216
217impl<'a> IntoIterator for &'a ListValue {
218 type Item = &'a Value;
219 type IntoIter = core::slice::Iter<'a, Value>;
220
221 fn into_iter(self) -> Self::IntoIter {
222 self.values.iter()
223 }
224}
225
226impl IntoIterator for ListValue {
227 type Item = Value;
228 type IntoIter = alloc::vec::IntoIter<Value>;
229
230 fn into_iter(self) -> Self::IntoIter {
231 self.values.into_iter()
232 }
233}
234
235impl FromIterator<Value> for ListValue {
236 fn from_iter<T: IntoIterator<Item = Value>>(iter: T) -> Self {
238 Self {
239 values: iter.into_iter().collect(),
240 ..Default::default()
241 }
242 }
243}
244
245impl Struct {
246 pub fn new() -> Self {
248 Self::default()
249 }
250
251 pub fn from_fields(
262 fields: impl IntoIterator<Item = (impl Into<String>, impl Into<Value>)>,
263 ) -> Self {
264 let mut s = Self::new();
265 for (k, v) in fields {
266 s.insert(k, v);
267 }
268 s
269 }
270
271 pub fn insert(&mut self, key: impl Into<String>, value: impl Into<Value>) {
273 self.fields.insert(key.into(), value.into());
274 }
275
276 pub fn get(&self, key: &str) -> Option<&Value> {
278 self.fields.get(key)
279 }
280}
281
282impl FromIterator<(String, Value)> for Struct {
283 fn from_iter<T: IntoIterator<Item = (String, Value)>>(iter: T) -> Self {
285 Self::from_fields(iter)
286 }
287}
288
289#[cfg(feature = "json")]
292use alloc::vec::Vec;
293
294#[cfg(feature = "json")]
295impl serde::Serialize for Value {
296 fn serialize<S: serde::Serializer>(&self, s: S) -> Result<S::Ok, S::Error> {
310 match &self.kind {
311 None | Some(Kind::NullValue(_)) => s.serialize_unit(),
312 Some(Kind::NumberValue(n)) => {
313 if !n.is_finite() {
314 return Err(serde::ser::Error::custom(
315 "Value.number_value must be finite; NaN and Infinity are not valid JSON numbers",
316 ));
317 }
318 s.serialize_f64(*n)
319 }
320 Some(Kind::StringValue(v)) => s.serialize_str(v),
321 Some(Kind::BoolValue(b)) => s.serialize_bool(*b),
322 Some(Kind::StructValue(st)) => st.serialize(s),
323 Some(Kind::ListValue(l)) => l.serialize(s),
324 }
325 }
326}
327
328#[cfg(feature = "json")]
329impl<'de> serde::Deserialize<'de> for Value {
330 fn deserialize<D: serde::Deserializer<'de>>(d: D) -> Result<Self, D::Error> {
331 use serde::de::{MapAccess, SeqAccess, Visitor};
332 struct V;
333 impl<'de> Visitor<'de> for V {
334 type Value = Value;
335 fn expecting(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
336 f.write_str("any JSON value")
337 }
338 fn visit_unit<E>(self) -> Result<Value, E> {
339 Ok(Value::null())
340 }
341 fn visit_none<E>(self) -> Result<Value, E> {
342 Ok(Value::null())
343 }
344 fn visit_bool<E>(self, v: bool) -> Result<Value, E> {
345 Ok(Value::from(v))
346 }
347 fn visit_f64<E>(self, v: f64) -> Result<Value, E> {
348 Ok(Value::from(v))
349 }
350 fn visit_i64<E>(self, v: i64) -> Result<Value, E> {
351 Ok(Value::from(v as f64))
352 }
353 fn visit_u64<E>(self, v: u64) -> Result<Value, E> {
354 Ok(Value::from(v as f64))
355 }
356 fn visit_str<E: serde::de::Error>(self, v: &str) -> Result<Value, E> {
357 Ok(Value::from(v))
358 }
359 fn visit_string<E>(self, v: String) -> Result<Value, E> {
360 Ok(Value::from(v))
361 }
362 fn visit_map<A: MapAccess<'de>>(self, mut map: A) -> Result<Value, A::Error> {
363 let mut st = Struct::default();
364 while let Some((k, v)) = map.next_entry::<String, Value>()? {
365 st.fields.insert(k, v);
366 }
367 Ok(Value::from(st))
368 }
369 fn visit_seq<A: SeqAccess<'de>>(self, mut seq: A) -> Result<Value, A::Error> {
370 let mut values = Vec::new();
371 while let Some(v) = seq.next_element::<Value>()? {
372 values.push(v);
373 }
374 Ok(Value::from(ListValue {
375 values,
376 ..Default::default()
377 }))
378 }
379 }
380 d.deserialize_any(V)
381 }
382}
383
384#[cfg(feature = "json")]
385impl serde::Serialize for Struct {
386 fn serialize<S: serde::Serializer>(&self, s: S) -> Result<S::Ok, S::Error> {
387 use serde::ser::SerializeMap;
388 let mut map = s.serialize_map(Some(self.fields.len()))?;
389 for (k, v) in &self.fields {
390 map.serialize_entry(k, v)?;
391 }
392 map.end()
393 }
394}
395
396#[cfg(feature = "json")]
397impl<'de> serde::Deserialize<'de> for Struct {
398 fn deserialize<D: serde::Deserializer<'de>>(d: D) -> Result<Self, D::Error> {
399 use serde::de::{MapAccess, Visitor};
400 struct V;
401 impl<'de> Visitor<'de> for V {
402 type Value = Struct;
403 fn expecting(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
404 f.write_str("a JSON object")
405 }
406 fn visit_map<A: MapAccess<'de>>(self, mut map: A) -> Result<Struct, A::Error> {
407 let mut st = Struct::default();
408 while let Some((k, v)) = map.next_entry::<String, Value>()? {
409 st.fields.insert(k, v);
410 }
411 Ok(st)
412 }
413 }
414 d.deserialize_map(V)
415 }
416}
417
418#[cfg(feature = "json")]
419impl serde::Serialize for ListValue {
420 fn serialize<S: serde::Serializer>(&self, s: S) -> Result<S::Ok, S::Error> {
421 use serde::ser::SerializeSeq;
422 let mut seq = s.serialize_seq(Some(self.values.len()))?;
423 for v in &self.values {
424 seq.serialize_element(v)?;
425 }
426 seq.end()
427 }
428}
429
430#[cfg(feature = "json")]
431impl<'de> serde::Deserialize<'de> for ListValue {
432 fn deserialize<D: serde::Deserializer<'de>>(d: D) -> Result<Self, D::Error> {
433 use serde::de::{SeqAccess, Visitor};
434 struct V;
435 impl<'de> Visitor<'de> for V {
436 type Value = ListValue;
437 fn expecting(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
438 f.write_str("a JSON array")
439 }
440 fn visit_seq<A: SeqAccess<'de>>(self, mut seq: A) -> Result<ListValue, A::Error> {
441 let mut values = Vec::new();
442 while let Some(v) = seq.next_element::<Value>()? {
443 values.push(v);
444 }
445 Ok(ListValue {
446 values,
447 ..Default::default()
448 })
449 }
450 }
451 d.deserialize_seq(V)
452 }
453}
454
455#[cfg(test)]
456mod tests {
457 use super::*;
458
459 #[test]
460 fn value_null() {
461 let v = Value::null();
462 assert!(v.is_null());
463 }
464
465 #[test]
466 fn value_from_f64() {
467 let v = Value::from(3.14_f64);
468 assert_eq!(v.as_number(), Some(3.14));
469 }
470
471 #[test]
472 fn value_from_string() {
473 let v = Value::from("hello".to_string());
474 assert_eq!(v.as_str(), Some("hello"));
475 }
476
477 #[test]
478 fn value_from_str_ref() {
479 let v = Value::from("world");
480 assert_eq!(v.as_str(), Some("world"));
481 }
482
483 #[test]
484 fn value_from_bool() {
485 assert_eq!(Value::from(true).as_bool(), Some(true));
486 assert_eq!(Value::from(false).as_bool(), Some(false));
487 }
488
489 #[test]
490 fn value_from_struct() {
491 let mut s = Struct::new();
492 s.insert("x", 1.0_f64);
493 let v = Value::from(s);
494 assert!(v.as_struct().is_some());
495 }
496
497 #[test]
498 fn value_from_list() {
499 let l = ListValue::from_values([1.0_f64, 2.0, 3.0]);
500 let v = Value::from(l);
501 assert!(v.as_list().is_some());
502 assert_eq!(v.as_list().unwrap().values.len(), 3);
503 }
504
505 #[test]
506 fn struct_insert_get() {
507 let mut s = Struct::new();
508 s.insert("key", "value");
509 assert_eq!(s.get("key").and_then(|v| v.as_str()), Some("value"));
510 assert!(s.get("missing").is_none());
511 }
512
513 #[test]
514 fn struct_from_fields() {
515 let s = Struct::from_fields([("a", Value::from(1.0_f64)), ("b", Value::from(2.0_f64))]);
516 assert_eq!(s.get("a").and_then(|v| v.as_number()), Some(1.0));
517 assert_eq!(s.get("b").and_then(|v| v.as_number()), Some(2.0));
518 }
519
520 #[test]
521 fn struct_from_fields_empty() {
522 let s = Struct::from_fields(core::iter::empty::<(&str, Value)>());
523 assert!(s.fields.is_empty());
524 }
525
526 #[test]
527 fn struct_from_iter() {
528 let pairs = vec![
529 ("x".to_string(), Value::from("hello")),
530 ("y".to_string(), Value::from(true)),
531 ];
532 let s: Struct = pairs.into_iter().collect();
533 assert_eq!(s.get("x").and_then(|v| v.as_str()), Some("hello"));
534 assert_eq!(s.get("y").and_then(|v| v.as_bool()), Some(true));
535 }
536
537 #[test]
538 fn list_value_from_values() {
539 let l = ListValue::from_values(["a", "b", "c"]);
540 assert_eq!(l.values.len(), 3);
541 }
542
543 #[test]
546 fn value_from_f32() {
547 let v = Value::from(1.5_f32);
548 assert_eq!(v.as_number(), Some(1.5_f64));
549 }
550
551 #[test]
554 fn list_value_len_and_is_empty() {
555 let empty = ListValue::from_values(core::iter::empty::<f64>());
556 assert!(empty.is_empty());
557 assert_eq!(empty.len(), 0);
558
559 let three = ListValue::from_values([1.0_f64, 2.0, 3.0]);
560 assert!(!three.is_empty());
561 assert_eq!(three.len(), 3);
562 }
563
564 #[test]
565 fn list_value_iter() {
566 let l = ListValue::from_values([1.0_f64, 2.0]);
567 let nums: Vec<f64> = l.iter().map(|v| v.as_number().unwrap()).collect();
568 assert_eq!(nums, [1.0, 2.0]);
569 }
570
571 #[test]
572 fn list_value_ref_into_iter() {
573 let l = ListValue::from_values(["a", "b"]);
574 let strs: Vec<&str> = (&l).into_iter().map(|v| v.as_str().unwrap()).collect();
575 assert_eq!(strs, ["a", "b"]);
576 }
577
578 #[test]
579 fn list_value_owned_into_iter() {
580 let l = ListValue::from_values([true, false]);
581 let bools: Vec<bool> = l.into_iter().map(|v| v.as_bool().unwrap()).collect();
582 assert_eq!(bools, [true, false]);
583 }
584
585 #[test]
588 fn value_from_i32() {
589 let v = Value::from(42_i32);
590 assert_eq!(v.as_number(), Some(42.0));
591 }
592
593 #[test]
594 fn value_from_u32() {
595 let v = Value::from(u32::MAX);
596 assert_eq!(v.as_number(), Some(u32::MAX as f64));
597 }
598
599 #[test]
600 fn value_from_i64_small() {
601 let v = Value::from(-100_i64);
603 assert_eq!(v.as_number(), Some(-100.0));
604 }
605
606 #[test]
607 fn value_from_u64_small() {
608 let v = Value::from(1_000_000_u64);
609 assert_eq!(v.as_number(), Some(1_000_000.0));
610 }
611
612 #[test]
615 fn as_struct_mut_returns_some_for_struct_value() {
616 let mut s = Struct::new();
617 s.insert("a", 1.0_f64);
618 let mut v = Value::from(s);
619 let m = v.as_struct_mut().unwrap();
620 m.insert("b", 2.0_f64);
621 assert_eq!(v.as_struct().unwrap().fields.len(), 2);
622 }
623
624 #[test]
625 fn as_struct_mut_returns_none_for_non_struct() {
626 let mut v = Value::from(1.0_f64);
627 assert!(v.as_struct_mut().is_none());
628 }
629
630 #[test]
631 fn as_list_mut_returns_some_for_list_value() {
632 let l = ListValue::from_values([1.0_f64]);
633 let mut v = Value::from(l);
634 let m = v.as_list_mut().unwrap();
635 m.values.push(Value::from(2.0_f64));
636 assert_eq!(v.as_list().unwrap().values.len(), 2);
637 }
638
639 #[test]
640 fn as_list_mut_returns_none_for_non_list() {
641 let mut v = Value::from(true);
642 assert!(v.as_list_mut().is_none());
643 }
644
645 #[cfg(feature = "json")]
648 mod serde_tests {
649 use super::*;
650
651 #[test]
652 fn value_null_roundtrip() {
653 let v = Value::null();
654 let json = serde_json::to_string(&v).unwrap();
655 assert_eq!(json, "null");
656 let back: Value = serde_json::from_str(&json).unwrap();
657 assert!(back.is_null());
658 }
659
660 #[test]
661 fn value_number_roundtrip() {
662 let v = Value::from(3.14_f64);
663 let json = serde_json::to_string(&v).unwrap();
664 let back: Value = serde_json::from_str(&json).unwrap();
665 assert!((back.as_number().unwrap() - 3.14).abs() < 1e-10);
666 }
667
668 #[test]
669 fn value_string_roundtrip() {
670 let v = Value::from("hello");
671 let json = serde_json::to_string(&v).unwrap();
672 assert_eq!(json, r#""hello""#);
673 let back: Value = serde_json::from_str(&json).unwrap();
674 assert_eq!(back.as_str(), Some("hello"));
675 }
676
677 #[test]
678 fn value_bool_roundtrip() {
679 let v = Value::from(true);
680 let json = serde_json::to_string(&v).unwrap();
681 assert_eq!(json, "true");
682 let back: Value = serde_json::from_str(&json).unwrap();
683 assert_eq!(back.as_bool(), Some(true));
684 }
685
686 #[test]
687 fn struct_value_roundtrip() {
688 let s = Struct::from_fields([("x", Value::from(1.0_f64))]);
689 let v = Value::from(s);
690 let json = serde_json::to_string(&v).unwrap();
691 assert_eq!(json, r#"{"x":1.0}"#);
692 let back: Value = serde_json::from_str(&json).unwrap();
693 assert!(back.as_struct().is_some());
694 assert_eq!(
695 back.as_struct()
696 .unwrap()
697 .get("x")
698 .and_then(|v| v.as_number()),
699 Some(1.0)
700 );
701 }
702
703 #[test]
704 fn list_value_roundtrip() {
705 let l = ListValue::from_values([1.0_f64, 2.0]);
706 let v = Value::from(l);
707 let json = serde_json::to_string(&v).unwrap();
708 assert_eq!(json, "[1.0,2.0]");
709 let back: Value = serde_json::from_str(&json).unwrap();
710 assert_eq!(back.as_list().unwrap().values.len(), 2);
711 }
712
713 #[test]
714 fn struct_roundtrip() {
715 let s = Struct::from_fields([("a", Value::from("b"))]);
716 let json = serde_json::to_string(&s).unwrap();
717 let back: Struct = serde_json::from_str(&json).unwrap();
718 assert_eq!(back.get("a").and_then(|v| v.as_str()), Some("b"));
719 }
720
721 #[test]
722 fn value_nan_serialize_is_error() {
723 let v = Value::from(f64::NAN);
724 let result = serde_json::to_string(&v);
725 assert!(result.is_err(), "NaN must fail serialization");
726 }
727
728 #[test]
729 fn value_infinity_serialize_is_error() {
730 let v = Value::from(f64::INFINITY);
731 assert!(
732 serde_json::to_string(&v).is_err(),
733 "Infinity must fail serialization"
734 );
735
736 let v = Value::from(f64::NEG_INFINITY);
737 assert!(
738 serde_json::to_string(&v).is_err(),
739 "-Infinity must fail serialization"
740 );
741 }
742
743 #[test]
744 fn list_value_deserializes_from_array() {
745 let json = r#"[null, 1, "s", true]"#;
746 let l: ListValue = serde_json::from_str(json).unwrap();
747 assert_eq!(l.values.len(), 4);
748 assert!(l.values[0].is_null());
749 }
750
751 #[test]
752 fn value_deserializes_integer() {
753 let v: Value = serde_json::from_str("42").unwrap();
755 assert_eq!(v.as_number(), Some(42.0));
756 }
757
758 #[test]
759 fn value_deserializes_negative_integer() {
760 let v: Value = serde_json::from_str("-100").unwrap();
761 assert_eq!(v.as_number(), Some(-100.0));
762 }
763
764 #[test]
765 fn value_deserializes_large_integer() {
766 let v: Value = serde_json::from_str("9007199254740992").unwrap();
768 assert_eq!(v.as_number(), Some(9007199254740992.0));
769 }
770
771 #[test]
772 fn value_deep_nesting_binary_respects_recursion_limit() {
773 use buffa::{DecodeError, Message};
776 let mut payload = alloc::vec::Vec::new();
784 for _ in 0..200 {
785 let mut lv = alloc::vec::Vec::new();
787 lv.push(0x0a); lv.push(payload.len() as u8); lv.extend_from_slice(&payload);
790 let mut v = alloc::vec::Vec::new();
792 v.push(0x32); v.push(lv.len() as u8);
794 v.extend_from_slice(&lv);
795 payload = v;
796 if payload.len() >= 120 {
798 break;
799 }
800 }
801 use buffa::encoding::encode_varint;
804 for _ in 0..200 {
805 let mut lv = alloc::vec::Vec::new();
806 lv.push(0x0a);
807 encode_varint(payload.len() as u64, &mut lv);
808 lv.extend_from_slice(&payload);
809 let mut v = alloc::vec::Vec::new();
810 v.push(0x32);
811 encode_varint(lv.len() as u64, &mut v);
812 v.extend_from_slice(&lv);
813 payload = v;
814 }
815 let result = Value::decode(&mut payload.as_slice());
819 assert!(
820 matches!(result, Err(DecodeError::RecursionLimitExceeded)),
821 "deep nesting must hit recursion limit, got: {result:?}"
822 );
823 }
824
825 #[test]
826 fn value_deep_nesting_json_bounded() {
827 let deep = alloc::format!("{}null{}", "[".repeat(200), "]".repeat(200));
832 let result: Result<Value, _> = serde_json::from_str(&deep);
833 assert!(result.is_err(), "200-level JSON nesting must be rejected");
834 }
835 }
836}