value-object-pattern 0.1.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (73) hide show
  1. value_object_pattern/__init__.py +10 -0
  2. value_object_pattern/decorators/__init__.py +7 -0
  3. value_object_pattern/decorators/value_object_process.py +83 -0
  4. value_object_pattern/decorators/value_object_validation.py +78 -0
  5. value_object_pattern/models/__init__.py +3 -0
  6. value_object_pattern/models/value_object.py +383 -0
  7. value_object_pattern/py.typed +0 -0
  8. value_object_pattern/usables/__init__.py +54 -0
  9. value_object_pattern/usables/dates/__init__.py +9 -0
  10. value_object_pattern/usables/dates/date/__init__.py +7 -0
  11. value_object_pattern/usables/dates/date/date_value_object.py +162 -0
  12. value_object_pattern/usables/dates/date/string_date_value_object.py +201 -0
  13. value_object_pattern/usables/dates/datetime/__init__.py +7 -0
  14. value_object_pattern/usables/dates/datetime/datetime_value_object.py +193 -0
  15. value_object_pattern/usables/dates/datetime/string_datetime_value_object.py +237 -0
  16. value_object_pattern/usables/identifiers/__init__.py +7 -0
  17. value_object_pattern/usables/identifiers/country_ids/__init__.py +3 -0
  18. value_object_pattern/usables/identifiers/country_ids/spain/__init__.py +3 -0
  19. value_object_pattern/usables/identifiers/country_ids/spain/dni_value_object.py +63 -0
  20. value_object_pattern/usables/identifiers/string_uuid_value_object.py +56 -0
  21. value_object_pattern/usables/identifiers/uuid_value_object.py +40 -0
  22. value_object_pattern/usables/internet/__init__.py +38 -0
  23. value_object_pattern/usables/internet/api_keys/__init__.py +13 -0
  24. value_object_pattern/usables/internet/api_keys/aws_access_key_id_value_object.py +40 -0
  25. value_object_pattern/usables/internet/api_keys/aws_secret_access_key_value_object.py +40 -0
  26. value_object_pattern/usables/internet/api_keys/github_personal_access_token_value_object.py +41 -0
  27. value_object_pattern/usables/internet/api_keys/openai_api_key_value_object.py +40 -0
  28. value_object_pattern/usables/internet/api_keys/resend_api_key_value_object.py +40 -0
  29. value_object_pattern/usables/internet/aws_cloud_region_value_object.py +77 -0
  30. value_object_pattern/usables/internet/domain_value_object.py +149 -0
  31. value_object_pattern/usables/internet/host_value_object.py +143 -0
  32. value_object_pattern/usables/internet/ipv4_address_value_object.py +305 -0
  33. value_object_pattern/usables/internet/ipv4_network_value_object.py +165 -0
  34. value_object_pattern/usables/internet/ipv6_address_value_object.py +288 -0
  35. value_object_pattern/usables/internet/ipv6_network_value_object.py +145 -0
  36. value_object_pattern/usables/internet/mac_address_value_object.py +390 -0
  37. value_object_pattern/usables/internet/port_value_object.py +682 -0
  38. value_object_pattern/usables/internet/uri/__init__.py +11 -0
  39. value_object_pattern/usables/internet/uri/http_https_url_value_object.py +39 -0
  40. value_object_pattern/usables/internet/uri/http_url_value_object.py +39 -0
  41. value_object_pattern/usables/internet/uri/https_url_value_object.py +39 -0
  42. value_object_pattern/usables/internet/uri/url_value_object.py +396 -0
  43. value_object_pattern/usables/primitives/__init__.py +45 -0
  44. value_object_pattern/usables/primitives/boolean/__init__.py +9 -0
  45. value_object_pattern/usables/primitives/boolean/boolean_value_object.py +36 -0
  46. value_object_pattern/usables/primitives/boolean/false_value_object.py +37 -0
  47. value_object_pattern/usables/primitives/boolean/true_value_object.py +37 -0
  48. value_object_pattern/usables/primitives/bytes/__init__.py +3 -0
  49. value_object_pattern/usables/primitives/bytes/bytes_value_object.py +36 -0
  50. value_object_pattern/usables/primitives/float/__init__.py +9 -0
  51. value_object_pattern/usables/primitives/float/float_value_object.py +36 -0
  52. value_object_pattern/usables/primitives/float/negative_float_value_object.py +37 -0
  53. value_object_pattern/usables/primitives/float/positive_float_value_object.py +37 -0
  54. value_object_pattern/usables/primitives/integer/__init__.py +13 -0
  55. value_object_pattern/usables/primitives/integer/even_integer_value_object.py +37 -0
  56. value_object_pattern/usables/primitives/integer/integer_value_object.py +36 -0
  57. value_object_pattern/usables/primitives/integer/negative_integer_value_object.py +37 -0
  58. value_object_pattern/usables/primitives/integer/odd_integer_value_object.py +37 -0
  59. value_object_pattern/usables/primitives/integer/positive_integer_value_object.py +37 -0
  60. value_object_pattern/usables/primitives/string/__init__.py +21 -0
  61. value_object_pattern/usables/primitives/string/alpha_value_object.py +37 -0
  62. value_object_pattern/usables/primitives/string/alphanumeric_value_object.py +37 -0
  63. value_object_pattern/usables/primitives/string/digit_value_object.py +37 -0
  64. value_object_pattern/usables/primitives/string/lowercase_string_value_object.py +37 -0
  65. value_object_pattern/usables/primitives/string/non_empty_string_value_object.py +37 -0
  66. value_object_pattern/usables/primitives/string/printable_string_value_object.py +37 -0
  67. value_object_pattern/usables/primitives/string/string_value_object.py +36 -0
  68. value_object_pattern/usables/primitives/string/trimmed_string_value_object.py +37 -0
  69. value_object_pattern/usables/primitives/string/uppercase_string_value_object.py +37 -0
  70. value_object_pattern-0.1.0.dist-info/METADATA +95 -0
  71. value_object_pattern-0.1.0.dist-info/RECORD +73 -0
  72. value_object_pattern-0.1.0.dist-info/WHEEL +4 -0
  73. value_object_pattern-0.1.0.dist-info/licenses/LICENSE.md +21 -0
@@ -0,0 +1,390 @@
1
+ # ruff: noqa: N802
2
+ """
3
+ MacAddressValueObject value object.
4
+ """
5
+
6
+ from __future__ import annotations
7
+
8
+ from re import Pattern, compile as re_compile
9
+
10
+ from value_object_pattern.decorators import process, validation
11
+ from value_object_pattern.usables import NotEmptyStringValueObject, TrimmedStringValueObject
12
+
13
+
14
+ class MacAddressValueObject(NotEmptyStringValueObject, TrimmedStringValueObject):
15
+ """
16
+ MacAddressValueObject value object ensures the provided value is a valid MAC address.
17
+
18
+ Formats:
19
+ - Raw: D5B9EB4DC2CC
20
+ - Universal: D5:B9:EB:4D:C2:CC
21
+ - Windows: D5-B9-EB-4D-C2-CC
22
+ - Cisco: D5B9.EB4D.C2CC
23
+ - Space: D5 B9 EB 4D C2 CC
24
+
25
+ Example:
26
+ ```python
27
+ from value_object_pattern.usables.internet import MacAddressValueObject
28
+
29
+ mac = MacAddressValueObject(value='D5:B9:EB:4D:C2:CC')
30
+
31
+ print(repr(mac))
32
+ # >>> MacAddressValueObject(value=D5:B9:EB:4D:C2:CC)
33
+ ```
34
+ """
35
+
36
+ __MAC_ADDRESS_VALUE_OBJECT_RAW_FORMAT_SEPARATOR: str = ''
37
+ __MAC_ADDRESS_VALUE_OBJECT_RAW_REGEX: Pattern[str] = re_compile(pattern=r'^[A-F0-9]{12}$')
38
+ __MAC_ADDRESS_VALUE_OBJECT_UNIVERSAL_SEPARATOR: str = ':'
39
+ __MAC_ADDRESS_VALUE_OBJECT_UNIVERSAL_REGEX: Pattern[str] = re_compile(pattern=r'^([A-F0-9]{2}:){5}[A-F0-9]{2}$')
40
+ __MAC_ADDRESS_VALUE_OBJECT_WINDOWS_FORMAT_SEPARATOR: str = '-'
41
+ __MAC_ADDRESS_VALUE_OBJECT_WINDOWS_REGEX: Pattern[str] = re_compile(pattern=r'^([A-F0-9]{2}-){5}[A-F0-9]{2}$')
42
+ __MAC_ADDRESS_VALUE_OBJECT_CISCO_FORMAT_SEPARATOR: str = '.'
43
+ __MAC_ADDRESS_VALUE_OBJECT_CISCO_REGEX: Pattern[str] = re_compile(pattern=r'^([A-F0-9]{4}\.){2}[0-9A-F]{4}$')
44
+ __MAC_ADDRESS_VALUE_OBJECT_SPACE_FORMAT_SEPARATOR: str = ' '
45
+ __MAC_ADDRESS_VALUE_OBJECT_SPACE_REGEX: Pattern[str] = re_compile(pattern=r'^([A-F0-9]{2} ){5}[A-F0-9]{2}$')
46
+
47
+ @process(order=0)
48
+ def _ensure_value_is_uppercase(self, value: str) -> str:
49
+ """
50
+ Ensures the value object value is uppercase.
51
+
52
+ Args:
53
+ value (str): Value.
54
+
55
+ Returns:
56
+ str: Uppercase value.
57
+ """
58
+ return value.upper()
59
+
60
+ @process(order=1)
61
+ def _ensure_value_is_normalized(self, value: str) -> str:
62
+ """
63
+ Ensures the value object value is normalized (universally formatted).
64
+
65
+ Args:
66
+ value (str): Value.
67
+
68
+ Returns:
69
+ str: Value with the normalized format (universally formatted).
70
+ """
71
+ if self.is_raw_format(value=value):
72
+ return ':'.join(value[i : i + 2] for i in range(0, len(value), 2))
73
+
74
+ if self.is_windows_format(value=value):
75
+ return value.replace(
76
+ self.__MAC_ADDRESS_VALUE_OBJECT_WINDOWS_FORMAT_SEPARATOR,
77
+ self.__MAC_ADDRESS_VALUE_OBJECT_UNIVERSAL_SEPARATOR,
78
+ )
79
+
80
+ if self.is_cisco_format(value=value):
81
+ raw_mac = value.replace(self.__MAC_ADDRESS_VALUE_OBJECT_CISCO_FORMAT_SEPARATOR, '')
82
+ return ':'.join(raw_mac[i : i + 2] for i in range(0, len(raw_mac), 2))
83
+
84
+ if self.is_space_format(value=value):
85
+ return value.replace(
86
+ self.__MAC_ADDRESS_VALUE_OBJECT_SPACE_FORMAT_SEPARATOR,
87
+ self.__MAC_ADDRESS_VALUE_OBJECT_UNIVERSAL_SEPARATOR,
88
+ )
89
+
90
+ return value
91
+
92
+ @validation(order=0)
93
+ def _ensure_value_is_valid_mac_address(self, value: str) -> None:
94
+ """
95
+ Ensures the value object value is a valid MAC address.
96
+
97
+ Args:
98
+ value (str): Value.
99
+
100
+ Raises:
101
+ ValueError: If the value is not a valid MAC address.
102
+ """
103
+ if (
104
+ not self.is_raw_format(value=value)
105
+ and not self.is_universal_format(value=value)
106
+ and not self.is_windows_format(value=value)
107
+ and not self.is_cisco_format(value=value)
108
+ and not self.is_space_format(value=value)
109
+ ):
110
+ raise ValueError(f'MacAddressValueObject value <<<{value}>>> is not a valid MAC address.')
111
+
112
+ @property
113
+ def raw_format(self) -> str:
114
+ """
115
+ Returns the MAC address in raw format (D5B9EB4DC2CC).
116
+
117
+ Returns:
118
+ str: MAC address in raw format.
119
+
120
+ Example:
121
+ ```python
122
+ from value_object_pattern.usables.internet import MacAddressValueObject
123
+
124
+ mac = MacAddressValueObject(value='D5:B9:EB:4D:C2:CC').raw_format
125
+
126
+ print(mac)
127
+ # >>> D5B9EB4DC2CC
128
+ ```
129
+ """
130
+ return self.value.replace(
131
+ self.__MAC_ADDRESS_VALUE_OBJECT_UNIVERSAL_SEPARATOR,
132
+ self.__MAC_ADDRESS_VALUE_OBJECT_RAW_FORMAT_SEPARATOR,
133
+ )
134
+
135
+ @classmethod
136
+ def is_raw_format(cls, *, value: str) -> bool:
137
+ """
138
+ Returns whether the value is a MAC address in raw format (D5B9EB4DC2CC).
139
+
140
+ Args:
141
+ value (str): Value.
142
+
143
+ Returns:
144
+ bool: Whether the value is a MAC address in raw format.
145
+
146
+ Example:
147
+ ```python
148
+ from value_object_pattern.usables.internet import MacAddressValueObject
149
+
150
+ is_raw = MacAddressValueObject.is_raw_format(value='D5B9EB4DC2CC')
151
+
152
+ print(is_raw)
153
+ # >>> True
154
+ ```
155
+ """
156
+ if type(value) is not str:
157
+ return False
158
+
159
+ return bool(cls.__MAC_ADDRESS_VALUE_OBJECT_RAW_REGEX.fullmatch(string=value.upper()))
160
+
161
+ @property
162
+ def universal_format(self) -> str:
163
+ """
164
+ Returns the MAC address in universal format (D5:B9:EB:4D:C2:CC).
165
+
166
+ Returns:
167
+ str: MAC address in universal format.
168
+
169
+ Example:
170
+ ```python
171
+ from value_object_pattern.usables.internet import MacAddressValueObject
172
+
173
+ mac = MacAddressValueObject(value='D5:B9:EB:4D:C2:CC').universal_format
174
+
175
+ print(mac)
176
+ # >>> D5:B9:EB:4D:C2:CC
177
+ ```
178
+ """
179
+ return self.value
180
+
181
+ @classmethod
182
+ def is_universal_format(cls, *, value: str) -> bool:
183
+ """
184
+ Returns whether the value is a MAC address in universal format (D5:B9:EB:4D:C2:CC).
185
+
186
+ Args:
187
+ value (str): Value.
188
+
189
+ Returns:
190
+ bool: Whether the value is a MAC address in universal format.
191
+
192
+ Example:
193
+ ```python
194
+ from value_object_pattern.usables.internet import MacAddressValueObject
195
+
196
+ is_universal = MacAddressValueObject.is_universal_format(value='D5:B9:EB:4D:C2:CC')
197
+
198
+ print(is_universal)
199
+ # >>> True
200
+ ```
201
+ """
202
+ if type(value) is not str:
203
+ return False
204
+
205
+ return bool(cls.__MAC_ADDRESS_VALUE_OBJECT_UNIVERSAL_REGEX.fullmatch(string=value.upper()))
206
+
207
+ @property
208
+ def windows_format(self) -> str:
209
+ """
210
+ Returns the MAC address in Windows format (D5-B9-EB-4D-C2-CC).
211
+
212
+ Returns:
213
+ str: MAC address in Windows format.
214
+
215
+ Example:
216
+ ```python
217
+ from value_object_pattern.usables.internet import MacAddressValueObject
218
+
219
+ mac = MacAddressValueObject(value='D5:B9:EB:4D:C2:CC').windows_format
220
+
221
+ print(mac)
222
+ # >>> D5-B9-EB-4D-C2-CC
223
+ ```
224
+ """
225
+ return self.value.replace(
226
+ self.__MAC_ADDRESS_VALUE_OBJECT_UNIVERSAL_SEPARATOR,
227
+ self.__MAC_ADDRESS_VALUE_OBJECT_WINDOWS_FORMAT_SEPARATOR,
228
+ )
229
+
230
+ @classmethod
231
+ def is_windows_format(cls, *, value: str) -> bool:
232
+ """
233
+ Returns whether the value is a MAC address in Windows format (D5-B9-EB-4D-C2-CC).
234
+
235
+ Args:
236
+ value (str): Value.
237
+
238
+ Returns:
239
+ bool: Whether the value is a MAC address in Windows format.
240
+
241
+ Example:
242
+ ```python
243
+ from value_object_pattern.usables.internet import MacAddressValueObject
244
+
245
+ is_windows = MacAddressValueObject.is_windows_format(value='D5-B9-EB-4D-C2-CC')
246
+
247
+ print(is_windows)
248
+ # >>> True
249
+ ```
250
+ """
251
+ if type(value) is not str:
252
+ return False
253
+
254
+ return bool(cls.__MAC_ADDRESS_VALUE_OBJECT_WINDOWS_REGEX.fullmatch(string=value.upper()))
255
+
256
+ @property
257
+ def cisco_format(self) -> str:
258
+ """
259
+ Returns the MAC address in Cisco format (D5B9.EB4D.C2CC).
260
+
261
+ Returns:
262
+ str: MAC address in Cisco format.
263
+
264
+ Example:
265
+ ```python
266
+ from value_object_pattern.usables.internet import MacAddressValueObject
267
+
268
+ mac = MacAddressValueObject(value='D5:B9:EB:4D:C2:CC').cisco_format
269
+
270
+ print(mac)
271
+ # >>> D5B9.EB4D.C2CC
272
+ ```
273
+ """
274
+ raw_mac = self.raw_format
275
+ return f'{raw_mac[:4]}{self.__MAC_ADDRESS_VALUE_OBJECT_CISCO_FORMAT_SEPARATOR}{raw_mac[4:8]}{self.__MAC_ADDRESS_VALUE_OBJECT_CISCO_FORMAT_SEPARATOR}{raw_mac[8:]}' # noqa: E501
276
+
277
+ @classmethod
278
+ def is_cisco_format(cls, *, value: str) -> bool:
279
+ """
280
+ Returns whether the value is a MAC address in Cisco format (D5B9.EB4D.C2CC).
281
+
282
+ Args:
283
+ value (str): Value.
284
+
285
+ Returns:
286
+ bool: Whether the value is a MAC address in Cisco format.
287
+
288
+ Example:
289
+ ```python
290
+ from value_object_pattern.usables.internet import MacAddressValueObject
291
+
292
+ is_cisco = MacAddressValueObject.is_cisco_format(value='D5B9.EB4D.C2CC')
293
+
294
+ print(is_cisco)
295
+ # >>> True
296
+ ```
297
+ """
298
+ if type(value) is not str:
299
+ return False
300
+
301
+ return bool(cls.__MAC_ADDRESS_VALUE_OBJECT_CISCO_REGEX.fullmatch(string=value.upper()))
302
+
303
+ @property
304
+ def space_format(self) -> str:
305
+ """
306
+ Returns the MAC address in space format (D5 B9 EB 4D C2 CC).
307
+
308
+ Returns:
309
+ str: MAC address in space format.
310
+
311
+ Example:
312
+ ```python
313
+ from value_object_pattern.usables.internet import MacAddressValueObject
314
+
315
+ mac = MacAddressValueObject(value='D5:B9:EB:4D:C2:CC').space_format
316
+
317
+ print(mac)
318
+ # >>> D5 B9 EB 4D C2 CC
319
+ ```
320
+ """
321
+ return self.value.replace(
322
+ self.__MAC_ADDRESS_VALUE_OBJECT_UNIVERSAL_SEPARATOR,
323
+ self.__MAC_ADDRESS_VALUE_OBJECT_SPACE_FORMAT_SEPARATOR,
324
+ )
325
+
326
+ @classmethod
327
+ def is_space_format(cls, *, value: str) -> bool:
328
+ """
329
+ Returns whether the value is a MAC address in space format (D5 B9 EB 4D C2 CC).
330
+
331
+ Args:
332
+ value (str): Value.
333
+
334
+ Returns:
335
+ bool: Whether the value is a MAC address in space format.
336
+
337
+ Example:
338
+ ```python
339
+ from value_object_pattern.usables.internet import MacAddressValueObject
340
+
341
+ is_space = MacAddressValueObject.is_space_format(value='D5 B9 EB 4D C2 CC')
342
+
343
+ print(is_space)
344
+ # >>> True
345
+ ```
346
+ """
347
+ if type(value) is not str:
348
+ return False
349
+
350
+ return bool(cls.__MAC_ADDRESS_VALUE_OBJECT_SPACE_REGEX.fullmatch(string=value.upper()))
351
+
352
+ @classmethod
353
+ def NULL(cls) -> MacAddressValueObject:
354
+ """
355
+ Returns the null MAC address.
356
+
357
+ Returns:
358
+ MacAddressValueObject: Null MAC address.
359
+
360
+ Example:
361
+ ```python
362
+ from value_object_pattern.usables.internet import MacAddressValueObject
363
+
364
+ mac = MacAddressValueObject.NULL()
365
+
366
+ print(repr(mac))
367
+ # >>> MacAddressValueObject(value=00:00:00:00:00:00')
368
+ ```
369
+ """
370
+ return cls(value='00:00:00:00:00:00')
371
+
372
+ @classmethod
373
+ def BROADCAST(cls) -> MacAddressValueObject:
374
+ """
375
+ Returns the broadcast MAC address.
376
+
377
+ Returns:
378
+ MacAddressValueObject: Broadcast MAC address.
379
+
380
+ Example:
381
+ ```python
382
+ from value_object_pattern.usables.internet import MacAddressValueObject
383
+
384
+ mac = MacAddressValueObject.BROADCAST()
385
+
386
+ print(repr(mac))
387
+ # >>> MacAddressValueObject(value=FF:FF:FF:FF:FF:FF')
388
+ ```
389
+ """
390
+ return cls(value='FF:FF:FF:FF:FF:FF')