1use crate::{
2 Pdu,
3 types::COctetString,
4 values::{InterfaceVersion, Npi, Ton},
5};
6
7macro_rules! declare_bind {
8 ($name:ident, $builder_name:ident) => {
9 crate::create! {
10 @[skip_test]
11 #[derive(Default, Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
12 #[cfg_attr(feature = "arbitrary", derive(::arbitrary::Arbitrary))]
13 pub struct $name {
14 pub system_id: COctetString<1, 16>,
17 pub password: COctetString<1, 9>,
21 pub system_type: COctetString<1, 13>,
24 pub interface_version: InterfaceVersion,
27 pub addr_ton: Ton,
32 pub addr_npi: Npi,
37 pub address_range: COctetString<1, 41>,
42 }
43 }
44
45 impl $name {
46 pub fn new(
47 system_id: COctetString<1, 16>,
48 password: COctetString<1, 9>,
49 system_type: COctetString<1, 13>,
50 interface_version: InterfaceVersion,
51 addr_ton: Ton,
52 addr_npi: Npi,
53 address_range: COctetString<1, 41>,
54 ) -> Self {
55 Self {
56 system_id,
57 password,
58 system_type,
59 interface_version,
60 addr_ton,
61 addr_npi,
62 address_range,
63 }
64 }
65
66 pub fn builder() -> $builder_name {
67 $builder_name::new()
68 }
69 }
70
71 #[derive(Debug, Default)]
72 pub struct $builder_name {
73 inner: $name,
74 }
75
76 impl $builder_name {
77 pub fn new() -> Self {
78 Self::default()
79 }
80
81 pub fn system_id(mut self, system_id: COctetString<1, 16>) -> Self {
82 self.inner.system_id = system_id;
83 self
84 }
85
86 pub fn password(mut self, password: COctetString<1, 9>) -> Self {
87 self.inner.password = password;
88 self
89 }
90
91 pub fn system_type(mut self, system_type: COctetString<1, 13>) -> Self {
92 self.inner.system_type = system_type;
93 self
94 }
95
96 pub fn interface_version(mut self, interface_version: InterfaceVersion) -> Self {
97 self.inner.interface_version = interface_version;
98 self
99 }
100
101 pub fn addr_ton(mut self, addr_ton: Ton) -> Self {
102 self.inner.addr_ton = addr_ton;
103 self
104 }
105
106 pub fn addr_npi(mut self, addr_npi: Npi) -> Self {
107 self.inner.addr_npi = addr_npi;
108 self
109 }
110
111 pub fn address_range(mut self, address_range: COctetString<1, 41>) -> Self {
112 self.inner.address_range = address_range;
113 self
114 }
115
116 pub fn build(self) -> $name {
117 self.inner
118 }
119 }
120 };
121}
122
123declare_bind!(BindTransmitter, BindTransmitterBuilder);
124declare_bind!(BindReceiver, BindReceiverBuilder);
125declare_bind!(BindTransceiver, BindTransceiverBuilder);
126
127impl From<BindTransmitter> for Pdu {
128 fn from(value: BindTransmitter) -> Self {
129 Self::BindTransmitter(value)
130 }
131}
132
133impl From<BindReceiver> for Pdu {
134 fn from(value: BindReceiver) -> Self {
135 Self::BindReceiver(value)
136 }
137}
138
139impl From<BindTransceiver> for Pdu {
140 fn from(value: BindTransceiver) -> Self {
141 Self::BindTransceiver(value)
142 }
143}
144
145#[cfg(test)]
146mod tests {
147 use std::str::FromStr;
148
149 use crate::tests::TestInstance;
150
151 use super::*;
152
153 impl TestInstance for BindTransmitter {
154 fn instances() -> alloc::vec::Vec<Self> {
155 alloc::vec![
156 Self::default(),
157 Self::builder()
158 .system_id(COctetString::from_str("system_id").unwrap())
159 .password(COctetString::from_str("password").unwrap())
160 .system_type(COctetString::from_str("system_type").unwrap())
161 .interface_version(InterfaceVersion::Smpp5_0)
162 .addr_ton(Ton::International)
163 .addr_npi(Npi::Isdn)
164 .address_range(COctetString::from_str("address_range").unwrap())
165 .build(),
166 ]
167 }
168 }
169
170 impl TestInstance for BindReceiver {
171 fn instances() -> alloc::vec::Vec<Self> {
172 alloc::vec![
173 Self::default(),
174 Self::builder()
175 .system_id(COctetString::from_str("system_id").unwrap())
176 .password(COctetString::from_str("password").unwrap())
177 .system_type(COctetString::from_str("system_type").unwrap())
178 .interface_version(InterfaceVersion::Smpp3_4)
179 .addr_ton(Ton::Alphanumeric)
180 .addr_npi(Npi::Ermes)
181 .address_range(COctetString::from_str("address_range").unwrap())
182 .build(),
183 ]
184 }
185 }
186
187 impl TestInstance for BindTransceiver {
188 fn instances() -> alloc::vec::Vec<Self> {
189 alloc::vec![
190 Self::default(),
191 Self::builder()
192 .system_id(COctetString::from_str("system_id").unwrap())
193 .password(COctetString::from_str("password").unwrap())
194 .system_type(COctetString::from_str("system_type").unwrap())
195 .interface_version(InterfaceVersion::Smpp3_3OrEarlier(2))
196 .addr_ton(Ton::International)
197 .addr_npi(Npi::Ermes)
198 .address_range(COctetString::from_str("address_range").unwrap())
199 .build(),
200 ]
201 }
202 }
203
204 #[test]
205 fn encode_decode() {
206 crate::tests::encode_decode_test_instances::<BindTransmitter>();
207 crate::tests::encode_decode_test_instances::<BindReceiver>();
208 crate::tests::encode_decode_test_instances::<BindTransceiver>();
209 }
210}