type_reg/untagged/
data_type.rs

1use std::any::{Any, TypeId};
2
3use downcast_rs::DowncastSync;
4use dyn_clone::DynClone;
5
6use crate::TypeNameLit;
7
8/// Trait to represent the stored type.
9#[cfg(all(not(feature = "debug"), not(feature = "resman")))]
10pub trait DataType: DowncastSync + DynClone + erased_serde::Serialize {
11    fn type_name(&self) -> TypeNameLit;
12    fn type_id_inner(&self) -> TypeId;
13}
14
15#[cfg(all(not(feature = "debug"), not(feature = "resman")))]
16impl<T> DataType for T
17where
18    T: Any + DynClone + erased_serde::Serialize + Send + Sync,
19{
20    fn type_name(&self) -> TypeNameLit {
21        TypeNameLit(std::any::type_name::<T>())
22    }
23
24    fn type_id_inner(&self) -> TypeId {
25        TypeId::of::<T>()
26    }
27}
28
29/// Trait to represent the stored type.
30#[cfg(all(not(feature = "debug"), feature = "resman"))]
31pub trait DataType: resman::Resource + DowncastSync + DynClone + erased_serde::Serialize {
32    fn type_name(&self) -> TypeNameLit;
33    fn type_id_inner(&self) -> TypeId;
34    fn upcast(self: Box<Self>) -> Box<dyn resman::Resource>;
35}
36
37#[cfg(all(not(feature = "debug"), feature = "resman"))]
38impl<T> DataType for T
39where
40    T: Any + DynClone + erased_serde::Serialize + Send + Sync,
41{
42    fn type_name(&self) -> TypeNameLit {
43        TypeNameLit(std::any::type_name::<T>())
44    }
45
46    fn type_id_inner(&self) -> TypeId {
47        TypeId::of::<T>()
48    }
49
50    fn upcast(self: Box<Self>) -> Box<dyn resman::Resource> {
51        self
52    }
53}
54
55/// Trait to represent the stored type.
56#[cfg(all(feature = "debug", not(feature = "resman")))]
57pub trait DataType: DowncastSync + DynClone + std::fmt::Debug + erased_serde::Serialize {
58    fn type_name(&self) -> TypeNameLit;
59    fn type_id_inner(&self) -> TypeId;
60}
61
62#[cfg(all(feature = "debug", not(feature = "resman")))]
63impl<T> DataType for T
64where
65    T: Any + DynClone + std::fmt::Debug + erased_serde::Serialize + Send + Sync,
66{
67    fn type_name(&self) -> TypeNameLit {
68        TypeNameLit(std::any::type_name::<T>())
69    }
70
71    fn type_id_inner(&self) -> TypeId {
72        TypeId::of::<T>()
73    }
74}
75
76/// Trait to represent the stored type.
77#[cfg(all(feature = "debug", feature = "resman"))]
78pub trait DataType:
79    resman::Resource + DowncastSync + DynClone + std::fmt::Debug + erased_serde::Serialize
80{
81    fn type_name(&self) -> TypeNameLit;
82    fn type_id_inner(&self) -> TypeId;
83    fn upcast(self: Box<Self>) -> Box<dyn resman::Resource>;
84}
85
86#[cfg(all(feature = "debug", feature = "resman"))]
87impl<T> DataType for T
88where
89    T: Any + DynClone + std::fmt::Debug + erased_serde::Serialize + Send + Sync,
90{
91    fn type_name(&self) -> TypeNameLit {
92        TypeNameLit(std::any::type_name::<T>())
93    }
94
95    fn type_id_inner(&self) -> TypeId {
96        TypeId::of::<T>()
97    }
98
99    fn upcast(self: Box<Self>) -> Box<dyn resman::Resource> {
100        self
101    }
102}
103
104downcast_rs::impl_downcast!(sync DataType);
105dyn_clone::clone_trait_object!(DataType);
106
107impl serde::Serialize for dyn DataType + '_ {
108    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
109    where
110        S: serde::Serializer,
111    {
112        erased_serde::serialize(self, serializer)
113    }
114}
115
116#[cfg(test)]
117mod tests {
118    use std::any::TypeId;
119
120    use super::DataType;
121
122    #[test]
123    fn type_id_inner_matches_inner_type_type_id() {
124        let n = 1u32;
125
126        assert_eq!(TypeId::of::<u32>(), DataType::type_id_inner(&n));
127    }
128
129    #[test]
130    fn type_id_inner_matches_box_inner_type_type_id() {
131        let n = Box::new(1u32);
132
133        assert_eq!(TypeId::of::<u32>(), DataType::type_id_inner(n.as_ref()));
134    }
135}