receipts.rs

  1// Copyright (c) 2017 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 try_from::TryFrom;
  8
  9use minidom::Element;
 10
 11use error::Error;
 12
 13use ns;
 14
 15#[derive(Debug, Clone)]
 16pub struct Request;
 17
 18impl TryFrom<Element> for Request {
 19    type Err = Error;
 20
 21    fn try_from(elem: Element) -> Result<Request, Error> {
 22        if !elem.is("request", ns::RECEIPTS) {
 23            return Err(Error::ParseError("This is not a request element."));
 24        }
 25        for _ in elem.children() {
 26            return Err(Error::ParseError("Unknown child in request element."));
 27        }
 28        for _ in elem.attrs() {
 29            return Err(Error::ParseError("Unknown attribute in request element."));
 30        }
 31        Ok(Request)
 32    }
 33}
 34
 35impl From<Request> for Element {
 36    fn from(_: Request) -> Element {
 37        Element::builder("request")
 38                .ns(ns::RECEIPTS)
 39                .build()
 40    }
 41}
 42
 43#[derive(Debug, Clone)]
 44pub struct Received {
 45    pub id: Option<String>,
 46}
 47
 48impl TryFrom<Element> for Received {
 49    type Err = Error;
 50
 51    fn try_from(elem: Element) -> Result<Received, Error> {
 52        if !elem.is("received", ns::RECEIPTS) {
 53            return Err(Error::ParseError("This is not a received element."));
 54        }
 55        for _ in elem.children() {
 56            return Err(Error::ParseError("Unknown child in received element."));
 57        }
 58        for (attr, _) in elem.attrs() {
 59            if attr != "id" {
 60                return Err(Error::ParseError("Unknown attribute in received element."));
 61            }
 62        }
 63        Ok(Received {
 64            id: get_attr!(elem, "id", optional),
 65        })
 66    }
 67}
 68
 69impl From<Received> for Element {
 70    fn from(received: Received) -> Element {
 71        Element::builder("received")
 72               .ns(ns::RECEIPTS)
 73               .attr("id", received.id)
 74               .build()
 75    }
 76}
 77
 78#[cfg(test)]
 79mod tests {
 80    use super::*;
 81
 82    #[test]
 83    fn test_simple() {
 84        let elem: Element = "<request xmlns='urn:xmpp:receipts'/>".parse().unwrap();
 85        Request::try_from(elem).unwrap();
 86
 87        let elem: Element = "<received xmlns='urn:xmpp:receipts'/>".parse().unwrap();
 88        Received::try_from(elem).unwrap();
 89
 90        let elem: Element = "<received xmlns='urn:xmpp:receipts' id='coucou'/>".parse().unwrap();
 91        Received::try_from(elem).unwrap();
 92    }
 93
 94    #[test]
 95    fn test_serialise() {
 96        let receipt = Request;
 97        let elem: Element = receipt.into();
 98        assert!(elem.is("request", ns::RECEIPTS));
 99        assert_eq!(elem.attrs().count(), 0);
100
101        let receipt = Received {
102            id: Some(String::from("coucou")),
103        };
104        let elem: Element = receipt.into();
105        assert!(elem.is("received", ns::RECEIPTS));
106        assert_eq!(elem.attr("id"), Some("coucou"));
107    }
108}