cel_cxx/values/impls/
optional.rs

1use super::{impl_into, impl_typed};
2use crate::{types::*, values::*};
3
4impl_typed!(
5    Optional: Value {
6        @[T: TypedValue]
7        Optional<T> => OptionalType::new(T::value_type()),
8
9        @[T: TypedValue]
10        Option<T> => OptionalType::new(T::value_type()),
11    }
12);
13
14impl_into!(
15    Optional: Value {
16        @[T: IntoValue]
17        Optional<T> => |self| self.map(IntoValue::into_value),
18
19        @[T: IntoValue]
20        Option<T> => |self| self.map(IntoValue::into_value).into(),
21    }
22);
23
24// FromValue for Optional<T>
25impl<T: FromValue + TypedValue> FromValue for Optional<T> {
26    type Output<'a> = Optional<T::Output<'a>>;
27
28    fn from_value<'a>(value: &'a Value) -> Result<Self::Output<'a>, FromValueError> {
29        match value {
30            Value::Optional(o) => o.as_ref().map(|v| T::from_value(v)).transpose(),
31            _ => Err(FromValueError::new_typed::<Self>(value.clone())),
32        }
33    }
34}
35
36// TryFrom<&Value> for Optional<T>
37impl<'a, T: TryFrom<&'a Value, Error = FromValueError> + TypedValue> TryFrom<&'a Value>
38    for Optional<T>
39{
40    type Error = FromValueError;
41
42    fn try_from(value: &'a Value) -> Result<Self, Self::Error> {
43        match value {
44            Value::Optional(o) => o.as_ref().map(|v| T::try_from(v)).transpose(),
45            _ => Err(FromValueError::new_typed::<Self>(value.clone())),
46        }
47    }
48}
49
50// TryFrom<Value> for Optional<T>
51impl<T: TryFrom<Value, Error = FromValueError> + TypedValue> TryFrom<Value> for Optional<T> {
52    type Error = FromValueError;
53
54    fn try_from(value: Value) -> Result<Self, Self::Error> {
55        match value {
56            Value::Optional(o) => o.map(|v| T::try_from(v)).transpose(),
57            _ => Err(FromValueError::new_typed::<Self>(value)),
58        }
59    }
60}
61
62// FromValue for Option<T>
63impl<T: FromValue + TypedValue> FromValue for Option<T> {
64    type Output<'a> = Option<T::Output<'a>>;
65
66    fn from_value<'a>(value: &'a Value) -> Result<Self::Output<'a>, FromValueError> {
67        match value {
68            Value::Optional(o) => o
69                .as_ref()
70                .map(|v| T::from_value(v))
71                .transpose()
72                .map(|optional| optional.into()),
73            _ => Err(FromValueError::new_typed::<Self>(value.clone())),
74        }
75    }
76}
77
78// TryFrom<&Value> for Option<T>
79impl<'a, T: TryFrom<&'a Value, Error = FromValueError> + TypedValue> TryFrom<&'a Value>
80    for Option<T>
81{
82    type Error = FromValueError;
83
84    fn try_from(value: &'a Value) -> Result<Self, Self::Error> {
85        match value {
86            Value::Optional(o) => o
87                .as_ref()
88                .map(|v| T::try_from(v))
89                .transpose()
90                .map(|optional| optional.into()),
91            _ => Err(FromValueError::new_typed::<Self>(value.clone())),
92        }
93    }
94}
95
96// TryFrom<Value> for Option<T>
97impl<T: TryFrom<Value, Error = FromValueError> + TypedValue> TryFrom<Value> for Option<T> {
98    type Error = FromValueError;
99
100    fn try_from(value: Value) -> Result<Self, Self::Error> {
101        match value {
102            Value::Optional(o) => o
103                .map(|v| T::try_from(v))
104                .transpose()
105                .map(|optional| optional.into()),
106            _ => Err(FromValueError::new_typed::<Self>(value)),
107        }
108    }
109}