diff options
| author | 2025-04-03 03:41:38 +0100 | |
|---|---|---|
| committer | 2025-04-03 03:41:38 +0100 | |
| commit | 91f1994af940085d5d475a97820900ebbf0eb553 (patch) | |
| tree | 6aab872f71d17a785d3d9286742fef38983d274c /stanza | |
| parent | 9ce3827a7d25714d17f266f0f50bb29f41090175 (diff) | |
| download | luz-91f1994af940085d5d475a97820900ebbf0eb553.tar.gz luz-91f1994af940085d5d475a97820900ebbf0eb553.tar.bz2 luz-91f1994af940085d5d475a97820900ebbf0eb553.zip | |
feat: better message handling, pep publish, xep_0172: nick
Diffstat (limited to 'stanza')
| -rw-r--r-- | stanza/Cargo.toml | 1 | ||||
| -rw-r--r-- | stanza/src/client/iq.rs | 9 | ||||
| -rw-r--r-- | stanza/src/client/message.rs | 15 | ||||
| -rw-r--r-- | stanza/src/client/presence.rs | 17 | ||||
| -rw-r--r-- | stanza/src/lib.rs | 2 | ||||
| -rw-r--r-- | stanza/src/xep_0060/event.rs | 21 | ||||
| -rw-r--r-- | stanza/src/xep_0060/pubsub.rs | 41 | ||||
| -rw-r--r-- | stanza/src/xep_0172.rs | 30 | 
8 files changed, 112 insertions, 24 deletions
| diff --git a/stanza/Cargo.toml b/stanza/Cargo.toml index 64962b6..3c3c3e0 100644 --- a/stanza/Cargo.toml +++ b/stanza/Cargo.toml @@ -16,5 +16,6 @@ xep_0030 = []  xep_0059 = []  xep_0060 = ["xep_0004", "dep:chrono"]  xep_0131 = [] +xep_0172 = []  xep_0199 = []  xep_0203 = ["dep:chrono"] diff --git a/stanza/src/client/iq.rs b/stanza/src/client/iq.rs index 6d0c671..50884aa 100644 --- a/stanza/src/client/iq.rs +++ b/stanza/src/client/iq.rs @@ -17,6 +17,9 @@ use crate::roster;  #[cfg(feature = "xep_0030")]  use crate::xep_0030::{self, info, items}; +#[cfg(feature = "xep_0060")] +use crate::xep_0060::pubsub::{self, Pubsub}; +  #[cfg(feature = "xep_0199")]  use crate::xep_0199::{self, Ping}; @@ -42,6 +45,8 @@ pub enum Query {      DiscoInfo(info::Query),      #[cfg(feature = "xep_0030")]      DiscoItems(items::Query), +    #[cfg(feature = "xep_0060")] +    Pubsub(Pubsub),      #[cfg(feature = "xep_0199")]      Ping(Ping),      #[cfg(feature = "rfc_6121")] @@ -67,6 +72,8 @@ impl FromElement for Query {              (Some(xep_0030::items::XMLNS), "query") => {                  Ok(Query::DiscoItems(items::Query::from_element(element)?))              } +            #[cfg(feature = "xep_0060")] +            (Some(pubsub::XMLNS), "pubsub") => Ok(Query::Pubsub(Pubsub::from_element(element)?)),              _ => Ok(Query::Unsupported),          }      } @@ -86,6 +93,8 @@ impl IntoElement for Query {              Query::DiscoInfo(query) => query.builder(),              #[cfg(feature = "xep_0030")]              Query::DiscoItems(query) => query.builder(), +            #[cfg(feature = "xep_0060")] +            Query::Pubsub(pubsub) => pubsub.builder(),          }      }  } diff --git a/stanza/src/client/message.rs b/stanza/src/client/message.rs index e521613..d94b82e 100644 --- a/stanza/src/client/message.rs +++ b/stanza/src/client/message.rs @@ -8,12 +8,14 @@ use peanuts::{  #[cfg(feature = "xep_0131")]  use crate::xep_0131::Headers; +#[cfg(feature = "xep_0172")] +use crate::xep_0172::Nick;  #[cfg(feature = "xep_0203")]  use crate::xep_0203::Delay;  use super::XMLNS; -#[derive(Debug, Clone)] +#[derive(Debug, Clone, Default)]  pub struct Message {      pub from: Option<JID>,      pub id: Option<String>, @@ -29,6 +31,8 @@ pub struct Message {      pub delay: Option<Delay>,      #[cfg(feature = "xep_0131")]      pub headers: Option<Headers>, +    #[cfg(feature = "xep_0172")] +    pub nick: Option<Nick>,  }  impl FromElement for Message { @@ -52,6 +56,9 @@ impl FromElement for Message {          #[cfg(feature = "xep_0131")]          let headers = element.child_opt()?; +        #[cfg(feature = "xep_0172")] +        let nick = element.child_opt()?; +          Ok(Message {              from,              id, @@ -65,6 +72,8 @@ impl FromElement for Message {              delay,              #[cfg(feature = "xep_0131")]              headers, +            #[cfg(feature = "xep_0172")] +            nick,          })      }  } @@ -93,6 +102,9 @@ impl IntoElement for Message {          #[cfg(feature = "xep_0131")]          let builder = builder.push_child_opt(self.headers.clone()); +        #[cfg(feature = "xep_0172")] +        let builder = builder.push_child_opt(self.nick.clone()); +          builder      }  } @@ -137,6 +149,7 @@ impl ToString for MessageType {  #[derive(Clone, Debug)]  pub struct Body {      pub lang: Option<String>, +    // TODO: string stuff      pub body: Option<String>,  } diff --git a/stanza/src/client/presence.rs b/stanza/src/client/presence.rs index 8fb96be..bffb0d0 100644 --- a/stanza/src/client/presence.rs +++ b/stanza/src/client/presence.rs @@ -8,12 +8,14 @@ use peanuts::{  #[cfg(feature = "xep_0131")]  use crate::xep_0131::Headers; +#[cfg(feature = "xep_0172")] +use crate::xep_0172::Nick;  #[cfg(feature = "xep_0203")]  use crate::xep_0203::Delay;  use super::{error::Error, XMLNS}; -#[derive(Debug, Clone)] +#[derive(Debug, Clone, Default)]  pub struct Presence {      pub from: Option<JID>,      pub id: Option<String>, @@ -28,8 +30,9 @@ pub struct Presence {      pub delay: Option<Delay>,      #[cfg(feature = "xep_0131")]      pub headers: Option<Headers>, -    // TODO: ##other -    // other: Vec<Other>, +    #[cfg(feature = "xep_0172")] +    pub nick: Option<Nick>, +    // ##other      pub errors: Vec<Error>,  } @@ -55,6 +58,9 @@ impl FromElement for Presence {          #[cfg(feature = "xep_0131")]          let headers = element.child_opt()?; +        #[cfg(feature = "xep_0172")] +        let nick = element.child_opt()?; +          Ok(Presence {              from,              id, @@ -69,6 +75,8 @@ impl FromElement for Presence {              delay,              #[cfg(feature = "xep_0131")]              headers, +            #[cfg(feature = "xep_0172")] +            nick,          })      }  } @@ -92,6 +100,9 @@ impl IntoElement for Presence {          #[cfg(feature = "xep_0131")]          let builder = builder.push_child_opt(self.headers.clone()); +        #[cfg(feature = "xep_0172")] +        let builder = builder.push_child_opt(self.nick.clone()); +          builder      }  } diff --git a/stanza/src/lib.rs b/stanza/src/lib.rs index 0a71a26..5474aee 100644 --- a/stanza/src/lib.rs +++ b/stanza/src/lib.rs @@ -19,6 +19,8 @@ pub mod xep_0059;  pub mod xep_0060;  #[cfg(feature = "xep_0131")]  pub mod xep_0131; +#[cfg(feature = "xep_0172")] +pub mod xep_0172;  #[cfg(feature = "xep_0199")]  pub mod xep_0199;  #[cfg(feature = "xep_0203")] diff --git a/stanza/src/xep_0060/event.rs b/stanza/src/xep_0060/event.rs index bdd8b53..d2c150a 100644 --- a/stanza/src/xep_0060/event.rs +++ b/stanza/src/xep_0060/event.rs @@ -8,6 +8,8 @@ use peanuts::{  };  use crate::xep_0004::X; +#[cfg(feature = "xep_0172")] +use crate::xep_0172::{self, Nick};  pub const XMLNS: &str = "http://jabber.org/protocol/pubsub#event"; @@ -292,19 +294,28 @@ impl IntoElement for Item {  #[derive(Clone, Debug)]  pub enum Content { -    Unknown, +    #[cfg(feature = "xep_0172")] +    Nick(Nick), +    Unknown(Element),  }  impl FromElement for Content { -    fn from_element(_element: Element) -> peanuts::element::DeserializeResult<Self> { -        // TODO: types -        return Ok(Self::Unknown); +    fn from_element(element: Element) -> peanuts::element::DeserializeResult<Self> { +        match element.identify() { +            #[cfg(feature = "xep_0172")] +            (Some(xep_0172::XMLNS), "nick") => Ok(Content::Nick(Nick::from_element(element)?)), +            _ => Ok(Self::Unknown(element)), +        }      }  }  impl IntoElement for Content {      fn builder(&self) -> peanuts::element::ElementBuilder { -        panic!("unknown content cannot be serialized") +        match self { +            #[cfg(feature = "xep_0172")] +            Content::Nick(nick) => nick.builder(), +            Content::Unknown(_e) => panic!("unknown content cannot be serialized"), +        }      }  } diff --git a/stanza/src/xep_0060/pubsub.rs b/stanza/src/xep_0060/pubsub.rs index 3a15a59..25fc405 100644 --- a/stanza/src/xep_0060/pubsub.rs +++ b/stanza/src/xep_0060/pubsub.rs @@ -7,6 +7,8 @@ use peanuts::{  };  use crate::xep_0004::X; +#[cfg(feature = "xep_0172")] +use crate::xep_0172::{self, Nick};  pub const XMLNS: &str = "http://jabber.org/protocol/pubsub"; @@ -301,10 +303,10 @@ impl ToString for DefaultType {  #[derive(Clone, Debug)]  pub struct Items { -    max_items: Option<usize>, -    node: String, -    subid: Option<String>, -    items: Vec<Item>, +    pub max_items: Option<usize>, +    pub node: String, +    pub subid: Option<String>, +    pub items: Vec<Item>,  }  impl FromElement for Items { @@ -337,11 +339,11 @@ impl IntoElement for Items {      }  } -#[derive(Clone, Debug)] +#[derive(Clone, Debug, Default)]  pub struct Item { -    id: Option<String>, -    publisher: Option<String>, -    item: Option<Content>, +    pub id: Option<String>, +    pub publisher: Option<String>, +    pub item: Option<Content>,  }  impl FromElement for Item { @@ -373,19 +375,28 @@ impl IntoElement for Item {  #[derive(Clone, Debug)]  pub enum Content { -    Unknown, +    #[cfg(feature = "xep_0172")] +    Nick(Nick), +    Unknown(Element),  }  impl FromElement for Content { -    fn from_element(_element: Element) -> peanuts::element::DeserializeResult<Self> { -        // TODO: types -        return Ok(Self::Unknown); +    fn from_element(element: Element) -> peanuts::element::DeserializeResult<Self> { +        match element.identify() { +            #[cfg(feature = "xep_0172")] +            (Some(xep_0172::XMLNS), "nick") => Ok(Content::Nick(Nick::from_element(element)?)), +            _ => Ok(Self::Unknown(element)), +        }      }  }  impl IntoElement for Content {      fn builder(&self) -> peanuts::element::ElementBuilder { -        panic!("unknown content cannot be serialized") +        match self { +            #[cfg(feature = "xep_0172")] +            Content::Nick(nick) => nick.builder(), +            Content::Unknown(_e) => panic!("unknown content cannot be serialized"), +        }      }  } @@ -429,8 +440,8 @@ impl IntoElement for Options {  #[derive(Clone, Debug)]  pub struct Publish { -    node: String, -    items: Vec<Item>, +    pub node: String, +    pub items: Vec<Item>,  }  impl FromElement for Publish { diff --git a/stanza/src/xep_0172.rs b/stanza/src/xep_0172.rs new file mode 100644 index 0000000..1c24200 --- /dev/null +++ b/stanza/src/xep_0172.rs @@ -0,0 +1,30 @@ +use peanuts::{ +    element::{FromElement, IntoElement}, +    Element, +}; + +pub const XMLNS: &str = "http://jabber.org/protocol/nick"; + +#[derive(Debug, Clone)] +pub struct Nick(pub String); + +impl FromElement for Nick { +    fn from_element(mut element: peanuts::Element) -> peanuts::element::DeserializeResult<Self> { +        element.check_name("nick")?; +        element.check_namespace(XMLNS)?; + +        Ok(Self(element.pop_value_opt()?.unwrap_or_default())) +    } +} + +impl IntoElement for Nick { +    fn builder(&self) -> peanuts::element::ElementBuilder { +        let builder = Element::builder("nick", Some(XMLNS)); + +        if self.0.is_empty() { +            builder +        } else { +            builder.push_text(self.0.clone()) +        } +    } +} | 
