mqtt/
encodable.rs

1//! Encodable traits
2
3use std::convert::Infallible;
4use std::error::Error;
5
6use std::io::{self, Read, Write};
7use std::marker::Sized;
8
9use byteorder::{BigEndian, ReadBytesExt, WriteBytesExt};
10
11/// Methods for encoding an Object to bytes according to MQTT specification
12pub trait Encodable {
13    /// Encodes to writer
14    fn encode<W: Write>(&self, writer: &mut W) -> io::Result<()>;
15    /// Length of bytes after encoded
16    fn encoded_length(&self) -> u32;
17}
18
19// impl<T: Encodable> Encodable for &T {
20//     fn encode<W: Write>(&self, writer: &mut W) -> io::Result<()> {
21//         (**self).encode(writer)
22//     }
23//     fn encoded_length(&self) -> u32 {
24//         (**self).encoded_length()
25//     }
26// }
27
28impl<T: Encodable> Encodable for Option<T> {
29    fn encode<W: Write>(&self, writer: &mut W) -> io::Result<()> {
30        if let Some(this) = self {
31            this.encode(writer)?
32        }
33        Ok(())
34    }
35
36    fn encoded_length(&self) -> u32 {
37        self.as_ref().map_or(0, |x| x.encoded_length())
38    }
39}
40
41/// Methods for decoding bytes to an Object according to MQTT specification
42pub trait Decodable: Sized {
43    type Error: Error;
44    type Cond;
45
46    /// Decodes object from reader
47    fn decode<R: Read>(reader: &mut R) -> Result<Self, Self::Error>
48    where
49        Self::Cond: Default,
50    {
51        Self::decode_with(reader, Default::default())
52    }
53
54    /// Decodes object with additional data (or hints)
55    fn decode_with<R: Read>(reader: &mut R, cond: Self::Cond) -> Result<Self, Self::Error>;
56}
57
58impl<'a> Encodable for &'a str {
59    fn encode<W: Write>(&self, writer: &mut W) -> Result<(), io::Error> {
60        assert!(self.as_bytes().len() <= u16::max_value() as usize);
61
62        writer
63            .write_u16::<BigEndian>(self.as_bytes().len() as u16)
64            .and_then(|_| writer.write_all(self.as_bytes()))
65    }
66
67    fn encoded_length(&self) -> u32 {
68        2 + self.as_bytes().len() as u32
69    }
70}
71
72impl<'a> Encodable for &'a [u8] {
73    fn encode<W: Write>(&self, writer: &mut W) -> Result<(), io::Error> {
74        writer.write_all(self)
75    }
76
77    fn encoded_length(&self) -> u32 {
78        self.len() as u32
79    }
80}
81
82impl Encodable for String {
83    fn encode<W: Write>(&self, writer: &mut W) -> Result<(), io::Error> {
84        (&self[..]).encode(writer)
85    }
86
87    fn encoded_length(&self) -> u32 {
88        (&self[..]).encoded_length()
89    }
90}
91
92impl Decodable for String {
93    type Error = io::Error;
94    type Cond = ();
95
96    fn decode_with<R: Read>(reader: &mut R, _rest: ()) -> Result<String, io::Error> {
97        let VarBytes(buf) = VarBytes::decode(reader)?;
98
99        String::from_utf8(buf).map_err(|e| io::Error::new(io::ErrorKind::InvalidData, e))
100    }
101}
102
103impl Encodable for Vec<u8> {
104    fn encode<W: Write>(&self, writer: &mut W) -> Result<(), io::Error> {
105        (&self[..]).encode(writer)
106    }
107
108    fn encoded_length(&self) -> u32 {
109        (&self[..]).encoded_length()
110    }
111}
112
113impl Decodable for Vec<u8> {
114    type Error = io::Error;
115    type Cond = Option<u32>;
116
117    fn decode_with<R: Read>(reader: &mut R, length: Option<u32>) -> Result<Vec<u8>, io::Error> {
118        match length {
119            Some(length) => {
120                let mut buf = Vec::with_capacity(length as usize);
121                reader.take(length.into()).read_to_end(&mut buf)?;
122                Ok(buf)
123            }
124            None => {
125                let mut buf = Vec::new();
126                reader.read_to_end(&mut buf)?;
127                Ok(buf)
128            }
129        }
130    }
131}
132
133impl Encodable for () {
134    fn encode<W: Write>(&self, _: &mut W) -> Result<(), io::Error> {
135        Ok(())
136    }
137
138    fn encoded_length(&self) -> u32 {
139        0
140    }
141}
142
143impl Decodable for () {
144    type Error = Infallible;
145    type Cond = ();
146
147    fn decode_with<R: Read>(_: &mut R, _: ()) -> Result<(), Self::Error> {
148        Ok(())
149    }
150}
151
152/// Bytes that encoded with length
153#[derive(Debug, Eq, PartialEq, Clone)]
154pub struct VarBytes(pub Vec<u8>);
155
156impl Encodable for VarBytes {
157    fn encode<W: Write>(&self, writer: &mut W) -> Result<(), io::Error> {
158        assert!(self.0.len() <= u16::max_value() as usize);
159        let len = self.0.len() as u16;
160        writer.write_u16::<BigEndian>(len)?;
161        writer.write_all(&self.0)?;
162        Ok(())
163    }
164
165    fn encoded_length(&self) -> u32 {
166        2 + self.0.len() as u32
167    }
168}
169
170impl Decodable for VarBytes {
171    type Error = io::Error;
172    type Cond = ();
173    fn decode_with<R: Read>(reader: &mut R, _: ()) -> Result<VarBytes, io::Error> {
174        let length = reader.read_u16::<BigEndian>()?;
175        let mut buf = Vec::with_capacity(length as usize);
176        reader.take(length.into()).read_to_end(&mut buf)?;
177        Ok(VarBytes(buf))
178    }
179}
180
181#[cfg(test)]
182mod test {
183    use super::*;
184
185    use std::io::Cursor;
186
187    #[test]
188    fn varbyte_encode() {
189        let test_var = vec![0, 1, 2, 3, 4, 5];
190        let bytes = VarBytes(test_var);
191
192        assert_eq!(bytes.encoded_length() as usize, 2 + 6);
193
194        let mut buf = Vec::new();
195        bytes.encode(&mut buf).unwrap();
196
197        assert_eq!(&buf, &[0, 6, 0, 1, 2, 3, 4, 5]);
198
199        let mut reader = Cursor::new(buf);
200        let decoded = VarBytes::decode(&mut reader).unwrap();
201
202        assert_eq!(decoded, bytes);
203    }
204}