stream.rs

  1// Copyright (c) 2018 Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
  2//
  3// This Source Code Form is subject to the terms of the Mozilla Public
  4// License, v. 2.0. If a copy of the MPL was not distributed with this
  5// file, You can obtain one at http://mozilla.org/MPL/2.0/.
  6
  7use jid::BareJid;
  8
  9generate_element!(
 10    /// The stream opening for client-server communications.
 11    Stream, "stream", STREAM,
 12    attributes: [
 13        /// The JID of the entity opening this stream.
 14        from: Option<BareJid> = "from",
 15
 16        /// The JID of the entity receiving this stream opening.
 17        to: Option<BareJid> = "to",
 18
 19        /// The id of the stream, used for authentication challenges.
 20        id: Option<String> = "id",
 21
 22        /// The XMPP version used during this stream.
 23        version: Option<String> = "version",
 24
 25        /// The default human language for all subsequent stanzas, which will
 26        /// be transmitted to other entities for better localisation.
 27        xml_lang: Option<String> = "xml:lang",
 28    ]
 29);
 30
 31impl Stream {
 32    /// Creates a simple client→server `<stream:stream>` element.
 33    pub fn new(to: BareJid) -> Stream {
 34        Stream {
 35            from: None,
 36            to: Some(to),
 37            id: None,
 38            version: Some(String::from("1.0")),
 39            xml_lang: None,
 40        }
 41    }
 42
 43    /// Sets the [@from](#structfield.from) attribute on this `<stream:stream>`
 44    /// element.
 45    pub fn with_from(mut self, from: BareJid) -> Stream {
 46        self.from = Some(from);
 47        self
 48    }
 49
 50    /// Sets the [@id](#structfield.id) attribute on this `<stream:stream>`
 51    /// element.
 52    pub fn with_id(mut self, id: String) -> Stream {
 53        self.id = Some(id);
 54        self
 55    }
 56
 57    /// Sets the [@xml:lang](#structfield.xml_lang) attribute on this
 58    /// `<stream:stream>` element.
 59    pub fn with_lang(mut self, xml_lang: String) -> Stream {
 60        self.xml_lang = Some(xml_lang);
 61        self
 62    }
 63
 64    /// Checks whether the version matches the expected one.
 65    pub fn is_version(&self, version: &str) -> bool {
 66        match self.version {
 67            None => false,
 68            Some(ref self_version) => self_version == &String::from(version),
 69        }
 70    }
 71}
 72
 73#[cfg(test)]
 74mod tests {
 75    use super::*;
 76    use crate::Element;
 77    use std::convert::TryFrom;
 78
 79    #[cfg(target_pointer_width = "32")]
 80    #[test]
 81    fn test_size() {
 82        assert_size!(Stream, 84);
 83    }
 84
 85    #[cfg(target_pointer_width = "64")]
 86    #[test]
 87    fn test_size() {
 88        assert_size!(Stream, 168);
 89    }
 90
 91    #[test]
 92    fn test_simple() {
 93        let elem: Element = "<stream:stream xmlns='jabber:client' xmlns:stream='http://etherx.jabber.org/streams' xml:lang='en' version='1.0' id='abc' from='some-server.example'/>".parse().unwrap();
 94        let stream = Stream::try_from(elem).unwrap();
 95        assert_eq!(stream.from, Some(BareJid::domain("some-server.example")));
 96        assert_eq!(stream.to, None);
 97        assert_eq!(stream.id, Some(String::from("abc")));
 98        assert_eq!(stream.version, Some(String::from("1.0")));
 99        assert_eq!(stream.xml_lang, Some(String::from("en")));
100    }
101}