1
2
3
4 package de.powerstat.validation.values;
5
6
7 import java.util.Arrays;
8 import java.util.Formatter;
9 import java.util.Locale;
10 import java.util.Map;
11 import java.util.Objects;
12 import java.util.concurrent.ConcurrentHashMap;
13 import java.util.regex.Pattern;
14
15 import de.powerstat.validation.interfaces.IValueObject;
16
17
18
19
20
21
22
23
24
25
26
27
28 @SuppressWarnings({"java:S923", "java:S3776", "PMD.ExcessiveClassLength"})
29 public class Address implements Comparable<Address>, IValueObject
30 {
31
32
33
34
35
36
37
38
39 private static final Map<String, String> ADDRESS_FORMATS = new ConcurrentHashMap<>();
40
41
42
43
44 private static final String FORMAT1 = "%2$s%n%16$s%n%4$s%n%3$s%n%1$s%n";
45
46
47
48
49 private static final String FORMAT2 = "%2$s%n%10$s%n%9$s%n%8$s %7$s%n%6$s%nBP %11$s%n%3$s %4$s%n%1$s%n";
50
51
52
53
54 private static final String FORMAT3 = "%2$s%nBP %11$s%n%4$s%n%1$s%n";
55
56
57
58
59 private static final String FORMAT4 = "%2$s%n%8$s %7$s%n%4$s%n%1$s%n";
60
61
62
63
64 private static final String FORMAT5 = "%2$s%n%16$s%n%4$s %5$s %3$s%n%1$s%n";
65
66
67
68
69 private static final String FORMAT6 = "%2$s%n%7$s %8$s%n%3$s %4$s%n%1$s%n";
70
71
72
73
74 private static final String FORMAT7 = "%2$s%nP.O. Box %11$s%n%4$s%n%1$s%n";
75
76
77
78
79 private static final String FORMAT8 = "%2$s%n%8$s %7$s%n%4$s %5$s %3$s%n%1$s%n";
80
81
82
83
84 private static final String FORMAT9 = "%2$s%n%8$s, %7$s%n%3$s %4$s%n%1$s%n";
85
86
87
88
89 private static final String FORMAT10 = "%2$s%n%7$s %8$s%n%4$s %5$s%n%1$s%n";
90
91
92
93
94 private static final String FORMAT11 = "%2$s%n%7$s %8$s %10$s%n%3$s %4$s%n%1$s%n";
95
96
97
98
99 private static final String FORMAT12 = "%2$s%nB.P. %11$s%n%4$s%n%1$s%n";
100
101
102
103
104 private static final String FORMAT13 = "%2$s%n%10$s%n%9$s%n%8$s %7$s%n%6$s%n%4$s%n%3$s%n%1$s%n";
105
106
107
108
109 private static final String FORMAT14 = "%2$s%n%8$s %7$s, %6$s%n%3$s %4$s%n%1$s%n";
110
111
112
113
114 private static final String FORMAT15 = "%2$s%nPostboks %11$s%n%7$s %8$s, %6$s%n%3$s %4$s%n%1$s%n";
115
116
117
118
119 private static final String FORMAT16 = "%2$s%n%7$s %8$s%n%4$s%n%1$s%n";
120
121
122
123
124 private static final String FORMAT17 = "%2$s%n%9$s%n%7$s %8$s%n%6$s%n%3$s %4$s%n%1$s%n";
125
126
127
128
129 private static final String FORMAT18 = "%2$s%n%7$s %8$s%n%6$s%n%3$s %4$s%n%1$s%n";
130
131
132
133
134 private static final String FORMAT19 = "%2$s%nBP %11$s%n%8$s %7$s%n%3$s %4$s%n%1$s%n";
135
136
137
138
139 private static final String FORMAT20 = "%2$s%nP.O. Box %11$s%n%7$s %8$s%n%3$s %4$s%n%1$s%n";
140
141
142
143
144 private static final String FORMAT21 = "%2$s%n%7$s %8$s%n%6$s%n%4$s%n%1$s%n";
145
146
147
148
149 private static final String FORMAT22 = "%2$s%n%16$s%n%4$s %3$s%n%1$s%n";
150
151
152
153
154 private static final String FORMAT23 = "%2$s%nPostboks %11$s%n%7$s %8$s%n%3$s %4$s%n%1$s%n";
155
156
157
158
159 private static final String FORMAT24 = "%2$s%nP.O. Box %11$s%n%4$s%n%5$s%n%1$s%n";
160
161
162
163
164 @SuppressWarnings("java:S5857")
165 private static final Pattern NOOPTIONALS_REGEXP = Pattern.compile("\\[.*?\\]");
166
167
168
169
170 private final Country country;
171
172
173
174
175 private final PostalCode postalCode;
176
177
178
179
180 private final City city;
181
182
183
184
185 private final Province province;
186
187
188
189
190 private final District district;
191
192
193
194
195 private final Street street;
196
197
198
199
200 private final BuildingNr buildingNr;
201
202
203
204
205 private final BuildingName buildingName;
206
207
208
209
210 private final SubBuilding subBuilding;
211
212
213
214
215 private final PoBoxNumber poBoxNumber;
216
217
218
219
220 private final Department department;
221
222
223
224
225 private final Neighbourhood neighbourhood;
226
227
228
229
230 private final Block block;
231
232
233
234
235 private final BFPONumber bFPONumber;
236
237
238
239
240 private final Lines lines;
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263 static
264 {
265 Address.ADDRESS_FORMATS.put("AF", "%2$s%n%6$s, %7$s%nHouse No. %8$s%nP.O. Box %11$s%n%4$s%n%3$s%n%1$s%n");
266 Address.ADDRESS_FORMATS.put("AX", "%2$s%n%7$s %8$s%nAX-%3$s %4$s%nÅLAND%n%1$s%n");
267 Address.ADDRESS_FORMATS.put("AL", "%2$s%n%7$s%n%8$s, %10$s, %9$s%n%3$s%n%4$s%n%1$s%n");
268 Address.ADDRESS_FORMATS.put("DZ", Address.FORMAT9);
269 Address.ADDRESS_FORMATS.put("AS", Address.FORMAT8);
270 Address.ADDRESS_FORMATS.put("AD", "%2$s%n%7$s, %8$s %10$s %9$s%n%3$s %5$s%n%1$s%n");
271 Address.ADDRESS_FORMATS.put("AO", "%2$s%n%7$s %8$s%nBP %11$s%n%4$s%n%1$s%n");
272 Address.ADDRESS_FORMATS.put("AI", Address.FORMAT7);
273 Address.ADDRESS_FORMATS.put("AQ", "");
274 Address.ADDRESS_FORMATS.put("AG", Address.FORMAT7);
275 Address.ADDRESS_FORMATS.put("AR", Address.FORMAT6);
276 Address.ADDRESS_FORMATS.put("AM", "%2$s%n%7$s %8$s %10$s %9$s%n%3$s %4$s%n%1$s%n");
277 Address.ADDRESS_FORMATS.put("AW", "%2$s%n%7$s # %8$s%n%10$s%n%4$s%n%1$s%n");
278 Address.ADDRESS_FORMATS.put("AU", Address.FORMAT5);
279 Address.ADDRESS_FORMATS.put("AT", Address.FORMAT6);
280 Address.ADDRESS_FORMATS.put("AZ", Address.FORMAT6);
281 Address.ADDRESS_FORMATS.put("BS", "%2$s%n%9$s%n%7$s%nP.O. Box N %11$s%n%4$s BS %3$s%n%1$s%n");
282 Address.ADDRESS_FORMATS.put("BH", "%2$s%n%7$s %8$s%nP.O. Box %11$s%n%4$s %3$s%n%1$s%n");
283 Address.ADDRESS_FORMATS.put("BD", "%2$s%n%9$s%n%7$s %8$s%n%4$s - %3$s%n%1$s%n");
284 Address.ADDRESS_FORMATS.put("BB", "%2$s%n%9$s%n%7$s%n%4$s%n%1$s%n");
285 Address.ADDRESS_FORMATS.put("BY", "%2$s%n%7$s %8$s %9$s %10$s%n%3$s %4$s%n%6$s%n%5$s%n%1$s%n");
286 Address.ADDRESS_FORMATS.put("BE", Address.FORMAT6);
287 Address.ADDRESS_FORMATS.put("BZ", Address.FORMAT4);
288 Address.ADDRESS_FORMATS.put("BJ", Address.FORMAT3);
289 Address.ADDRESS_FORMATS.put("BM", "%2$s%n%9$s%n%8$s %7$s%n%4$s %3$s%n%1$s%n");
290 Address.ADDRESS_FORMATS.put("BT", "%2$s%n%9$s%nHouse No. %8$s%nP.O Box %11$s%n%6$s%n%4$s %3$s%n%1$s%n");
291 Address.ADDRESS_FORMATS.put("BO", "%2$s%n%7$s %8$s%nPO BOX %11$s%n%4$s%n%1$s%n");
292 Address.ADDRESS_FORMATS.put("BQ", Address.FORMAT10);
293 Address.ADDRESS_FORMATS.put("BA", Address.FORMAT6);
294 Address.ADDRESS_FORMATS.put("BW", Address.FORMAT7);
295 Address.ADDRESS_FORMATS.put("BV", "");
296 Address.ADDRESS_FORMATS.put("BR", "%2$s%n%7$s, %8$s%n%4$s - %5$s%n%3$s%n%1$s%n");
297 Address.ADDRESS_FORMATS.put("IO", Address.FORMAT13);
298 Address.ADDRESS_FORMATS.put("BN", "%2$s%n%8$s %10$s %9$s, %7$s%n%4$s%n%5$s %3$s%n%1$s%n");
299 Address.ADDRESS_FORMATS.put("BG", Address.FORMAT11);
300 Address.ADDRESS_FORMATS.put("BF", "%2$s%nBP %11$s%n%4$s %3$s%n%1$s%n");
301 Address.ADDRESS_FORMATS.put("BI", Address.FORMAT3);
302 Address.ADDRESS_FORMATS.put("KH", Address.FORMAT8);
303 Address.ADDRESS_FORMATS.put("CM", Address.FORMAT3);
304 Address.ADDRESS_FORMATS.put("CA", Address.FORMAT5);
305 Address.ADDRESS_FORMATS.put("CV", "%2$s%nC.P. %11$s%n%7$s %8$s%n%3$s %4$s%n%1$s%n");
306 Address.ADDRESS_FORMATS.put("KY", "%2$s%nP.O. Box %11$s%n%5$s %3$s%n%1$s%n");
307 Address.ADDRESS_FORMATS.put("CF", Address.FORMAT3);
308 Address.ADDRESS_FORMATS.put("TD", Address.FORMAT3);
309 Address.ADDRESS_FORMATS.put("CL", "%2$s%n%7$s %8$s%n%3$s %4$s%n%5$s%n%1$s%n");
310 Address.ADDRESS_FORMATS.put("CN", Address.FORMAT14);
311 Address.ADDRESS_FORMATS.put("CX", Address.FORMAT8);
312 Address.ADDRESS_FORMATS.put("CC", Address.FORMAT8);
313 Address.ADDRESS_FORMATS.put("CO", "%2$s%n%7$s %8$s%n%4$s[-%5$s %3$s%n%1$s%n");
314 Address.ADDRESS_FORMATS.put("KM", Address.FORMAT3);
315 Address.ADDRESS_FORMATS.put("CG", "%2$s%nBP %11$s%n%8$s, %7$s%n%4$s%n%1$s%n");
316 Address.ADDRESS_FORMATS.put("CD", Address.FORMAT12);
317 Address.ADDRESS_FORMATS.put("CK", "%2$s%n%8$s %7$s%n%6$s%n%4$s %3$s%n%1$s%n");
318 Address.ADDRESS_FORMATS.put("CR", "%2$s%n%7$s # %8$s%n%6$s, %4$s, %5$s%n%3$s%n%1$s%n");
319 Address.ADDRESS_FORMATS.put("CI", "%2$s%n%9$s%n%7$s%nB.P. %11$s %4$s%n%1$s%n");
320 Address.ADDRESS_FORMATS.put("HR", "%2$s%n%7$s %8$s%nP.P. %11$s%nHR-%3$s %4$s%n%1$s%n");
321 Address.ADDRESS_FORMATS.put("CU", "%2$s%n%7$s %8$s%n%6$s%nCP %3$s %4$s %5$s%n%1$s%n");
322 Address.ADDRESS_FORMATS.put("CW", Address.FORMAT10);
323 Address.ADDRESS_FORMATS.put("CY", "%2$s%nP.O. Box %11$s%n%7$s %8$s%nCY-%3$s %4$s%n%1$s%n");
324 Address.ADDRESS_FORMATS.put("CZ", "%2$s%n%9$s%n%7$s %8$s%n%3$s %4$s%n%1$s%n");
325 Address.ADDRESS_FORMATS.put("DK", Address.FORMAT15);
326 Address.ADDRESS_FORMATS.put("DJ", Address.FORMAT3);
327 Address.ADDRESS_FORMATS.put("DM", "%2$s%n%9$s%n%8$s %7$s%n%4$s%n%1$s%n");
328 Address.ADDRESS_FORMATS.put("DO", "%2$s%n%7$s # %8$s %10$s%n%6$s%n%3$s %4$s%n%1$s%n");
329 Address.ADDRESS_FORMATS.put("EC", "%2$s%n%7$s %8$s%n%3$s%n%4$s%n%1$s%n");
330 Address.ADDRESS_FORMATS.put("EG", "%2$s%n%8$s, %7$s%n%6$s%n%4$s%n%3$s%n%1$s%n");
331 Address.ADDRESS_FORMATS.put("SV", "%2$s%n%7$s #%8$s%nCP %3$s - %4$s%n%5$s%n%1$s%n");
332 Address.ADDRESS_FORMATS.put("GQ", Address.FORMAT16);
333 Address.ADDRESS_FORMATS.put("ER", "%2$s%nPO Box %11$s%n%7$s %8$s%n%4$s%n%1$s%n");
334 Address.ADDRESS_FORMATS.put("EE", Address.FORMAT17);
335 Address.ADDRESS_FORMATS.put("ET", "%2$s%nP.O. Box %11$s%n%9$s%n%7$s %8$s%n%3$s %4$s%n%1$s%n");
336 Address.ADDRESS_FORMATS.put("FK", "%2$s%n%9$s%n%8$s %7$s%n%4$s%n%3$s%n%1$s%n");
337 Address.ADDRESS_FORMATS.put("FO", "%2$s%n%7$s %8$s%nPO%3$s %4$s%n%1$s%n");
338 Address.ADDRESS_FORMATS.put("FJ", "%2$s%nPO BOX %11$s%n%8$s %7$s%n%4$s%n%1$s%n");
339 Address.ADDRESS_FORMATS.put("FI", "%2$s%nPL %11$s%n%7$s %8$s%nFI-%3$s %4$s%n%1$s%n");
340 Address.ADDRESS_FORMATS.put("FR", Address.FORMAT2);
341 Address.ADDRESS_FORMATS.put("GF", Address.FORMAT2);
342 Address.ADDRESS_FORMATS.put("PF", Address.FORMAT2);
343 Address.ADDRESS_FORMATS.put("TF", Address.FORMAT2);
344 Address.ADDRESS_FORMATS.put("GA", "%2$s%nBP %11$s%n%3$s %4$s%n%1$s%n");
345 Address.ADDRESS_FORMATS.put("GM", Address.FORMAT4);
346 Address.ADDRESS_FORMATS.put("GE", Address.FORMAT6);
347 Address.ADDRESS_FORMATS.put("DE", "%2$s%n[Postfach %11$s%n][%7$s %8$s%n]%3$s %4$s%n%1$s%n");
348 Address.ADDRESS_FORMATS.put("GH", "%2$s%nP.O. Box %11$s%n%4$s - %5$s%n%1$s%n");
349 Address.ADDRESS_FORMATS.put("GI", "%2$s%n%10$s%n%9$s%n%8$s %7$s%nPO Box %11$s%nGibraltar%nGX11 1AA%n%1$s%n");
350 Address.ADDRESS_FORMATS.put("GR", "%2$s%n%8$s %7$s%nP.O. Box %11$s%n%3$s %4$s%n%1$s%n");
351 Address.ADDRESS_FORMATS.put("GL", Address.FORMAT15);
352 Address.ADDRESS_FORMATS.put("GD", "%2$s%n%7$s%nP.O. BOX %11$s%n%4$s%n%1$s%n");
353 Address.ADDRESS_FORMATS.put("GP", Address.FORMAT2);
354 Address.ADDRESS_FORMATS.put("GU", Address.FORMAT5);
355 Address.ADDRESS_FORMATS.put("GT", "%2$s%n%9$s%n%8$s %7$s%n%3$s-]%4$s%n%1$s%n");
356 Address.ADDRESS_FORMATS.put("GG", Address.FORMAT1);
357 Address.ADDRESS_FORMATS.put("GN", "%2$s%n%3$s BP %11$s %4$s%n%1$s%n");
358 Address.ADDRESS_FORMATS.put("GW", Address.FORMAT6);
359 Address.ADDRESS_FORMATS.put("GY", Address.FORMAT8);
360 Address.ADDRESS_FORMATS.put("HT", "%2$s%n%9$s%n%7$s %8$s%nHT%3$s %4$s%n%1$s%n");
361 Address.ADDRESS_FORMATS.put("HM", "");
362 Address.ADDRESS_FORMATS.put("VA", "%2$s%n%7$s %8$s%n%3$s %4$s %5$s%n%1$s%n");
363 Address.ADDRESS_FORMATS.put("HN", "%2$s%n%7$s %8$s%n%3$s %4$s, %5$s%n%1$s%n");
364 Address.ADDRESS_FORMATS.put("HK", "%2$s%n%10$s%n%9$s%n%8$s %7$s%nP.O. Box %11$s%n%6$s%n%1$s%n");
365 Address.ADDRESS_FORMATS.put("HU", "%2$s%n%4$s%n%7$s %8$s%nPF. %11$s%n%3$s%n%1$s%n");
366 Address.ADDRESS_FORMATS.put("IS", Address.FORMAT6);
367 Address.ADDRESS_FORMATS.put("IN", "%2$s%n%10$s %9$s%n%8$s, %7$s%n%4$s%n%3$s%n%1$s%n");
368 Address.ADDRESS_FORMATS.put("ID", "%2$s%n%9$s%n%7$s No. %8$s, %10$s%n%6$s%n%4$s %3$s%n%1$s%n");
369 Address.ADDRESS_FORMATS.put("IR", "%2$s%n%4$s, %6$s%n%7$s%n%9$s No. %8$s, %10$s%n%5$s%n%3$s%n%1$s%n");
370 Address.ADDRESS_FORMATS.put("IQ", "%2$s%nP.O. box %11$s%n%8$s %7$s%n%4$s, %5$s%n%3$s%n%1$s%n");
371 Address.ADDRESS_FORMATS.put("IE", "%2$s%n%12$s%n%16$s%n%4$s%n%3$s%n%1$s%n");
372 Address.ADDRESS_FORMATS.put("IM", Address.FORMAT13);
373 Address.ADDRESS_FORMATS.put("IL", "%2$s%n%9$s%n%10$s%n%8$s, %7$s%n%3$s %4$s%n%1$s%n");
374 Address.ADDRESS_FORMATS.put("IT", "%2$s%n%7$s %8$s %10$s%n%3$s %4$s %5$s%n%1$s%n");
375 Address.ADDRESS_FORMATS.put("JM", "%2$s%nP.O. Box %11$s%n%8$s %7$s%n%4$s %3$s%n%1$s%n");
376 Address.ADDRESS_FORMATS.put("JP", "%2$s%n%9$s%8$s %14$s, %13$s%n%6$s, %4$s, %5$s%n%3$s%n%1$s%n");
377 Address.ADDRESS_FORMATS.put("JE", Address.FORMAT1);
378 Address.ADDRESS_FORMATS.put("JO", "%2$s%n%5$s%n%6$s%n%7$s%n%8$s %10$s%nPO Box %11$s%n%4$s %3$s%n%1$s%n");
379 Address.ADDRESS_FORMATS.put("KZ", "%2$s%n%7$s, %8$s, %10$s%n%4$s %6$s%n%1$s%n%3$s%n");
380 Address.ADDRESS_FORMATS.put("KE", "%2$s%n%9$s%n%7$s%nP O Box %11$s%n%4$s%n%3$s%n%1$s%n");
381 Address.ADDRESS_FORMATS.put("KI", "%2$s%nPO Box %11$s%n%8$s %7$s%n%4$s%n%5$s%n%1$s%n");
382 Address.ADDRESS_FORMATS.put("KP", "%2$s%n%7$s %8$s%n%4$s %3$s%n%1$s%n");
383 Address.ADDRESS_FORMATS.put("KR", "%2$s%n%9$s%n%8$s, %7$s%n%5$s %3$s%n%1$s%n");
384 Address.ADDRESS_FORMATS.put("KW", "%2$s%nB.P. %11$s %6$s%n%7$s %8$s%n%3$s %4$s%n%1$s%n");
385 Address.ADDRESS_FORMATS.put("KG", "%2$s%n%8$s, %7$s, %10$s%n%3$s %4$s%n%5$s%n%1$s%n");
386 Address.ADDRESS_FORMATS.put("LA", Address.FORMAT9);
387 Address.ADDRESS_FORMATS.put("LV", "%2$s%n%7$s %8$s, %10$s%n%4$s, %3$s%n%1$s%n");
388 Address.ADDRESS_FORMATS.put("LB", "%2$s%nP.O. Box %11$s%n%8$s %7$s. %10$s%n%4$s %3$s%n%1$s%n");
389 Address.ADDRESS_FORMATS.put("LS", "%2$s%nP.O. Box %11$s%n%7$s%n%4$s %3$s%n%1$s%n");
390 Address.ADDRESS_FORMATS.put("LR", "%2$s%n%7$s%n%3$s %4$s %5$s%n%1$s%n");
391 Address.ADDRESS_FORMATS.put("LY", Address.FORMAT16);
392 Address.ADDRESS_FORMATS.put("LI", Address.FORMAT11);
393 Address.ADDRESS_FORMATS.put("LT", Address.FORMAT18);
394 Address.ADDRESS_FORMATS.put("LU", Address.FORMAT19);
395 Address.ADDRESS_FORMATS.put("MO", "%2$s%nP.O. Box %11$s%n%7$s %8$s, %10$s%n%6$s%n%1$s%n");
396 Address.ADDRESS_FORMATS.put("MK", Address.FORMAT20);
397 Address.ADDRESS_FORMATS.put("MG", "%2$s%nB.P. %11$s%n%8$s %7$s %6$s%n%3$s %4$s%n%1$s%n");
398 Address.ADDRESS_FORMATS.put("MW", "%2$s%n%7$s%nP.O. Box %11$s%n%4$s%n%1$s%n");
399 Address.ADDRESS_FORMATS.put("MY", "%2$s%n%10$s %9$s%n%8$s, %7$s%n%6$s%n%3$s %4$s%n%5$s%n%1$s%n");
400 Address.ADDRESS_FORMATS.put("MV", "%2$s%n%8$s, %7$s%n%4$s %3$s%n%1$s%n");
401 Address.ADDRESS_FORMATS.put("ML", Address.FORMAT21);
402 Address.ADDRESS_FORMATS.put("MT", "%2$s%nKaxxa Postali %11$s%n%8$s %7$s%n%4$s%n%5$s %3$s%n%1$s%n");
403 Address.ADDRESS_FORMATS.put("MH", Address.FORMAT8);
404 Address.ADDRESS_FORMATS.put("MQ", Address.FORMAT2);
405 Address.ADDRESS_FORMATS.put("MR", Address.FORMAT12);
406 Address.ADDRESS_FORMATS.put("MU", "%2$s%n%8$s, %7$s%n%6$s%n%4$s%n%1$s%n");
407 Address.ADDRESS_FORMATS.put("YT", Address.FORMAT2);
408 Address.ADDRESS_FORMATS.put("MX", "%2$s%n%7$s %8$s - %10$s%n%6$s%n%3$s %4$s, %5$s%n%1$s%n");
409 Address.ADDRESS_FORMATS.put("FM", Address.FORMAT8);
410 Address.ADDRESS_FORMATS.put("MD", "%2$s%n%8$s %7$s, %10$s%nMD-%3$s %4$s%n%1$s%n");
411 Address.ADDRESS_FORMATS.put("MC", Address.FORMAT2);
412 Address.ADDRESS_FORMATS.put("MN", "%2$s%nPO Box %11$s%n%10$s, %7$s %8$s%n%6$s%n%4$s %3$s%n%1$s%n");
413 Address.ADDRESS_FORMATS.put("ME", Address.FORMAT6);
414 Address.ADDRESS_FORMATS.put("MS", Address.FORMAT1);
415 Address.ADDRESS_FORMATS.put("MA", "%2$s%nP.O %11$s%n%10$s%n%9$s%8$s %7$s%n%3$s %4$s%n%1$s%n");
416 Address.ADDRESS_FORMATS.put("MZ", "%2$s%nP.O %11$s%n%7$s %8$s, %10$s%n%3$s %4$s%n%5$s%n%1$s%n");
417 Address.ADDRESS_FORMATS.put("MM", "%2$s%nNo. %8$s %7$s%n%6$s%n%4$s, %3$s%n%1$s%n");
418 Address.ADDRESS_FORMATS.put("NA", Address.FORMAT7);
419 Address.ADDRESS_FORMATS.put("NR", "%2$s%n%9$s%n%11$s%n%6$s%n%4$s%n%1$s%n");
420 Address.ADDRESS_FORMATS.put("NP", "%2$s%n%7$s, %8$s%n%6$s%n%4$s %3$s%n%1$s%n");
421 Address.ADDRESS_FORMATS.put("NL", "%2$s%n%10$s%n%9$s%n%7$s %8$s%n%3$s %4$s%n%1$s%n");
422 Address.ADDRESS_FORMATS.put("NC", "%2$s%n%10$s%n%9$s%n%8$s %7$s%n%6$s%n%3$s %4$s%n%1$s%n");
423 Address.ADDRESS_FORMATS.put("NZ", Address.FORMAT22);
424 Address.ADDRESS_FORMATS.put("NI", "%2$s%n%9$s %7$s %8$s%n%6$s%n%3$s%n%4$s, %5$s%n%1$s%n");
425 Address.ADDRESS_FORMATS.put("NE", Address.FORMAT19);
426 Address.ADDRESS_FORMATS.put("NG", "%2$s%nP.O. Box %11$s%n%8$s %7$s, %6$s%n%4$s %3$s%n%5$s%n%1$s%n");
427 Address.ADDRESS_FORMATS.put("NU", Address.FORMAT22);
428 Address.ADDRESS_FORMATS.put("NF", Address.FORMAT5);
429 Address.ADDRESS_FORMATS.put("MP", Address.FORMAT8);
430 Address.ADDRESS_FORMATS.put("NO", Address.FORMAT23);
431 Address.ADDRESS_FORMATS.put("OM", "%2$s%nBP %11$s%n%3$s%n%4$s%n%5$s%n%1$s%n");
432 Address.ADDRESS_FORMATS.put("PK", "%2$s%n%9$s%n%8$s %7$s%n%6$s%n%4$s-%3$s%n%1$s%n");
433 Address.ADDRESS_FORMATS.put("PW", Address.FORMAT5);
434 Address.ADDRESS_FORMATS.put("PS", "");
435 Address.ADDRESS_FORMATS.put("PA", "%2$s%n%7$s %8$s%n%3$s, %4$s%n%5$s%n%1$s%n");
436 Address.ADDRESS_FORMATS.put("PG", "%2$s%nP.O. Box %11$s%n%4$s %3$s %5$s%n%1$s%n");
437 Address.ADDRESS_FORMATS.put("PY", Address.FORMAT6);
438 Address.ADDRESS_FORMATS.put("PE", "%2$s%n%7$s %8$s, %6$s%n%3$s%n%4$s%n%1$s%n");
439 Address.ADDRESS_FORMATS.put("PH", "%2$s%nP.O. Box %11$s%n%9$s%n%8$s %7$s, %6$s%n%4$s%n%3$s %5$s%n%1$s%n");
440 Address.ADDRESS_FORMATS.put("PN", Address.FORMAT1);
441 Address.ADDRESS_FORMATS.put("PL", Address.FORMAT6);
442 Address.ADDRESS_FORMATS.put("PT", Address.FORMAT17);
443 Address.ADDRESS_FORMATS.put("PR", Address.FORMAT5);
444 Address.ADDRESS_FORMATS.put("QA", "%2$s%n%9$s%nP.O. Box %11$s%n%4$s%n%1$s%n");
445 Address.ADDRESS_FORMATS.put("RE", Address.FORMAT2);
446 Address.ADDRESS_FORMATS.put("RO", Address.FORMAT18);
447 Address.ADDRESS_FORMATS.put("RU", "%2$s%n%7$s%na/ya %11$s%n%8$s, %10$s%n%4$s%n%6$s%n%5$s%n%1$s%n%3$s%n");
448 Address.ADDRESS_FORMATS.put("RW", Address.FORMAT12);
449 Address.ADDRESS_FORMATS.put("BL", Address.FORMAT2);
450 Address.ADDRESS_FORMATS.put("SH", Address.FORMAT1);
451 Address.ADDRESS_FORMATS.put("KN", "%2$s%n%8$s %7$s%n%4$s%n%5$s%n%1$s%n");
452 Address.ADDRESS_FORMATS.put("LC", Address.FORMAT4);
453 Address.ADDRESS_FORMATS.put("MF", Address.FORMAT2);
454 Address.ADDRESS_FORMATS.put("PM", Address.FORMAT2);
455 Address.ADDRESS_FORMATS.put("VC", "%2$s%nP.O. Box %11$s%n%8$s %7$s%n%4$s VC%3$s%n%1$s%n");
456 Address.ADDRESS_FORMATS.put("WS", "%2$s%nP.O Box %11$s%n%8$s %7$s%n%6$s%n%4$s%n%1$s%n");
457 Address.ADDRESS_FORMATS.put("SM", Address.FORMAT6);
458 Address.ADDRESS_FORMATS.put("ST", "%2$s%n%7$s %8$s, %10$s%n%4$s%n%1$s%n");
459 Address.ADDRESS_FORMATS.put("SA", "%2$s%n%11$s%n%8$s %7$s, %6$s%n%4$s %3$s%n%1$s%n");
460 Address.ADDRESS_FORMATS.put("SN", "%2$s%n%10$s%n%9$s%n%8$s %7$s%nBP %11$s%n%3$s %4$s%n%1$s%n");
461 Address.ADDRESS_FORMATS.put("RS", "%2$s%nPP %11$s%n%7$s %8$s /%10$s%n%4$s%n%3$s%n%1$s%n");
462 Address.ADDRESS_FORMATS.put("SC", "%2$s%nP.O. Box %11$s %4$s%n%5$s%n%1$s%n");
463 Address.ADDRESS_FORMATS.put("SL", Address.FORMAT4);
464 Address.ADDRESS_FORMATS.put("SG", "%2$s%n%8$s %7$s%n%10$s %9$s%n%4$s %3$s%n%1$s%n");
465 Address.ADDRESS_FORMATS.put("SX", Address.FORMAT10);
466 Address.ADDRESS_FORMATS.put("SK", Address.FORMAT20);
467 Address.ADDRESS_FORMATS.put("SI", "%2$s%np.p. %11$s%n%7$s %8$s%nSI-%3$s %4$s%n%1$s%n");
468 Address.ADDRESS_FORMATS.put("SB", Address.FORMAT24);
469 Address.ADDRESS_FORMATS.put("SO", "%2$s%nP.O. Box %11$s%n%8$s %7$s%n%4$s, %5$s %3$s%n%1$s%n");
470 Address.ADDRESS_FORMATS.put("ZA", "%2$s%nPO Box %11$s%n%10$s %9$s%n%8$s %7$s%n%6$s%n%4$s%n%3$s%n%1$s%n");
471 Address.ADDRESS_FORMATS.put("GS", Address.FORMAT1);
472 Address.ADDRESS_FORMATS.put("SS", "%2$s%nPOST OFFICE BOX %11$s%n%3$s %4$s%n%1$s%n");
473 Address.ADDRESS_FORMATS.put("ES", "%2$s%nApartado %11$s%n%9$s%n%7$s %8$s, %10$s%n%3$s %4$s%n%5$s%n%1$s%n");
474 Address.ADDRESS_FORMATS.put("LK", "%2$s%n%8$s %7$s%n%6$s%n%4$s%n%3$s%n%1$s%n");
475 Address.ADDRESS_FORMATS.put("SD", "%2$s%n%9$s%nB.P. %11$s%n%3$s%n%4$s%n%1$s%n");
476 Address.ADDRESS_FORMATS.put("SR", Address.FORMAT21);
477 Address.ADDRESS_FORMATS.put("SJ", Address.FORMAT23);
478 Address.ADDRESS_FORMATS.put("SZ", "%2$s%nP.O. Box %11$s%n%4$s%n%3$s%n%1$s%n");
479 Address.ADDRESS_FORMATS.put("SE", "%2$s%nBOX %11$s%n%7$s %8$s%nSE-%3$s %4$s%n%1$s%n");
480 Address.ADDRESS_FORMATS.put("CH", "%2$s%n%7$s %8$s%nCase postale %11$s%n%3$s %4$s%n%1$s%n");
481 Address.ADDRESS_FORMATS.put("SY", "%2$s%n%7$s, %8$s%n%6$s%n%3$s %4$s%n%1$s%n");
482 Address.ADDRESS_FORMATS.put("TW", Address.FORMAT14);
483 Address.ADDRESS_FORMATS.put("TJ", Address.FORMAT6);
484 Address.ADDRESS_FORMATS.put("TZ", "%2$s%nP.O. Box %11$s%n%10$s%n%8$s %7$s%n%3$s %4$s%n%5$s%n%1$s%n");
485 Address.ADDRESS_FORMATS.put("TH", "%2$s%n%8$s %7$s%n%6$s, %4$s, %5$s%n%3$s%n%1$s%n");
486 Address.ADDRESS_FORMATS.put("TL", "%2$s%n%8$s %7$s%n%4$s %3$s%n%1$s%n");
487 Address.ADDRESS_FORMATS.put("TG", "%2$s%n%7$s %8$s%nB.P. %11$s%n%4$s%n%1$s%n");
488 Address.ADDRESS_FORMATS.put("TK", "");
489 Address.ADDRESS_FORMATS.put("TO", "%2$s%nPO BOX %11$s%n%4$s%n%1$s%n");
490 Address.ADDRESS_FORMATS.put("TT", "%2$s%n%9$s%n%8$s %7$s %10$s%nP.O. Box %11$s%n%4$s, %3$s%n%1$s%n");
491 Address.ADDRESS_FORMATS.put("TN", "%2$s%n%8$s %7$s%n%3$s %4$s %5$s%n%1$s%n");
492 Address.ADDRESS_FORMATS.put("TR", "%2$s%n%6$s Mh.%n%7$s %8$s%n%9$s%nPK %11$s%n%3$s %4$s/%5$s%n%1$s%n");
493 Address.ADDRESS_FORMATS.put("TM", Address.FORMAT9);
494 Address.ADDRESS_FORMATS.put("TC", Address.FORMAT1);
495 Address.ADDRESS_FORMATS.put("TV", Address.FORMAT24);
496 Address.ADDRESS_FORMATS.put("UG", Address.FORMAT7);
497 Address.ADDRESS_FORMATS.put("UA", "%2$s%n%7$s, %8$s, %10$s%n%4$s, %6$s%n%5$s%n%3$s%n%1$s%n");
498 Address.ADDRESS_FORMATS.put("AE", "%2$s%nB.P. %11$s%n%4$s%n%5$s%n%1$s%n");
499 Address.ADDRESS_FORMATS.put("GB", "%2$s%n%12$s%n%16$s%n%4$s%n%3$s%n%15$s%n%1$s%n");
500 Address.ADDRESS_FORMATS.put("US", Address.FORMAT5);
501 Address.ADDRESS_FORMATS.put("UM", "");
502 Address.ADDRESS_FORMATS.put("UY", Address.FORMAT11);
503 Address.ADDRESS_FORMATS.put("UZ", "%2$s%n%7$s %8$s, %10$s%na/ya %11$s%n%4$s%n%1$s%n%3$s%n");
504 Address.ADDRESS_FORMATS.put("VU", Address.FORMAT7);
505 Address.ADDRESS_FORMATS.put("VE", "%2$s%n%6$s%n%7$s%n%9$s%n%10$s%n%4$s %3$s, %5$s%n%1$s%n");
506 Address.ADDRESS_FORMATS.put("VN", "%2$s%nP.O Box %11$s%n%10$s%nNo %8$s, %7$s%n%6$s, %4$s%n%5$s %3$s%n%1$s%n");
507 Address.ADDRESS_FORMATS.put("VG", Address.FORMAT1);
508 Address.ADDRESS_FORMATS.put("VI", Address.FORMAT5);
509 Address.ADDRESS_FORMATS.put("WF", Address.FORMAT2);
510 Address.ADDRESS_FORMATS.put("EH", "");
511 Address.ADDRESS_FORMATS.put("YE", "%2$s%nB.P. %11$s%n%8$s %7$s%n%4$s%n%1$s%n");
512 Address.ADDRESS_FORMATS.put("ZM", "%2$s%nP.O. Box %11$s%n%8$s %7$s%n%6$s%n%4$s %3$s%n%1$s%n");
513 Address.ADDRESS_FORMATS.put("ZW", "%2$s%nP.O. Box %11$s%n%8$s %7$s%n%4$s%n%5$s%n%1$s%n");
514 }
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537 protected Address(final Country country, final PostalCode postalCode, final City city, final Province province, final District district, final Street street, final BuildingNr buildingNr, final BuildingName buildingName, final SubBuilding subBuilding, final PoBoxNumber poBoxNumber, final Department department, final Neighbourhood neighbourhood, final Block block, final BFPONumber bFPONumber, final Lines lines)
538 {
539 super();
540 Objects.requireNonNull(country, "country");
541 final String format = Address.ADDRESS_FORMATS.get(country.stringValue());
542 final String formatWithoutOptionals = Address.NOOPTIONALS_REGEXP.matcher(format).replaceAll("");
543 if (formatWithoutOptionals.contains("%3$"))
544 {
545 Objects.requireNonNull(postalCode, "postalCode");
546 }
547 if (formatWithoutOptionals.contains("%4$"))
548 {
549 Objects.requireNonNull(city, "City");
550 }
551 if (formatWithoutOptionals.contains("%5$"))
552 {
553 Objects.requireNonNull(province, "Province");
554 }
555 if (formatWithoutOptionals.contains("%6$"))
556 {
557 Objects.requireNonNull(district, "District");
558 }
559 if (formatWithoutOptionals.contains("%7$"))
560 {
561 Objects.requireNonNull(street, "Street");
562 }
563 if (formatWithoutOptionals.contains("%8$"))
564 {
565 Objects.requireNonNull(buildingNr, "BuildingNr");
566 }
567 if (formatWithoutOptionals.contains("%9$"))
568 {
569 Objects.requireNonNull(buildingName, "buildingName");
570 }
571 if (formatWithoutOptionals.contains("%10$"))
572 {
573 Objects.requireNonNull(subBuilding, "subBuilding");
574 }
575 if (formatWithoutOptionals.contains("%11$"))
576 {
577 Objects.requireNonNull(poBoxNumber, "poBoxNumber");
578 }
579 if (formatWithoutOptionals.contains("%12$"))
580 {
581 Objects.requireNonNull(department, "department");
582 }
583 if (formatWithoutOptionals.contains("%13$"))
584 {
585 Objects.requireNonNull(neighbourhood, "neighbourhood");
586 }
587 if (formatWithoutOptionals.contains("%14$"))
588 {
589 Objects.requireNonNull(block, "block");
590 }
591 if (formatWithoutOptionals.contains("%15$"))
592 {
593 Objects.requireNonNull(bFPONumber, "bFPONumber");
594 }
595 if (formatWithoutOptionals.contains("%16$"))
596 {
597 Objects.requireNonNull(lines, "lines");
598 }
599 this.country = country;
600 this.postalCode = postalCode;
601 this.city = city;
602 this.province = province;
603 this.district = district;
604 this.street = street;
605 this.buildingNr = buildingNr;
606 this.buildingName = buildingName;
607 this.subBuilding = subBuilding;
608 this.poBoxNumber = poBoxNumber;
609 this.department = department;
610 this.neighbourhood = neighbourhood;
611 this.block = block;
612 this.bFPONumber = bFPONumber;
613 this.lines = lines;
614 }
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637 public static Address of(final Country country, final PostalCode postalCode, final City city, final Province province, final District district, final Street street, final BuildingNr buildingNr, final BuildingName buildingName, final SubBuilding subBuilding, final PoBoxNumber poBoxNumber, final Department department, final Neighbourhood neighbourhood, final Block block, final BFPONumber bFPONumber, final Lines lines)
638 {
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653 return new Address(country, postalCode, city, province, district, street, buildingNr, buildingName, subBuilding, poBoxNumber, department, neighbourhood, block, bFPONumber, lines);
654 }
655
656
657
658
659
660
661
662
663 public static Address of(final String value)
664 {
665 String[] values = value.split(",");
666 if ((values.length < 1) || (values.length > 15))
667 {
668 throw new IllegalArgumentException("value not in expected format: " + values.length);
669 }
670 if (values.length < 15)
671 {
672 values = Arrays.copyOf(values, 15);
673 for (int i = 1; i < 15; ++i)
674 {
675 if (values[i] == null)
676 {
677 values[i] = "";
678 }
679 }
680 }
681 final var country = Country.of(values[0]);
682 final PostalCode postalCode = values[1].isEmpty() ? null : PostalCode.of(values[1]);
683 final City city = values[2].isEmpty() ? null : City.of(values[2]);
684 final Province province = values[3].isEmpty() ? null : Province.of(values[3]);
685 final District district = values[4].isEmpty() ? null : District.of(values[4]);
686 final Street street = values[5].isEmpty() ? null : Street.of(values[5]);
687 final BuildingNr buildingNr = values[6].isEmpty() ? null : BuildingNr.of(values[6]);
688 final BuildingName buildingName = values[7].isEmpty() ? null : BuildingName.of(values[7]);
689 final SubBuilding subBuilding = values[8].isEmpty() ? null : SubBuilding.of(values[8]);
690 final PoBoxNumber poBoxNumber = values[9].isEmpty() ? null : PoBoxNumber.of(values[9]);
691 final Department department = values[10].isEmpty() ? null : Department.of(values[10]);
692 final Neighbourhood neighbourhood = values[11].isEmpty() ? null : Neighbourhood.of(values[11]);
693 final Block block = values[12].isEmpty() ? null : Block.of(values[12]);
694 final BFPONumber bFPONumber = values[13].isEmpty() ? null : BFPONumber.of(values[13]);
695 final Lines lines = values[14].isEmpty() ? null : Lines.of(values[14]);
696 return of(country, postalCode, city, province, district, street, buildingNr, buildingName, subBuilding, poBoxNumber, department, neighbourhood, block, bFPONumber, lines);
697 }
698
699
700
701
702
703
704
705 @Override
706 public String stringValue()
707 {
708 return getFormattedAddress("");
709 }
710
711
712
713
714
715
716
717
718 @Override
719 public int hashCode()
720 {
721 return Objects.hash(this.country, this.postalCode, this.city, this.province, this.district, this.street, this.buildingNr, this.buildingName, this.subBuilding, this.poBoxNumber, this.department, this.neighbourhood, this.block, this.bFPONumber, this.lines);
722 }
723
724
725
726
727
728
729
730
731
732
733 private static <T> boolean equalField(final T obj1, final T obj2)
734 {
735 return (obj1 == null) ? (obj2 == null) : obj1.equals(obj2);
736 }
737
738
739
740
741
742
743
744
745
746 @Override
747 public boolean equals(final Object obj)
748 {
749 if (this == obj)
750 {
751 return true;
752 }
753
754 if (!(obj instanceof Address))
755 {
756 return false;
757 }
758 final Address other = (Address)obj;
759 boolean result = this.country.equals(other.country);
760 if (result)
761 {
762 result = equalField(this.postalCode, other.postalCode);
763 if (result)
764 {
765 result = equalField(this.city, other.city);
766 if (result)
767 {
768 result = equalField(this.province, other.province);
769 if (result)
770 {
771 result = equalField(this.district, other.district);
772 if (result)
773 {
774 result = equalField(this.street, other.street);
775 if (result)
776 {
777 result = equalField(this.buildingNr, other.buildingNr);
778 if (result)
779 {
780 result = equalField(this.buildingName, other.buildingName);
781 if (result)
782 {
783 result = equalField(this.subBuilding, other.subBuilding);
784 if (result)
785 {
786 result = equalField(this.poBoxNumber, other.poBoxNumber);
787 if (result)
788 {
789 result = equalField(this.department, other.department);
790 if (result)
791 {
792 result = equalField(this.neighbourhood, other.neighbourhood);
793 if (result)
794 {
795 result = equalField(this.block, other.block);
796 if (result)
797 {
798 result = equalField(this.bFPONumber, other.bFPONumber);
799 if (result)
800 {
801 result = equalField(this.lines, other.lines);
802 }
803 }
804 }
805 }
806 }
807 }
808 }
809 }
810 }
811 }
812 }
813 }
814 }
815 }
816 return result;
817 }
818
819
820
821
822
823
824
825
826
827
828
829
830 @Override
831 public String toString()
832 {
833 final var builder = new StringBuilder(182);
834 builder.append("Address[country=").append(this.country.stringValue());
835 if (this.postalCode != null)
836 {
837 builder.append(", postalCode=").append(this.postalCode.stringValue());
838 }
839 if (this.city != null)
840 {
841 builder.append(", city=").append(this.city.stringValue());
842 }
843 if (this.province != null)
844 {
845 builder.append(", province=").append(this.province.stringValue());
846 }
847 if (this.district != null)
848 {
849 builder.append(", district=").append(this.district.stringValue());
850 }
851 if (this.street != null)
852 {
853 builder.append(", street=").append(this.street.stringValue());
854 }
855 if (this.buildingNr != null)
856 {
857 builder.append(", buildingNr=").append(this.buildingNr.stringValue());
858 }
859 if (this.buildingName != null)
860 {
861 builder.append(", buildingName=").append(this.buildingName.stringValue());
862 }
863 if (this.subBuilding != null)
864 {
865 builder.append(", subBuilding=").append(this.subBuilding.stringValue());
866 }
867 if (this.poBoxNumber != null)
868 {
869 builder.append(", poBoxNumber=").append(this.poBoxNumber.longValue());
870 }
871 if (this.department != null)
872 {
873 builder.append(", department=").append(this.department.stringValue());
874 }
875 if (this.neighbourhood != null)
876 {
877 builder.append(", neighbourhood=").append(this.neighbourhood.stringValue());
878 }
879 if (this.block != null)
880 {
881 builder.append(", block=").append(this.block.stringValue());
882 }
883 if (this.bFPONumber != null)
884 {
885 builder.append(", bFPONumber=").append(this.bFPONumber.intValue());
886 }
887 if (this.lines != null)
888 {
889 builder.append(", lines=").append(this.lines.stringValue());
890 }
891 builder.append(']');
892 return builder.toString();
893 }
894
895
896
897
898
899
900
901
902
903
904 private static <T extends Comparable<T>> int compareField(final T obj1, final T obj2)
905 {
906 return (obj1 == null) ? ((obj2 == null) ? 0 : -1) : ((obj2 == null) ? 1 : obj1.compareTo(obj2));
907 }
908
909
910
911
912
913
914
915
916
917 @Override
918 public int compareTo(final Address obj)
919 {
920 Objects.requireNonNull(obj, "obj");
921 int result = this.country.compareTo(obj.country);
922 if (result == 0)
923 {
924 result = compareField(this.postalCode, obj.postalCode);
925 if (result == 0)
926 {
927 result = compareField(this.city, obj.city);
928 if (result == 0)
929 {
930 result = compareField(this.province, obj.province);
931 if (result == 0)
932 {
933 result = compareField(this.district, obj.district);
934 if (result == 0)
935 {
936 result = compareField(this.street, obj.street);
937 if (result == 0)
938 {
939 result = compareField(this.buildingNr, obj.buildingNr);
940 if (result == 0)
941 {
942 result = compareField(this.buildingName, obj.buildingName);
943 if (result == 0)
944 {
945 result = compareField(this.subBuilding, obj.subBuilding);
946 if (result == 0)
947 {
948 result = compareField(this.poBoxNumber, obj.poBoxNumber);
949 if (result == 0)
950 {
951 result = compareField(this.department, obj.department);
952 if (result == 0)
953 {
954 result = compareField(this.neighbourhood, obj.neighbourhood);
955 if (result == 0)
956 {
957 result = compareField(this.block, obj.block);
958 if (result == 0)
959 {
960 result = compareField(this.bFPONumber, obj.bFPONumber);
961 if (result == 0)
962 {
963 result = compareField(this.lines, obj.lines);
964 }
965 }
966 }
967 }
968 }
969 }
970 }
971 }
972 }
973 }
974 }
975 }
976 }
977 }
978 return result;
979 }
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
1001
1002
1003
1004
1005 private String processBlocks(final String formatStr, final String... vars)
1006 {
1007
1008
1009 String format = formatStr;
1010 int pos = 0;
1011 while (pos < format.length())
1012 {
1013 final int posStartBlock = format.indexOf('[', pos);
1014 if (posStartBlock == -1)
1015 {
1016 pos = format.length();
1017 }
1018 else
1019 {
1020 final int posEndBlock = format.indexOf(']', posStartBlock + 1);
1021 if (posEndBlock == -1)
1022 {
1023 throw new IllegalArgumentException("Block without end found in: " + this.country.stringValue());
1024 }
1025 pos = posEndBlock + 1;
1026 final var blk = format.substring(posStartBlock + 1, posEndBlock);
1027 boolean removedBlock = false;
1028 int fieldPos = 0;
1029 while (fieldPos < blk.length())
1030 {
1031 final int posFieldStart = blk.indexOf('%', fieldPos);
1032 if (posFieldStart == -1)
1033 {
1034 fieldPos = blk.length();
1035 }
1036 else if (blk.charAt(posFieldStart + 1) == 'n')
1037 {
1038 fieldPos = posFieldStart + 2;
1039 }
1040 else
1041 {
1042 final int posFieldEnd = blk.indexOf('$', posFieldStart);
1043 if (posFieldEnd == -1)
1044 {
1045 throw new IllegalArgumentException("Unsupported field format code found in: " + this.country.stringValue());
1046 }
1047 final int fieldNr = Integer.parseInt(blk.substring(posFieldStart + 1, posFieldEnd));
1048 fieldPos = posFieldEnd + 1;
1049 if ((fieldNr < 1) || (fieldNr > 16))
1050 {
1051 throw new IllegalArgumentException("Illegal field number (1-16): " + fieldNr);
1052 }
1053 if ((vars[fieldNr - 1] == null) || vars[fieldNr - 1].isBlank())
1054 {
1055 final String newFormat = format.substring(0, posStartBlock) + (((posEndBlock + 1) > format.length()) ? "" : format.substring(posEndBlock + 1));
1056 format = newFormat;
1057 removedBlock = true;
1058 pos = posStartBlock;
1059 fieldPos = blk.length();
1060 }
1061 }
1062 }
1063 if (!removedBlock)
1064 {
1065 final String newFormat = format.substring(0, posStartBlock) + blk + (((posEndBlock + 1) > format.length()) ? "" : format.substring(posEndBlock + 1));
1066 format = newFormat;
1067 pos -= 2;
1068 }
1069 }
1070 }
1071 return format;
1072 }
1073
1074
1075
1076
1077
1078
1079
1080
1081
1082
1083
1084
1085
1086
1087
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097 private String getAddressFormat(final String... vars)
1098 {
1099
1100 final String format = Address.ADDRESS_FORMATS.get(this.country.stringValue());
1101 return processBlocks(format, vars);
1102 }
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112 public String getFormattedAddress(final String recipientName)
1113 {
1114 Objects.requireNonNull(recipientName, "recipientName");
1115 final var builder = new StringBuilder();
1116 try (var formatter = new Formatter(builder, Locale.getDefault()))
1117 {
1118 final String tmpPostalCode = this.postalCode == null ? null : this.postalCode.stringValue();
1119 final String tmpCity = this.city == null ? null : this.city.stringValue();
1120 final String tmpProvince = this.province == null ? null : this.province.stringValue();
1121 final String tmpDistrict = this.district == null ? null : this.district.stringValue();
1122 final String tmpStreet = this.street == null ? null : this.street.stringValue();
1123 final String tmpBuildingNr = this.buildingNr == null ? null : this.buildingNr.stringValue();
1124 final String tmpBuildingName = this.buildingName == null ? null : this.buildingName.stringValue();
1125 final String tmpSubBuilding = this.subBuilding == null ? null : this.subBuilding.stringValue();
1126 final String tmpPoBoxNumber = this.poBoxNumber == null ? null : this.poBoxNumber.stringValue();
1127 final String tmpDepartment = this.department == null ? null : this.department.stringValue();
1128 final String tmpNeighbourhood = this.neighbourhood == null ? null : this.neighbourhood.stringValue();
1129 final String tmpBlock = this.block == null ? null : this.block.stringValue();
1130 final String tmpBFPONumber = this.bFPONumber == null ? null : this.bFPONumber.stringValue();
1131 final String tmpLines = this.lines == null ? null : this.lines.stringValue();
1132 final String format = getAddressFormat(this.country.getEnglishCountryName(), recipientName, tmpPostalCode, tmpCity, tmpProvince, tmpDistrict, tmpStreet, tmpBuildingNr, tmpBuildingName, tmpSubBuilding, tmpPoBoxNumber, tmpDepartment, tmpNeighbourhood, tmpBlock, tmpBFPONumber, tmpLines);
1133 formatter.format(format, this.country.getEnglishCountryName(), recipientName, tmpPostalCode, tmpCity, tmpProvince, tmpDistrict, tmpStreet, tmpBuildingNr, tmpBuildingName, tmpSubBuilding, tmpPoBoxNumber, tmpDepartment, tmpNeighbourhood, tmpBlock, tmpBFPONumber, tmpLines);
1134 }
1135 return builder.toString();
1136 }
1137
1138
1139
1140
1141
1142
1143
1144 public Country getCountry()
1145 {
1146 return this.country;
1147 }
1148
1149
1150
1151
1152
1153
1154
1155 public PostalCode getPostalCode()
1156 {
1157 return this.postalCode;
1158 }
1159
1160
1161
1162
1163
1164
1165
1166 public City getCity()
1167 {
1168 return this.city;
1169 }
1170
1171
1172
1173
1174
1175
1176
1177 public Province getProvince()
1178 {
1179 return this.province;
1180 }
1181
1182
1183
1184
1185
1186
1187
1188 public District getDistrict()
1189 {
1190 return this.district;
1191 }
1192
1193
1194
1195
1196
1197
1198
1199 public Street getStreet()
1200 {
1201 return this.street;
1202 }
1203
1204
1205
1206
1207
1208
1209
1210 public BuildingNr getBuildingNr()
1211 {
1212 return this.buildingNr;
1213 }
1214
1215
1216
1217
1218
1219
1220
1221 public BuildingName getBuildingName()
1222 {
1223 return this.buildingName;
1224 }
1225
1226
1227
1228
1229
1230
1231
1232 public SubBuilding getSubBuilding()
1233 {
1234 return this.subBuilding;
1235 }
1236
1237
1238
1239
1240
1241
1242
1243 public PoBoxNumber getPoBoxNumber()
1244 {
1245 return this.poBoxNumber;
1246 }
1247
1248
1249
1250
1251
1252
1253
1254 public Department getDepartment()
1255 {
1256 return this.department;
1257 }
1258
1259
1260
1261
1262
1263
1264
1265 public Neighbourhood getNeighbourhood()
1266 {
1267 return this.neighbourhood;
1268 }
1269
1270
1271
1272
1273
1274
1275
1276 public Block getBlock()
1277 {
1278 return this.block;
1279 }
1280
1281
1282
1283
1284
1285
1286
1287 public BFPONumber getBFPONumber()
1288 {
1289 return this.bFPONumber;
1290 }
1291
1292
1293
1294
1295
1296
1297
1298 public Lines getLines()
1299 {
1300 return this.lines;
1301 }
1302
1303 }