whatsapp_rust/handlers/
chatstate.rs1use super::traits::StanzaHandler;
4use crate::client::Client;
5use async_trait::async_trait;
6use log::debug;
7use std::sync::Arc;
8use wacore::iq::chatstate::{
9 ChatstateParseError, ChatstateSource, ChatstateStanza, ReceivedChatState,
10};
11use wacore_binary::Jid;
12
13#[derive(Debug, Clone)]
18pub struct ChatStateEvent {
19 pub chat: Jid,
21 pub participant: Option<Jid>,
23 pub state: ReceivedChatState,
25}
26
27impl ChatStateEvent {
28 pub fn from_stanza(stanza: ChatstateStanza) -> Self {
30 let (chat, participant) = match stanza.source {
31 ChatstateSource::User { from } => (from, None),
32 ChatstateSource::Group { from, participant } => (from, Some(participant)),
33 };
34 Self {
35 chat,
36 participant,
37 state: stanza.state,
38 }
39 }
40}
41
42#[derive(Default)]
47pub struct ChatstateHandler;
48
49#[cfg_attr(target_arch = "wasm32", async_trait(?Send))]
50#[cfg_attr(not(target_arch = "wasm32"), async_trait)]
51impl StanzaHandler for ChatstateHandler {
52 fn tag(&self) -> &'static str {
53 "chatstate"
54 }
55
56 #[cfg_attr(
57 feature = "tracing",
58 tracing::instrument(name = "wa.recv.chatstate", level = "debug", skip_all)
59 )]
60 async fn handle(
61 &self,
62 client: Arc<Client>,
63 node: Arc<wacore_binary::OwnedNodeRef>,
64 _cancelled: &mut bool,
65 ) -> bool {
66 match ChatstateStanza::parse(node.get()) {
67 Ok(stanza) => {
68 debug!(
69 target: "ChatstateHandler",
70 "Received chatstate: {:?} from {:?}",
71 stanza.state,
72 stanza.source
73 );
74 client.dispatch_chatstate_event(stanza).await;
75 }
76 Err(ChatstateParseError::SelfEcho) => {
77 debug!(
78 target: "ChatstateHandler",
79 "Ignoring self-echo chatstate"
80 );
81 }
82 Err(e) => {
83 log::warn!(
84 target: "ChatstateHandler",
85 "Failed to parse chatstate stanza: {e}"
86 );
87 }
88 }
89 true
90 }
91}