facet_reflect/
scalar.rs

1use core::net::{IpAddr, Ipv4Addr, Ipv6Addr};
2
3use facet_core::{ConstTypeId, Shape};
4
5/// All scalar types supported out of the box by peek and poke.
6#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash, Debug)]
7#[non_exhaustive]
8pub enum ScalarType {
9    /// Unit tuple `()`.
10    Unit,
11    /// Primitive type `bool`.
12    Bool,
13    /// Primitive type `char`.
14    Char,
15    /// Primitive type `str`.
16    Str,
17    /// `std::string::String`.
18    String,
19    /// `std::borrow::Cow<'_, str>`.
20    CowStr,
21    /// Primitive type `f32`.
22    F32,
23    /// Primitive type `f64`.
24    F64,
25    /// Primitive type `u8`.
26    U8,
27    /// Primitive type `u16`.
28    U16,
29    /// Primitive type `u32`.
30    U32,
31    /// Primitive type `u64`.
32    U64,
33    /// Primitive type `u128`.
34    U128,
35    /// Primitive type `usize`.
36    USize,
37    /// Primitive type `i8`.
38    I8,
39    /// Primitive type `i16`.
40    I16,
41    /// Primitive type `i32`.
42    I32,
43    /// Primitive type `i64`.
44    I64,
45    /// Primitive type `i128`.
46    I128,
47    /// Primitive type `isize`.
48    ISize,
49    /// `core::net::SocketAddr`.
50    #[cfg(feature = "std")]
51    SocketAddr,
52    /// `core::net::IpAddr`.
53    IpAddr,
54    /// `core::net::Ipv4Addr`.
55    Ipv4Addr,
56    /// `core::net::Ipv6Addr`.
57    Ipv6Addr,
58    /// `facet_core::typeid::ConstTypeId`.
59    ConstTypeId,
60}
61
62impl ScalarType {
63    /// Infer the type from a shape definition.
64    pub fn try_from_shape(shape: &'static Shape) -> Option<Self> {
65        #[cfg(feature = "std")]
66        if shape.id == ConstTypeId::of::<String>() {
67            return Some(ScalarType::String);
68        } else if shape.id == ConstTypeId::of::<alloc::borrow::Cow<'_, str>>() {
69            return Some(ScalarType::CowStr);
70        } else if shape.id == ConstTypeId::of::<core::net::SocketAddr>() {
71            return Some(ScalarType::SocketAddr);
72        }
73
74        if shape.id == ConstTypeId::of::<()>() {
75            Some(Self::Unit)
76        } else if shape.id == ConstTypeId::of::<bool>() {
77            Some(ScalarType::Bool)
78        } else if shape.id == ConstTypeId::of::<char>() {
79            Some(ScalarType::Char)
80        } else if shape.id == ConstTypeId::of::<&str>() {
81            Some(ScalarType::Str)
82        } else if shape.id == ConstTypeId::of::<f32>() {
83            Some(ScalarType::F32)
84        } else if shape.id == ConstTypeId::of::<f64>() {
85            Some(ScalarType::F64)
86        } else if shape.id == ConstTypeId::of::<u8>() {
87            Some(ScalarType::U8)
88        } else if shape.id == ConstTypeId::of::<u16>() {
89            Some(ScalarType::U16)
90        } else if shape.id == ConstTypeId::of::<u32>() {
91            Some(ScalarType::U32)
92        } else if shape.id == ConstTypeId::of::<u64>() {
93            Some(ScalarType::U64)
94        } else if shape.id == ConstTypeId::of::<u128>() {
95            Some(ScalarType::U128)
96        } else if shape.id == ConstTypeId::of::<usize>() {
97            Some(ScalarType::USize)
98        } else if shape.id == ConstTypeId::of::<i8>() {
99            Some(ScalarType::I8)
100        } else if shape.id == ConstTypeId::of::<i16>() {
101            Some(ScalarType::I16)
102        } else if shape.id == ConstTypeId::of::<i32>() {
103            Some(ScalarType::I32)
104        } else if shape.id == ConstTypeId::of::<i64>() {
105            Some(ScalarType::I64)
106        } else if shape.id == ConstTypeId::of::<i128>() {
107            Some(ScalarType::I128)
108        } else if shape.id == ConstTypeId::of::<isize>() {
109            Some(ScalarType::ISize)
110        } else if shape.id == ConstTypeId::of::<IpAddr>() {
111            Some(ScalarType::IpAddr)
112        } else if shape.id == ConstTypeId::of::<Ipv4Addr>() {
113            Some(ScalarType::Ipv4Addr)
114        } else if shape.id == ConstTypeId::of::<Ipv6Addr>() {
115            Some(ScalarType::Ipv6Addr)
116        } else if shape.id == ConstTypeId::of::<ConstTypeId>() {
117            Some(ScalarType::ConstTypeId)
118        } else {
119            None
120        }
121    }
122}
123
124#[cfg(test)]
125mod tests {
126    use super::*;
127
128    use core::net::{IpAddr, Ipv4Addr, Ipv6Addr};
129
130    use facet_core::Facet;
131
132    /// Simple check to ensure every can be loaded from a shape.
133    #[test]
134    fn test_ensure_try_from_shape() {
135        assert_eq!(
136            ScalarType::Unit,
137            ScalarType::try_from_shape(<()>::SHAPE).unwrap()
138        );
139        assert_eq!(
140            ScalarType::Bool,
141            ScalarType::try_from_shape(bool::SHAPE).unwrap()
142        );
143        assert_eq!(
144            ScalarType::Str,
145            ScalarType::try_from_shape(<&str>::SHAPE).unwrap()
146        );
147        #[cfg(feature = "std")]
148        assert_eq!(
149            ScalarType::String,
150            ScalarType::try_from_shape(String::SHAPE).unwrap()
151        );
152        #[cfg(feature = "std")]
153        assert_eq!(
154            ScalarType::CowStr,
155            ScalarType::try_from_shape(alloc::borrow::Cow::SHAPE).unwrap()
156        );
157        assert_eq!(
158            ScalarType::F32,
159            ScalarType::try_from_shape(f32::SHAPE).unwrap()
160        );
161        assert_eq!(
162            ScalarType::F64,
163            ScalarType::try_from_shape(f64::SHAPE).unwrap()
164        );
165        assert_eq!(
166            ScalarType::U8,
167            ScalarType::try_from_shape(u8::SHAPE).unwrap()
168        );
169        assert_eq!(
170            ScalarType::U16,
171            ScalarType::try_from_shape(u16::SHAPE).unwrap()
172        );
173        assert_eq!(
174            ScalarType::U32,
175            ScalarType::try_from_shape(u32::SHAPE).unwrap()
176        );
177        assert_eq!(
178            ScalarType::U64,
179            ScalarType::try_from_shape(u64::SHAPE).unwrap()
180        );
181        assert_eq!(
182            ScalarType::U128,
183            ScalarType::try_from_shape(u128::SHAPE).unwrap()
184        );
185        assert_eq!(
186            ScalarType::USize,
187            ScalarType::try_from_shape(usize::SHAPE).unwrap()
188        );
189        assert_eq!(
190            ScalarType::I8,
191            ScalarType::try_from_shape(i8::SHAPE).unwrap()
192        );
193        assert_eq!(
194            ScalarType::I16,
195            ScalarType::try_from_shape(i16::SHAPE).unwrap()
196        );
197        assert_eq!(
198            ScalarType::I32,
199            ScalarType::try_from_shape(i32::SHAPE).unwrap()
200        );
201        assert_eq!(
202            ScalarType::I64,
203            ScalarType::try_from_shape(i64::SHAPE).unwrap()
204        );
205        assert_eq!(
206            ScalarType::I128,
207            ScalarType::try_from_shape(i128::SHAPE).unwrap()
208        );
209        assert_eq!(
210            ScalarType::ISize,
211            ScalarType::try_from_shape(isize::SHAPE).unwrap()
212        );
213        #[cfg(feature = "std")]
214        assert_eq!(
215            ScalarType::SocketAddr,
216            ScalarType::try_from_shape(core::net::SocketAddr::SHAPE).unwrap()
217        );
218        assert_eq!(
219            ScalarType::IpAddr,
220            ScalarType::try_from_shape(IpAddr::SHAPE).unwrap()
221        );
222        assert_eq!(
223            ScalarType::Ipv4Addr,
224            ScalarType::try_from_shape(Ipv4Addr::SHAPE).unwrap()
225        );
226        assert_eq!(
227            ScalarType::Ipv6Addr,
228            ScalarType::try_from_shape(Ipv6Addr::SHAPE).unwrap()
229        );
230        assert_eq!(
231            ScalarType::ConstTypeId,
232            ScalarType::try_from_shape(ConstTypeId::SHAPE).unwrap()
233        );
234    }
235}