wx_sdk/mp/event/msg_event/
event_scan.rs1use crate::{
2 error::SdkError,
3 mp::event::{xmlutil::get_text_from_root, ReceivedMessageParser},
4 SdkResult,
5};
6
7pub struct ScanEvent {
8 pub event_key: String,
9 pub ticket: String,
10}
11
12impl ReceivedMessageParser for ScanEvent {
13 type ReceivedMessage = ScanEvent;
14
15 fn from_xml(node: &roxmltree::Node) -> SdkResult<Self::ReceivedMessage> {
16 let event_key = get_text_from_root(node, "EventKey")?;
17 let ticket = get_text_from_root(node, "Ticket")?;
18 Ok(ScanEvent {
19 event_key: event_key.to_string(),
20 ticket: ticket.to_string(),
21 })
22 }
23}
24
25pub struct MenuScanEvent {
26 pub event_key: String,
27 pub scan_type: String,
28 pub scan_result: String,
29}
30
31impl ReceivedMessageParser for MenuScanEvent {
32 type ReceivedMessage = MenuScanEvent;
33
34 fn from_xml(node: &roxmltree::Node) -> SdkResult<Self::ReceivedMessage> {
35 let event_key = get_text_from_root(node, "EventKey")?;
36 let scan_code_info = node
37 .descendants()
38 .find(|n| n.has_tag_name("ScanCodeInfo"))
39 .ok_or_else(|| {
40 SdkError::InvalidParams(format!(
41 "Parse XML msg from wechat error: tag `{}` is none",
42 "ScanCodeInfo"
43 ))
44 })?;
45 let scan_type = get_text_from_root(&scan_code_info, "ScanType")?;
46 let scan_result = get_text_from_root(&scan_code_info, "ScanResult")?;
47 let event = MenuScanEvent {
48 event_key: event_key.to_owned(),
49 scan_type: scan_type.to_owned(),
50 scan_result: scan_result.to_owned(),
51 };
52 Ok(event)
53 }
54}
55
56#[cfg(test)]
57mod tests {
58 use super::*;
59 use crate::SdkResult;
60
61 #[test]
62 pub fn parse() -> SdkResult<()> {
63 use roxmltree::Document;
64 let s = "<xml>
65 <ToUserName><![CDATA[toUser]]></ToUserName>
66 <FromUserName><![CDATA[FromUser]]></FromUserName>
67 <CreateTime>123456789</CreateTime>
68 <MsgType><![CDATA[event]]></MsgType>
69 <Event><![CDATA[SCAN]]></Event>
70 <EventKey><![CDATA[SCENE_VALUE]]></EventKey>
71 <Ticket><![CDATA[TICKET]]></Ticket>
72 </xml>";
73 let node = Document::parse(&s)?;
74 let msg = ScanEvent::from_xml(&node.root())?;
75
76 assert_eq!(msg.event_key, "SCENE_VALUE");
77 Ok(())
78 }
79
80 #[test]
81 pub fn parse_menuscan() -> SdkResult<()> {
82 use roxmltree::Document;
83 let s = "<xml>
84 <FromUserName><![CDATA[oMgHVjngRipVsoxg6TuX3vz6glDg]]></FromUserName>
85 <CreateTime>1408090502</CreateTime>
86 <MsgType><![CDATA[event]]></MsgType>
87 <Event><![CDATA[scancode_push]]></Event>
88 <EventKey><![CDATA[6]]></EventKey>
89 <ScanCodeInfo><ScanType><![CDATA[qrcode]]></ScanType>
90 <ScanResult><![CDATA[1]]></ScanResult>
91 </ScanCodeInfo>
92 </xml>";
93 let node = Document::parse(&s)?;
94 let msg = MenuScanEvent::from_xml(&node.root())?;
95
96 assert_eq!(msg.event_key, "6");
97 assert_eq!(msg.scan_type, "qrcode");
98 assert_eq!(msg.scan_result, "1");
99 Ok(())
100 }
101}