aldrin_core/message/
connect2.rs1use super::message_ops::Sealed;
2use super::{Message, MessageKind, MessageOps};
3use crate::error::{DeserializeError, SerializeError};
4use crate::message_deserializer::{MessageDeserializeError, MessageWithValueDeserializer};
5use crate::message_serializer::{MessageSerializeError, MessageSerializer};
6use crate::serialized_value::{SerializedValue, SerializedValueSlice};
7use crate::value_deserializer::{Deserialize, Deserializer};
8use crate::value_serializer::{AsSerializeArg, Serialize, Serializer};
9use bytes::BytesMut;
10use num_enum::{IntoPrimitive, TryFromPrimitive};
11
12#[derive(Debug, Clone, PartialEq, Eq, Default)]
13#[cfg_attr(feature = "fuzzing", derive(arbitrary::Arbitrary))]
14pub struct ConnectData {
15 pub user: Option<SerializedValue>,
16}
17
18impl ConnectData {
19 pub fn new() -> Self {
20 Self::default()
21 }
22
23 pub fn serialize_user<T: Serialize + ?Sized>(
24 &mut self,
25 user: &T,
26 ) -> Result<&mut Self, SerializeError> {
27 self.user = SerializedValue::serialize(user).map(Some)?;
28 Ok(self)
29 }
30
31 pub fn deserialize_user<T: Deserialize>(&self) -> Option<Result<T, DeserializeError>> {
32 self.user.as_deref().map(SerializedValueSlice::deserialize)
33 }
34}
35
36#[derive(IntoPrimitive, TryFromPrimitive)]
37#[repr(u32)]
38enum ConnectDataField {
39 User = 0,
40}
41
42impl Serialize for ConnectData {
43 fn serialize(&self, serializer: Serializer) -> Result<(), SerializeError> {
44 let mut serializer = serializer.serialize_struct(1)?;
45 serializer.serialize_field(ConnectDataField::User, &self.user)?;
46 serializer.finish()
47 }
48}
49
50impl Deserialize for ConnectData {
51 fn deserialize(deserializer: Deserializer) -> Result<Self, DeserializeError> {
52 let mut deserializer = deserializer.deserialize_struct()?;
53
54 let mut user = None;
55
56 while deserializer.has_more_fields() {
57 let deserializer = deserializer.deserialize_field()?;
58
59 let Ok(field) = deserializer.try_id() else {
60 deserializer.skip()?;
61 continue;
62 };
63
64 match field {
65 ConnectDataField::User => user = deserializer.deserialize()?,
66 }
67 }
68
69 deserializer.finish(Self { user })
70 }
71}
72
73impl AsSerializeArg for ConnectData {
74 type SerializeArg<'a> = &'a Self;
75
76 fn as_serialize_arg<'a>(&'a self) -> Self::SerializeArg<'a>
77 where
78 Self: 'a,
79 {
80 self
81 }
82}
83
84#[derive(Debug, Clone, PartialEq, Eq)]
85#[cfg_attr(feature = "fuzzing", derive(arbitrary::Arbitrary))]
86pub struct Connect2 {
87 pub major_version: u32,
88 pub minor_version: u32,
89 pub value: SerializedValue,
90}
91
92impl Connect2 {
93 pub fn with_serialize_data(
94 major_version: u32,
95 minor_version: u32,
96 data: &ConnectData,
97 ) -> Result<Self, SerializeError> {
98 let value = SerializedValue::serialize(data)?;
99
100 Ok(Self {
101 major_version,
102 minor_version,
103 value,
104 })
105 }
106
107 pub fn deserialize_connect_data(&self) -> Result<ConnectData, DeserializeError> {
108 self.value.deserialize()
109 }
110}
111
112impl MessageOps for Connect2 {
113 fn kind(&self) -> MessageKind {
114 MessageKind::Connect2
115 }
116
117 fn serialize_message(self) -> Result<BytesMut, MessageSerializeError> {
118 let mut serializer = MessageSerializer::with_value(self.value, MessageKind::Connect2)?;
119
120 serializer.put_varint_u32_le(self.major_version);
121 serializer.put_varint_u32_le(self.minor_version);
122
123 serializer.finish()
124 }
125
126 fn deserialize_message(buf: BytesMut) -> Result<Self, MessageDeserializeError> {
127 let mut deserializer = MessageWithValueDeserializer::new(buf, MessageKind::Connect2)?;
128
129 let major_version = deserializer.try_get_varint_u32_le()?;
130 let minor_version = deserializer.try_get_varint_u32_le()?;
131 let value = deserializer.finish()?;
132
133 Ok(Self {
134 major_version,
135 minor_version,
136 value,
137 })
138 }
139
140 fn value(&self) -> Option<&SerializedValueSlice> {
141 Some(&self.value)
142 }
143}
144
145impl Sealed for Connect2 {}
146
147impl From<Connect2> for Message {
148 fn from(msg: Connect2) -> Self {
149 Self::Connect2(msg)
150 }
151}
152
153#[cfg(test)]
154mod test {
155 use super::super::test::{assert_deserialize_eq_with_value, assert_serialize_eq};
156 use super::super::Message;
157 use super::{Connect2, ConnectData};
158
159 #[test]
160 fn connect() {
161 let serialized = [15, 0, 0, 0, 46, 4, 0, 0, 0, 39, 1, 0, 0, 1, 2];
162 let value = ConnectData::new();
163
164 let msg = Connect2::with_serialize_data(1, 2, &value).unwrap();
165 assert_serialize_eq(&msg, serialized);
166 assert_deserialize_eq_with_value(&msg, serialized, &value);
167
168 let msg = Message::Connect2(msg);
169 assert_serialize_eq(&msg, serialized);
170 assert_deserialize_eq_with_value(&msg, serialized, &value);
171 }
172}