socketioxide_parser_msgpack/
lib.rs

1#![warn(
2    clippy::all,
3    clippy::todo,
4    clippy::empty_enum,
5    clippy::mem_forget,
6    clippy::unused_self,
7    clippy::filter_map_next,
8    clippy::needless_continue,
9    clippy::needless_borrow,
10    clippy::match_wildcard_for_single_variants,
11    clippy::if_let_mutex,
12    clippy::await_holding_lock,
13    clippy::match_on_vec_items,
14    clippy::imprecise_flops,
15    clippy::suboptimal_flops,
16    clippy::lossy_float_literal,
17    clippy::rest_pat_in_fully_bound_structs,
18    clippy::fn_params_excessive_bools,
19    clippy::exit,
20    clippy::inefficient_to_string,
21    clippy::linkedlist,
22    clippy::macro_use_imports,
23    clippy::option_option,
24    clippy::verbose_file_reads,
25    clippy::unnested_or_patterns,
26    rust_2018_idioms,
27    future_incompatible,
28    nonstandard_style,
29    missing_docs
30)]
31
32//! The msgpack parser sub-crate for the socketioxide crate.
33//!
34//! This is a custom parser implementation that can be enable with the `msgpack` feature flag in socketioxide.
35//!
36//! It is used to parse and serialize the msgpack packet format of the socket.io protocol:
37//! ```json
38//! {
39//!   "type": 2,
40//!   "nsp": "/",
41//!   "data": ["event", "foo"],
42//!   "id": 1
43//! }
44//! ```
45//! will be directly converted to the following msgpack binary format:
46//! `84 A4 74 79 70 65 02 A3 6E 73 70 A1 2F A4 64 61 74 61 92 A5 65 76 65 6E 74 A3 66 6F 6F A2 69 64 01`
47
48use std::str;
49
50use bytes::Bytes;
51use de::deserialize_packet;
52use ser::serialize_packet;
53use serde::Deserialize;
54use socketioxide_core::{
55    packet::Packet,
56    parser::{Parse, ParseError, ParserError, ParserState},
57    Str, Value,
58};
59
60mod de;
61mod ser;
62mod value;
63
64/// The MsgPack parser
65#[derive(Default, Debug, Clone, Copy)]
66pub struct MsgPackParser;
67
68impl Parse for MsgPackParser {
69    fn encode(self, packet: Packet) -> socketioxide_core::Value {
70        let data = serialize_packet(packet);
71        Value::Bytes(data.into())
72    }
73
74    fn decode_str(self, _: &ParserState, _data: Str) -> Result<Packet, ParseError> {
75        Err(ParseError::UnexpectedStringPacket)
76    }
77
78    fn decode_bin(self, _: &ParserState, bin: Bytes) -> Result<Packet, ParseError> {
79        deserialize_packet(bin)
80    }
81
82    fn encode_value<T: ?Sized + serde::Serialize>(
83        self,
84        data: &T,
85        event: Option<&str>,
86    ) -> Result<Value, ParserError> {
87        value::to_value(data, event).map_err(ParserError::new)
88    }
89
90    fn decode_value<'de, T: Deserialize<'de>>(
91        self,
92        value: &'de mut Value,
93        with_event: bool,
94    ) -> Result<T, ParserError> {
95        value::from_value(value, with_event).map_err(ParserError::new)
96    }
97
98    fn decode_default<'de, T: Deserialize<'de>>(
99        self,
100        value: Option<&'de Value>,
101    ) -> Result<T, ParserError> {
102        if let Some(value) = value {
103            let value = value.as_bytes().expect("value should be bytes");
104            rmp_serde::from_slice(value).map_err(ParserError::new)
105        } else {
106            rmp_serde::from_slice(&[0xc0]).map_err(ParserError::new) // nil value
107        }
108    }
109
110    fn encode_default<T: ?Sized + serde::Serialize>(self, data: &T) -> Result<Value, ParserError> {
111        rmp_serde::to_vec_named(data)
112            .map(|b| Value::Bytes(b.into()))
113            .map_err(ParserError::new)
114    }
115
116    fn read_event(self, value: &Value) -> Result<&str, ParserError> {
117        value::read_event(value).map_err(ParserError::new)
118    }
119}
120
121/// All the static binary data is generated from this script, using the official socket.io implementation:
122/// https://gist.github.com/Totodore/943fac5107325589bfbfb50f55925698
123#[cfg(test)]
124mod tests {
125    use std::str::FromStr;
126
127    use serde_json::json;
128    use socketioxide_core::{packet::ConnectPacket, Sid};
129
130    use super::*;
131    const BIN: Bytes = Bytes::from_static(&[1, 2, 3, 4]);
132
133    fn decode(value: &'static [u8]) -> Packet {
134        MsgPackParser
135            .decode_bin(&Default::default(), Bytes::from_static(value))
136            .unwrap()
137    }
138    fn encode(packet: Packet) -> Bytes {
139        match MsgPackParser.encode(packet) {
140            Value::Bytes(b) => b,
141            Value::Str(_, _) => panic!("implementation should only return bytes"),
142        }
143    }
144    fn to_event_value(data: &impl serde::Serialize, event: &str) -> Value {
145        MsgPackParser.encode_value(data, Some(event)).unwrap()
146    }
147    fn to_value(data: &impl serde::Serialize) -> Value {
148        MsgPackParser.encode_value(data, None).unwrap()
149    }
150    fn to_connect_value(data: &impl serde::Serialize) -> Value {
151        Value::Bytes(rmp_serde::to_vec_named(data).unwrap().into())
152    }
153
154    #[test]
155    fn packet_encode_connect_root_ns() {
156        const DATA: &[u8] = &[
157            131, 164, 116, 121, 112, 101, 0, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
158            129, 163, 115, 105, 100, 176, 110, 119, 122, 51, 67, 56, 117, 55, 113, 121, 115, 118,
159            103, 86, 113, 106,
160        ];
161
162        let sid = Sid::from_str("nwz3C8u7qysvgVqj").unwrap();
163        let sid = to_connect_value(&ConnectPacket { sid });
164        let packet = encode(Packet::connect("/", Some(sid)));
165        assert_eq!(DATA, packet.as_ref());
166    }
167
168    #[test]
169    fn packet_decode_connect_root_ns() {
170        const DATA: &[u8] = &[
171            131, 164, 116, 121, 112, 101, 0, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
172            129, 163, 115, 105, 100, 176, 110, 119, 122, 51, 67, 56, 117, 55, 113, 121, 115, 118,
173            103, 86, 113, 106,
174        ];
175        let sid = Sid::from_str("nwz3C8u7qysvgVqj").unwrap();
176        let sid = to_connect_value(&ConnectPacket { sid });
177        let packet = decode(DATA);
178        assert_eq!(packet, Packet::connect("/", Some(sid)));
179    }
180
181    #[test]
182    fn packet_encode_connect_custom_ns() {
183        const DATA: &[u8] = &[
184            131, 164, 116, 121, 112, 101, 0, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
185            226, 132, 162, 164, 100, 97, 116, 97, 129, 163, 115, 105, 100, 176, 110, 119, 122, 51,
186            67, 56, 117, 55, 113, 121, 115, 118, 103, 86, 113, 106,
187        ];
188
189        let sid = Sid::from_str("nwz3C8u7qysvgVqj").unwrap();
190        let sid = to_connect_value(&ConnectPacket { sid });
191        let packet = encode(Packet::connect("/admin™", Some(sid)));
192        assert_eq!(DATA, packet.as_ref());
193    }
194
195    #[test]
196    fn packet_decode_connect_custom_ns() {
197        const DATA: &[u8] = &[
198            131, 164, 116, 121, 112, 101, 0, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
199            226, 132, 162, 164, 100, 97, 116, 97, 129, 163, 115, 105, 100, 176, 110, 119, 122, 51,
200            67, 56, 117, 55, 113, 121, 115, 118, 103, 86, 113, 106,
201        ];
202
203        let sid = Sid::from_str("nwz3C8u7qysvgVqj").unwrap();
204        let sid = to_connect_value(&ConnectPacket { sid });
205        let packet = decode(DATA);
206        assert_eq!(packet, Packet::connect("/admin™", Some(sid)));
207    }
208
209    #[test]
210    fn packet_encode_disconnect_root_ns() {
211        const DATA: &[u8] = &[130, 164, 116, 121, 112, 101, 1, 163, 110, 115, 112, 161, 47];
212        let packet = encode(Packet::disconnect("/"));
213        assert_eq!(DATA, packet.as_ref());
214    }
215
216    #[test]
217    fn packet_decode_disconnect_root_ns() {
218        const DATA: &[u8] = &[130, 164, 116, 121, 112, 101, 1, 163, 110, 115, 112, 161, 47];
219        let packet = decode(DATA);
220        assert_eq!(packet, Packet::disconnect("/"));
221    }
222
223    #[test]
224    fn packet_encode_disconnect_custom_ns() {
225        const DATA: &[u8] = &[
226            130, 164, 116, 121, 112, 101, 1, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
227            226, 132, 162,
228        ];
229        let packet = encode(Packet::disconnect("/admin™"));
230        assert_eq!(DATA, packet.as_ref());
231    }
232
233    #[test]
234    fn packet_decode_disconnect_custom_ns() {
235        const DATA: &[u8] = &[
236            130, 164, 116, 121, 112, 101, 1, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
237            226, 132, 162,
238        ];
239        let packet = decode(DATA);
240        assert_eq!(packet, Packet::disconnect("/admin™"));
241    }
242
243    #[test]
244    fn packet_encode_event_root_ns() {
245        const DATA: &[u8] = &[
246            131, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
247            146, 165, 101, 118, 101, 110, 116, 129, 164, 100, 97, 116, 97, 168, 118, 97, 108, 117,
248            101, 226, 132, 162,
249        ];
250        let packet = encode(Packet::event(
251            "/",
252            to_event_value(&json!({ "data": "value™" }), "event"),
253        ));
254        assert_eq!(DATA, packet.as_ref());
255    }
256
257    #[test]
258    fn packet_decode_event_root_ns() {
259        const DATA: &[u8] = &[
260            131, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
261            146, 165, 101, 118, 101, 110, 116, 129, 164, 100, 97, 116, 97, 168, 118, 97, 108, 117,
262            101, 226, 132, 162,
263        ];
264        let data = to_event_value(&json!({ "data": "value™" }), "event");
265        let packet = decode(DATA);
266        assert_eq!(packet, Packet::event("/", data));
267    }
268    #[test]
269    fn packet_decode_event_root_ns_empty_data() {
270        const DATA: &[u8] = &[
271            131, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
272            145, 165, 101, 118, 101, 110, 116,
273        ];
274        let data = to_event_value(&[0; 0], "event");
275        let packet = decode(DATA);
276        assert_eq!(packet, Packet::event("/", data));
277    }
278
279    #[test]
280    fn packet_encode_event_root_ns_with_ack_id() {
281        const DATA: &[u8] = &[
282            132, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
283            146, 165, 101, 118, 101, 110, 116, 129, 164, 100, 97, 116, 97, 168, 118, 97, 108, 117,
284            101, 226, 132, 162, 162, 105, 100, 1,
285        ];
286        let data = to_event_value(&json!({ "data": "value™" }), "event");
287        let mut packet = Packet::event("/", data);
288        packet.inner.set_ack_id(1);
289        let packet = encode(packet);
290        assert_eq!(DATA, packet.as_ref());
291    }
292
293    #[test]
294    fn packet_decode_event_root_ns_with_ack_id() {
295        const DATA: &[u8] = &[
296            132, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
297            146, 165, 101, 118, 101, 110, 116, 129, 164, 100, 97, 116, 97, 168, 118, 97, 108, 117,
298            101, 226, 132, 162, 162, 105, 100, 1,
299        ];
300        let data = to_event_value(&json!({ "data": "value™" }), "event");
301        let mut packet_comp = Packet::event("/", data);
302        packet_comp.inner.set_ack_id(1);
303        let packet = decode(DATA);
304        assert_eq!(packet, packet_comp);
305    }
306    #[test]
307    fn packet_encode_event_custom_ns() {
308        const DATA: &[u8] = &[
309            131, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
310            226, 132, 162, 164, 100, 97, 116, 97, 146, 165, 101, 118, 101, 110, 116, 129, 164, 100,
311            97, 116, 97, 168, 118, 97, 108, 117, 101, 226, 132, 162,
312        ];
313        let data = to_event_value(&json!({"data": "value™"}), "event");
314        let packet = encode(Packet::event("/admin™", data));
315
316        assert_eq!(DATA, packet.as_ref());
317    }
318
319    #[test]
320    fn packet_decode_event_custom_ns() {
321        const DATA: &[u8] = &[
322            131, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
323            226, 132, 162, 164, 100, 97, 116, 97, 146, 165, 101, 118, 101, 110, 116, 129, 164, 100,
324            97, 116, 97, 168, 118, 97, 108, 117, 101, 226, 132, 162,
325        ];
326        let data = to_event_value(&json!({"data": "value™"}), "event");
327        let packet = decode(DATA);
328
329        assert_eq!(packet, Packet::event("/admin™", data));
330    }
331    #[test]
332    fn packet_encode_event_custom_ns_with_ack_id() {
333        const DATA: &[u8] = &[
334            132, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
335            226, 132, 162, 164, 100, 97, 116, 97, 146, 165, 101, 118, 101, 110, 116, 129, 164, 100,
336            97, 116, 97, 168, 118, 97, 108, 117, 101, 226, 132, 162, 162, 105, 100, 1,
337        ];
338        let data = to_event_value(&json!({"data": "value™"}), "event");
339        let mut packet = Packet::event("/admin™", data);
340        packet.inner.set_ack_id(1);
341        let packet = encode(packet);
342        assert_eq!(DATA, packet.as_ref());
343    }
344
345    #[test]
346    fn packet_decode_event_custom_ns_with_ack_id() {
347        const DATA: &[u8] = &[
348            132, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
349            226, 132, 162, 164, 100, 97, 116, 97, 146, 165, 101, 118, 101, 110, 116, 129, 164, 100,
350            97, 116, 97, 168, 118, 97, 108, 117, 101, 226, 132, 162, 162, 105, 100, 1,
351        ];
352        let data = to_event_value(&json!({"data": "value™"}), "event");
353        let mut packet_ref = Packet::event("/admin™", data);
354        packet_ref.inner.set_ack_id(1);
355        let packet = decode(DATA);
356        assert_eq!(packet, packet_ref);
357    }
358
359    #[test]
360    fn packet_encode_event_ack_root_ns() {
361        const DATA: &[u8] = &[
362            132, 164, 116, 121, 112, 101, 3, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
363            145, 164, 100, 97, 116, 97, 162, 105, 100, 54,
364        ];
365        let data = to_value(&"data");
366        let packet = encode(Packet::ack("/", data, 54));
367        assert_eq!(DATA, packet.as_ref());
368    }
369
370    #[test]
371    fn packet_decode_event_ack_root_ns() {
372        const DATA: &[u8] = &[
373            132, 164, 116, 121, 112, 101, 3, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
374            145, 164, 100, 97, 116, 97, 162, 105, 100, 54,
375        ];
376        let data = to_value(&"data");
377        let packet = decode(DATA);
378        assert_eq!(packet, Packet::ack("/", data, 54));
379    }
380
381    #[test]
382    fn packet_encode_event_ack_custom_ns() {
383        const DATA: &[u8] = &[
384            132, 164, 116, 121, 112, 101, 3, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
385            226, 132, 162, 164, 100, 97, 116, 97, 145, 164, 100, 97, 116, 97, 162, 105, 100, 54,
386        ];
387
388        let data = to_value(&"data");
389        let packet = encode(Packet::ack("/admin™", data, 54));
390        assert_eq!(DATA, packet.as_ref());
391    }
392
393    #[test]
394    fn packet_decode_event_ack_custom_ns() {
395        const DATA: &[u8] = &[
396            132, 164, 116, 121, 112, 101, 3, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
397            226, 132, 162, 164, 100, 97, 116, 97, 145, 164, 100, 97, 116, 97, 162, 105, 100, 54,
398        ];
399
400        let data = to_value(&["data"]);
401        let packet = decode(DATA);
402        assert_eq!(packet, Packet::ack("/admin™", data, 54));
403    }
404
405    #[test]
406    fn packet_encode_binary_event_root_ns() {
407        const DATA: &[u8] = &[
408            131, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
409            147, 165, 101, 118, 101, 110, 116, 129, 164, 100, 97, 116, 97, 168, 118, 97, 108, 117,
410            101, 226, 132, 162, 196, 4, 1, 2, 3, 4,
411        ];
412        let data = to_event_value(&(json!({ "data": "value™" }), BIN), "event");
413        let packet = encode(Packet::event("/", data));
414        assert_eq!(DATA, packet.as_ref());
415    }
416
417    #[test]
418    fn packet_decode_binary_event_root_ns() {
419        const DATA: &[u8] = &[
420            131, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
421            147, 165, 101, 118, 101, 110, 116, 129, 164, 100, 97, 116, 97, 168, 118, 97, 108, 117,
422            101, 226, 132, 162, 196, 4, 1, 2, 3, 4,
423        ];
424        let data = to_event_value(&(json!({ "data": "value™" }), BIN), "event");
425        let packet = decode(DATA);
426        assert_eq!(packet, Packet::event("/", data));
427    }
428
429    #[test]
430    fn packet_encode_binary_event_root_ns_with_ack_id() {
431        const DATA: &[u8] = &[
432            132, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
433            147, 165, 101, 118, 101, 110, 116, 129, 164, 100, 97, 116, 97, 168, 118, 97, 108, 117,
434            101, 226, 132, 162, 196, 4, 1, 2, 3, 4, 162, 105, 100, 204, 254,
435        ];
436        let data = to_event_value(&(json!({ "data": "value™" }), BIN), "event");
437        let mut packet = Packet::event("/", data);
438        packet.inner.set_ack_id(254);
439        let packet = encode(packet);
440
441        assert_eq!(DATA, packet.as_ref());
442    }
443
444    #[test]
445    fn packet_decode_binary_event_root_ns_with_ack_id() {
446        const DATA: &[u8] = &[
447            132, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
448            147, 165, 101, 118, 101, 110, 116, 129, 164, 100, 97, 116, 97, 168, 118, 97, 108, 117,
449            101, 226, 132, 162, 196, 4, 1, 2, 3, 4, 162, 105, 100, 204, 254,
450        ];
451        let data = to_event_value(&(json!({ "data": "value™" }), BIN), "event");
452        let mut packet_ref = Packet::event("/", data);
453        packet_ref.inner.set_ack_id(254);
454        let packet = decode(DATA);
455
456        assert_eq!(packet, packet_ref);
457    }
458
459    #[test]
460    fn packet_encode_binary_event_custom_ns() {
461        const DATA: &[u8] = &[
462            131, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
463            226, 132, 162, 164, 100, 97, 116, 97, 147, 165, 101, 118, 101, 110, 116, 129, 164, 100,
464            97, 116, 97, 168, 118, 97, 108, 117, 101, 226, 132, 162, 196, 4, 1, 2, 3, 4,
465        ];
466        let data = to_event_value(&(json!({"data": "value™"}), BIN), "event");
467        let packet = encode(Packet::event("/admin™", data));
468
469        assert_eq!(DATA, packet.as_ref());
470    }
471
472    #[test]
473    fn packet_decode_binary_event_custom_ns() {
474        const DATA: &[u8] = &[
475            131, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
476            226, 132, 162, 164, 100, 97, 116, 97, 147, 165, 101, 118, 101, 110, 116, 129, 164, 100,
477            97, 116, 97, 168, 118, 97, 108, 117, 101, 226, 132, 162, 196, 4, 1, 2, 3, 4,
478        ];
479        let data = to_event_value(&(json!({"data": "value™"}), BIN), "event");
480        let packet = decode(DATA);
481
482        assert_eq!(packet, Packet::event("/admin™", data));
483    }
484
485    #[test]
486    fn packet_encode_binary_event_custom_ns_with_ack_id() {
487        const DATA: &[u8] = &[
488            132, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
489            226, 132, 162, 164, 100, 97, 116, 97, 147, 165, 101, 118, 101, 110, 116, 129, 164, 100,
490            97, 116, 97, 168, 118, 97, 108, 117, 101, 226, 132, 162, 196, 4, 1, 2, 3, 4, 162, 105,
491            100, 204, 254,
492        ];
493        let data = to_event_value(&(json!({"data": "value™"}), BIN), "event");
494        let mut packet = Packet::event("/admin™", data);
495        packet.inner.set_ack_id(254);
496        let packet = encode(packet);
497        assert_eq!(DATA, packet.as_ref());
498    }
499
500    #[test]
501    fn packet_decode_binary_event_custom_ns_with_ack_id() {
502        const DATA: &[u8] = &[
503            132, 164, 116, 121, 112, 101, 2, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
504            226, 132, 162, 164, 100, 97, 116, 97, 147, 165, 101, 118, 101, 110, 116, 129, 164, 100,
505            97, 116, 97, 168, 118, 97, 108, 117, 101, 226, 132, 162, 196, 4, 1, 2, 3, 4, 162, 105,
506            100, 204, 254,
507        ];
508        let data = to_event_value(&(json!({"data": "value™"}), BIN), "event");
509        let mut packet_ref = Packet::event("/admin™", data);
510        packet_ref.inner.set_ack_id(254);
511        let packet = decode(DATA);
512        assert_eq!(packet, packet_ref);
513    }
514
515    #[test]
516    fn packet_encode_binary_ack_root_ns() {
517        const DATA: &[u8] = &[
518            132, 164, 116, 121, 112, 101, 3, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
519            146, 129, 164, 100, 97, 116, 97, 168, 118, 97, 108, 117, 101, 226, 132, 162, 196, 4, 1,
520            2, 3, 4, 162, 105, 100, 54,
521        ];
522        let data = to_value(&(json!({ "data": "value™" }), BIN));
523        let packet = encode(Packet::ack("/", data, 54));
524        assert_eq!(DATA, packet.as_ref());
525    }
526
527    #[test]
528    fn packet_decode_binary_ack_root_ns() {
529        const DATA: &[u8] = &[
530            132, 164, 116, 121, 112, 101, 3, 163, 110, 115, 112, 161, 47, 164, 100, 97, 116, 97,
531            146, 129, 164, 100, 97, 116, 97, 168, 118, 97, 108, 117, 101, 226, 132, 162, 196, 4, 1,
532            2, 3, 4, 162, 105, 100, 54,
533        ];
534        let data = to_value(&(json!({ "data": "value™" }), BIN));
535        let packet = decode(DATA);
536        assert_eq!(packet, Packet::ack("/", data, 54));
537    }
538
539    #[test]
540    fn packet_encode_binary_ack_custom_ns() {
541        const DATA: &[u8] = &[
542            132, 164, 116, 121, 112, 101, 3, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
543            226, 132, 162, 164, 100, 97, 116, 97, 146, 129, 164, 100, 97, 116, 97, 168, 118, 97,
544            108, 117, 101, 226, 132, 162, 196, 4, 1, 2, 3, 4, 162, 105, 100, 54,
545        ];
546        let data = to_value(&(json!({ "data": "value™" }), BIN));
547        let packet = encode(Packet::ack("/admin™", data, 54));
548
549        assert_eq!(DATA, packet.as_ref());
550    }
551
552    #[test]
553    fn packet_decode_binary_ack_custom_ns() {
554        const DATA: &[u8] = &[
555            132, 164, 116, 121, 112, 101, 3, 163, 110, 115, 112, 169, 47, 97, 100, 109, 105, 110,
556            226, 132, 162, 164, 100, 97, 116, 97, 146, 129, 164, 100, 97, 116, 97, 168, 118, 97,
557            108, 117, 101, 226, 132, 162, 196, 4, 1, 2, 3, 4, 162, 105, 100, 54,
558        ];
559        let data = to_value(&(json!({ "data": "value™" }), BIN));
560        let packet = decode(DATA);
561
562        assert_eq!(packet, Packet::ack("/admin™", data, 54));
563    }
564}