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