tower_web/response/
default_serializer.rs

1use response::{ContentType, Serializer, SerializerContext};
2use util::Chain;
3use util::tuple::Either2;
4
5use bytes::Bytes;
6use http::header::HeaderValue;
7use serde::Serialize;
8
9/// Default serializer
10///
11/// Serializes responses into one of a number of common HTTP formats.
12#[derive(Debug, Clone)]
13pub struct DefaultSerializer<T = ()> {
14    custom: T,
15    plain: HeaderValue,
16    json: HeaderValue,
17}
18
19/// Response type
20#[derive(Debug, Clone)]
21pub struct Format {
22    kind: Kind,
23}
24
25#[derive(Debug, Clone)]
26enum Kind {
27    Json,
28    Plain,
29}
30
31const TEXT_PLAIN: &str = "text/plain";
32const APPLICATION_JSON: &str = "application/json";
33
34impl DefaultSerializer {
35    /// Return a new `DefaultSerializer` value.
36    pub fn new() -> DefaultSerializer {
37        DefaultSerializer {
38            custom: (),
39            plain: HeaderValue::from_static(TEXT_PLAIN),
40            json: HeaderValue::from_static(APPLICATION_JSON),
41        }
42    }
43}
44
45impl<T> Serializer for DefaultSerializer<T>
46where T: Serializer,
47{
48    type Format = Either2<T::Format, Format>;
49
50    fn lookup(&self, name: &str) -> Option<ContentType<Self::Format>> {
51        if let Some(content_type) = self.custom.lookup(name) {
52            return Some(content_type.map(Either2::A));
53        }
54
55        match name {
56            "json" | APPLICATION_JSON => {
57                let format = Either2::B(Format::json());
58                Some(ContentType::new(self.json.clone(), format))
59            }
60            "plain" | TEXT_PLAIN => {
61                let format = Either2::B(Format::plain());
62                Some(ContentType::new(self.plain.clone(), format))
63            }
64            _ => {
65                None
66            }
67        }
68    }
69
70    fn serialize<V>(&self, value: &V, format: &Self::Format, ctx: &SerializerContext)
71        -> Result<Bytes, ::Error>
72    where
73        V: Serialize,
74    {
75        match format {
76            Either2::A(ref format) => self.custom.serialize(value, format, ctx),
77            Either2::B(ref format) => {
78                match format.kind {
79                    Kind::Json => {
80                        let body = ::serde_json::to_vec(&value).unwrap();
81                        Ok(body.into())
82                    }
83                    Kind::Plain => {
84                        let body = ::serde_plain::to_string(&value).unwrap();
85                        Ok(body.into())
86                    }
87                }
88            }
89        }
90    }
91}
92
93impl<T, U> Chain<U> for DefaultSerializer<T> {
94    type Output = DefaultSerializer<(T, U)>;
95
96    fn chain(self, other: U) -> Self::Output {
97        DefaultSerializer {
98            custom: (self.custom, other),
99            plain: self.plain,
100            json: self.json,
101        }
102    }
103}
104
105impl<T> ::util::Sealed for DefaultSerializer<T> {}
106
107impl Format {
108    /// Json
109    fn json() -> Format {
110        Format { kind: Kind::Json }
111    }
112
113    /// Plain
114    fn plain() -> Format {
115        Format { kind: Kind::Plain }
116    }
117}