1//! A crate parsing common XMPP elements into Rust structures.
2//!
3//! Each module implements the `TryFrom<&minidom::Element>` trait, which takes
4//! a minidom `Element` reference and returns a `Result`.
5//!
6//! Parsed structs can then be manipulated manually, and must be serialised
7//! back before being sent over the wire.
8
9// Copyright (c) 2017 Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
10// Copyright (c) 2017 Maxime “pep” Buquet <pep+code@bouah.net>
11//
12// This Source Code Form is subject to the terms of the Mozilla Public
13// License, v. 2.0. If a copy of the MPL was not distributed with this
14// file, You can obtain one at http://mozilla.org/MPL/2.0/.
15
16extern crate minidom;
17extern crate jid;
18extern crate base64;
19extern crate digest;
20extern crate sha_1;
21extern crate sha2;
22extern crate sha3;
23extern crate blake2;
24extern crate chrono;
25extern crate try_from;
26
27macro_rules! get_attr {
28 ($elem:ident, $attr:tt, $type:tt) => (
29 get_attr!($elem, $attr, $type, value, value.parse()?)
30 );
31 ($elem:ident, $attr:tt, optional, $value:ident, $func:expr) => (
32 match $elem.attr($attr) {
33 Some($value) => Some($func),
34 None => None,
35 }
36 );
37 ($elem:ident, $attr:tt, required, $value:ident, $func:expr) => (
38 match $elem.attr($attr) {
39 Some($value) => $func,
40 None => return Err(Error::ParseError(concat!("Required attribute '", $attr, "' missing."))),
41 }
42 );
43 ($elem:ident, $attr:tt, default, $value:ident, $func:expr) => (
44 match $elem.attr($attr) {
45 Some($value) => $func,
46 None => Default::default(),
47 }
48 );
49}
50
51macro_rules! generate_attribute {
52 ($elem:ident, $name:tt, {$($a:ident => $b:tt),+,}) => (
53 generate_attribute!($elem, $name, {$($a => $b),+});
54 );
55 ($elem:ident, $name:tt, {$($a:ident => $b:tt),+,}, Default = $default:ident) => (
56 generate_attribute!($elem, $name, {$($a => $b),+}, Default = $default);
57 );
58 ($elem:ident, $name:tt, {$($a:ident => $b:tt),+}) => (
59 #[derive(Debug, Clone, PartialEq)]
60 pub enum $elem {
61 $($a),+
62 }
63 impl FromStr for $elem {
64 type Err = Error;
65 fn from_str(s: &str) -> Result<$elem, Error> {
66 Ok(match s {
67 $($b => $elem::$a),+,
68 _ => return Err(Error::ParseError(concat!("Unknown value for '", $name, "' attribute."))),
69 })
70 }
71 }
72 impl IntoAttributeValue for $elem {
73 fn into_attribute_value(self) -> Option<String> {
74 Some(String::from(match self {
75 $($elem::$a => $b),+
76 }))
77 }
78 }
79 );
80 ($elem:ident, $name:tt, {$($a:ident => $b:tt),+}, Default = $default:ident) => (
81 #[derive(Debug, Clone, PartialEq)]
82 pub enum $elem {
83 $($a),+
84 }
85 impl FromStr for $elem {
86 type Err = Error;
87 fn from_str(s: &str) -> Result<$elem, Error> {
88 Ok(match s {
89 $($b => $elem::$a),+,
90 _ => return Err(Error::ParseError(concat!("Unknown value for '", $name, "' attribute."))),
91 })
92 }
93 }
94 impl IntoAttributeValue for $elem {
95 #[allow(unreachable_patterns)]
96 fn into_attribute_value(self) -> Option<String> {
97 Some(String::from(match self {
98 $elem::$default => return None,
99 $($elem::$a => $b),+
100 }))
101 }
102 }
103 impl Default for $elem {
104 fn default() -> $elem {
105 $elem::$default
106 }
107 }
108 );
109}
110
111macro_rules! generate_id {
112 ($elem:ident) => (
113 #[derive(Debug, Clone, PartialEq, Eq, Hash)]
114 pub struct $elem(pub String);
115 impl FromStr for $elem {
116 type Err = Error;
117 fn from_str(s: &str) -> Result<$elem, Error> {
118 // TODO: add a way to parse that differently when needed.
119 Ok($elem(String::from(s)))
120 }
121 }
122 impl IntoAttributeValue for $elem {
123 fn into_attribute_value(self) -> Option<String> {
124 Some(self.0)
125 }
126 }
127 );
128}
129
130/// Error type returned by every parser on failure.
131pub mod error;
132/// XML namespace definitions used through XMPP.
133pub mod ns;
134
135/// RFC 6120: Extensible Messaging and Presence Protocol (XMPP): Core
136pub mod message;
137/// RFC 6120: Extensible Messaging and Presence Protocol (XMPP): Core
138pub mod presence;
139/// RFC 6120: Extensible Messaging and Presence Protocol (XMPP): Core
140pub mod iq;
141/// RFC 6120: Extensible Messaging and Presence Protocol (XMPP): Core
142pub mod stanza_error;
143
144/// RFC 6121: Extensible Messaging and Presence Protocol (XMPP): Instant Messaging and Presence
145pub mod roster;
146
147/// XEP-0004: Data Forms
148pub mod data_forms;
149
150/// XEP-0030: Service Discovery
151pub mod disco;
152
153/// XEP-0045: Multi-User Chat
154pub mod muc;
155
156/// XEP-0047: In-Band Bytestreams
157pub mod ibb;
158
159/// XEP-0059: Result Set Management
160pub mod rsm;
161
162/// XEP-0060: Publish-Subscribe
163pub mod pubsub;
164
165/// XEP-0077: In-Band Registration
166pub mod ibr;
167
168/// XEP-0085: Chat State Notifications
169pub mod chatstates;
170
171/// XEP-0115: Entity Capabilities
172pub mod caps;
173
174/// XEP-0166: Jingle
175pub mod jingle;
176
177/// XEP-0184: Message Delivery Receipts
178pub mod receipts;
179
180/// XEP-0199: XMPP Ping
181pub mod ping;
182
183/// XEP-0203: Delayed Delivery
184pub mod delay;
185
186/// XEP-0221: Data Forms Media Element
187pub mod media_element;
188
189/// XEP-0224: Attention
190pub mod attention;
191
192/// XEP-0234: Jingle File Transfer
193pub mod jingle_ft;
194
195/// XEP-0260: Jingle SOCKS5 Bytestreams Transport Method
196pub mod jingle_s5b;
197
198/// XEP-0261: Jingle In-Band Bytestreams Transport Method
199pub mod jingle_ibb;
200
201/// XEP-0297: Stanza Forwarding
202pub mod forwarding;
203
204/// XEP-0300: Use of Cryptographic Hash Functions in XMPP
205pub mod hashes;
206
207/// XEP-0308: Last Message Correction
208pub mod message_correct;
209
210/// XEP-0313: Message Archive Management
211pub mod mam;
212
213/// XEP-0319: Last User Interaction in Presence
214pub mod idle;
215
216/// XEP-0353: Jingle Message Initiation
217pub mod jingle_message;
218
219/// XEP-0359: Unique and Stable Stanza IDs
220pub mod stanza_id;
221
222/// XEP-0380: Explicit Message Encryption
223pub mod eme;
224
225/// XEP-0390: Entity Capabilities 2.0
226pub mod ecaps2;