mail_headers_ng/
header.rs1use std::any::TypeId;
2use std::ops::{Deref, DerefMut};
3use std::fmt::{self, Debug};
4
5use internals::{
6 error::EncodingError,
7 encoder::{
8 EncodableInHeader,
9 EncodingWriter,
10 }
11};
12
13
14use ::error::ComponentCreationError;
15use ::convert::HeaderTryInto;
16use ::name::{HeaderName, HasHeaderName};
17use ::map::HeaderMapValidator;
21
22pub trait HeaderKind: Clone + Default + 'static {
28
29 type Component: EncodableInHeader + Clone;
31
32 fn name() -> HeaderName;
39
40 const VALIDATOR: Option<HeaderMapValidator>;
54
55 const MAX_ONE: bool;
65
66 fn auto_body<H>(body: H) -> Result<Header<Self>, ComponentCreationError>
77 where H: HeaderTryInto<Self::Component>
78 {
79 Ok(Self::body(HeaderTryInto::try_into(body)?))
80 }
81
82 fn body(body: Self::Component) -> Header<Self> {
84 Header::new(body)
85 }
86}
87
88impl<H> HasHeaderName for H
89 where H: HeaderKind
90{
91 fn get_name(&self) -> HeaderName {
92 H::name()
93 }
94}
95
96pub trait MaxOneMarker: HeaderKind {}
97
98#[derive(Clone)]
99pub struct Header<H>
100 where H: HeaderKind
101{
102 body: H::Component
103}
104
105impl<H> Header<H>
106 where H: HeaderKind
107{
108 pub fn new(body: H::Component) -> Header<H> {
109 Header { body }
110 }
111
112 pub fn body(&self) -> &H::Component {
113 &self.body
114 }
115
116 pub fn body_mut(&mut self) -> &mut H::Component {
117 &mut self.body
118 }
119}
120
121impl<H> Deref for Header<H>
122 where H: HeaderKind
123{
124 type Target = H::Component;
125 fn deref(&self) -> &Self::Target {
126 self.body()
127 }
128}
129
130impl<H> DerefMut for Header<H>
131 where H: HeaderKind
132{
133 fn deref_mut(&mut self) -> &mut Self::Target {
134 self.body_mut()
135 }
136}
137
138impl<H> Debug for Header<H>
139 where H: HeaderKind
140{
141 fn fmt(&self, fter: &mut fmt::Formatter) -> fmt::Result {
142 self.body.fmt(fter)
143 }
144}
145
146pub type HeaderObj = dyn HeaderObjTrait;
148
149pub trait HeaderObjTrait: Sync + Send + ::std::any::Any + Debug {
150 fn name(&self) -> HeaderName;
151 fn is_max_one(&self) -> bool;
152 fn validator(&self) -> Option<HeaderMapValidator>;
153 fn encode(&self, encoder: &mut EncodingWriter) -> Result<(), EncodingError>;
154 fn boxed_clone(&self) -> Box<HeaderObj>;
155
156 #[doc(hidden)]
157 fn type_id(&self) -> TypeId {
158 TypeId::of::<Self>()
159 }
160}
161
162impl<H> HeaderObjTrait for Header<H>
163 where H: HeaderKind
164{
165 fn name(&self) -> HeaderName {
166 H::name()
167 }
168
169 fn is_max_one(&self) -> bool {
170 H::MAX_ONE
171 }
172
173 fn validator(&self) -> Option<HeaderMapValidator> {
174 H::VALIDATOR
175 }
176
177 fn encode(&self, encoder: &mut EncodingWriter) -> Result<(), EncodingError> {
178 self.body.encode(encoder)
179 }
180
181 fn boxed_clone(&self) -> Box<HeaderObj> {
182 let cloned = self.clone();
183 Box::new(cloned)
184 }
185}
186
187impl<H> HasHeaderName for Header<H>
188 where H: HeaderKind
189{
190 fn get_name(&self) -> HeaderName {
191 H::name()
192 }
193}
194
195
196impl HeaderObj {
197 pub fn is<H>(&self) -> bool
198 where H: HeaderKind
199 {
200 HeaderObjTrait::type_id(self) == TypeId::of::<Header<H>>()
201 }
202
203 pub fn downcast_ref<H>(&self) -> Option<&Header<H>>
204 where H: HeaderKind
205 {
206 if self.is::<H>() {
207 Some(unsafe { &*(self as *const _ as *const Header<H>) })
208 } else {
209 None
210 }
211 }
212
213 pub fn downcast_mut<H>(&mut self) -> Option<&mut Header<H>>
214 where H: HeaderKind
215 {
216 if self.is::<H>() {
217 Some(unsafe { &mut *(self as *mut _ as *mut Header<H>) })
218 } else {
219 None
220 }
221 }
222}
223
224impl Clone for Box<HeaderObj> {
225 fn clone(&self) -> Self {
226 self.boxed_clone()
227 }
228}
229
230impl HasHeaderName for HeaderObj {
231 fn get_name(&self) -> HeaderName {
232 self.name()
233 }
234}
235
236pub trait HeaderObjTraitBoxExt: Sized {
237 fn downcast<H>(self) -> Result<Box<Header<H>>, Self>
238 where H: HeaderKind;
239}
240
241impl HeaderObjTraitBoxExt for Box<HeaderObjTrait> {
242
243 fn downcast<H>(self) -> Result<Box<Header<H>>, Self>
244 where H: HeaderKind
245 {
246 if HeaderObjTrait::is::<H>(&*self) {
247 let ptr: *mut (HeaderObj) = Box::into_raw(self);
248 Ok(unsafe { Box::from_raw(ptr as *mut Header<H>) })
249 } else {
250 Err(self)
251 }
252 }
253}