1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.bremersee.spring.boot.autoconfigure.security.authentication;
18
19 import static org.springframework.util.ObjectUtils.isEmpty;
20
21 import java.util.ArrayList;
22 import java.util.Collection;
23 import java.util.LinkedHashMap;
24 import java.util.List;
25 import java.util.Map;
26 import java.util.stream.Collectors;
27 import java.util.stream.Stream;
28 import lombok.Data;
29 import org.springframework.boot.context.properties.ConfigurationProperties;
30
31
32
33
34
35
36 @ConfigurationProperties(prefix = "bremersee.authentication")
37 @Data
38 public class AuthenticationProperties {
39
40
41
42
43 private RememberMeProperties rememberMe = new RememberMeProperties();
44
45
46
47
48 private JwtConverterProperties jwtConverter = new JwtConverterProperties();
49
50
51
52
53 private LdaptiveProperties ldaptive = new LdaptiveProperties();
54
55
56
57
58 private ActuatorProperties actuator = new ActuatorProperties();
59
60
61
62
63 public AuthenticationProperties() {
64 super();
65 }
66
67
68
69
70
71
72 @Data
73 public static class RememberMeProperties {
74
75
76
77
78 private String key;
79
80
81
82
83 private Boolean alwaysRemember;
84
85
86
87
88 private String cookieName;
89
90
91
92
93 private String cookieDomain;
94
95
96
97
98 private Boolean useSecureCookie;
99
100
101
102
103 private String parameterName;
104
105
106
107
108 private Integer tokenValiditySeconds;
109
110
111
112
113 public RememberMeProperties() {
114 super();
115 }
116 }
117
118
119
120
121 @Data
122 public static class JwtConverterProperties {
123
124
125
126
127 private String nameJsonPath = "$.sub";
128
129
130
131
132 private String firstNameJsonPath = "$.given_name";
133
134
135
136
137 private String lastNameJsonPath = "$.family_name";
138
139
140
141
142 private String emailJsonPath = "$.email";
143
144
145
146
147 private String rolesJsonPath = "$.scope";
148
149
150
151
152
153 private boolean rolesValueList = false;
154
155
156
157
158 private String rolesValueSeparator = " ";
159
160
161
162
163 private List<String> defaultRoles = new ArrayList<>();
164
165
166
167
168 private List<SimpleMapping> roleMapping = new ArrayList<>();
169
170
171
172
173 private String rolePrefix = "SCOPE_";
174
175
176
177
178 private CaseTransformation roleCaseTransformation;
179
180
181
182
183 private List<StringReplacement> roleStringReplacements;
184
185
186
187
188 private String groupsJsonPath = "$.groups";
189
190
191
192
193
194 private boolean groupsValueList = false;
195
196
197
198
199 private String groupsValueSeparator = " ";
200
201
202
203
204 private List<String> defaultGroups = new ArrayList<>();
205
206
207
208
209 private List<SimpleMapping> groupMapping = new ArrayList<>();
210
211
212
213
214 private String groupPrefix = "";
215
216
217
218
219 private CaseTransformation groupCaseTransformation;
220
221
222
223
224 private List<StringReplacement> groupStringReplacements;
225
226
227
228
229 public JwtConverterProperties() {
230 super();
231 }
232
233
234
235
236
237
238 public Map<String, String> toRoleMappings() {
239 return Stream.ofNullable(getRoleMapping())
240 .flatMap(Collection::stream)
241 .collect(Collectors.toMap(
242 SimpleMapping::getSource,
243 SimpleMapping::getTarget,
244 (first, second) -> first,
245 LinkedHashMap::new));
246 }
247
248
249
250
251
252
253 public Map<String, String> toGroupMappings() {
254 return Stream.ofNullable(getGroupMapping())
255 .flatMap(Collection::stream)
256 .collect(Collectors.toMap(
257 SimpleMapping::getSource,
258 SimpleMapping::getTarget,
259 (first, second) -> first,
260 LinkedHashMap::new));
261 }
262
263
264
265
266
267
268 public Map<String, String> toRoleStringReplacements() {
269 return Stream.ofNullable(getRoleStringReplacements())
270 .flatMap(Collection::stream)
271 .collect(Collectors.toMap(
272 StringReplacement::getRegex,
273 StringReplacement::getReplacement,
274 (first, second) -> first,
275 LinkedHashMap::new));
276 }
277
278
279
280
281
282
283 public Map<String, String> toGroupStringReplacements() {
284 return Stream.ofNullable(getGroupStringReplacements())
285 .flatMap(Collection::stream)
286 .collect(Collectors.toMap(
287 StringReplacement::getRegex,
288 StringReplacement::getReplacement,
289 (first, second) -> first,
290 LinkedHashMap::new));
291 }
292
293 }
294
295
296
297
298 @Data
299 public static class LdaptiveProperties {
300
301
302
303
304 private Template template = Template.ACTIVE_DIRECTORY;
305
306
307
308
309 private String userBaseDn;
310
311
312
313
314 private List<String> refusedUsernames;
315
316
317
318
319
320 private String userObjectClass;
321
322
323
324
325
326 private String usernameAttribute;
327
328
329
330
331
332
333
334
335 private String passwordAttribute;
336
337
338
339
340
341 private String passwordLastSetAttribute;
342
343
344
345
346
347 private String userFindOneFilter;
348
349
350
351
352 private SearchScope userFindOneSearchScope;
353
354
355
356
357 protected String firstNameAttribute;
358
359
360
361
362 protected String lastNameAttribute;
363
364
365
366
367 private String emailAttribute;
368
369
370
371
372 private AccountControlEvaluatorProperty accountControlEvaluator;
373
374
375
376
377 private GroupFetchStrategy groupFetchStrategy;
378
379
380
381
382 private String memberAttribute;
383
384
385
386
387
388 private String groupBaseDn;
389
390
391
392
393
394 private SearchScope groupSearchScope;
395
396
397
398
399
400 private String groupObjectClass;
401
402
403
404
405
406 private String groupIdAttribute;
407
408
409
410
411
412 private String groupMemberAttribute;
413
414
415
416
417
418 private String groupMemberFormat;
419
420
421
422
423 private List<SimpleMapping> roleMapping;
424
425
426
427
428 private List<String> defaultRoles;
429
430
431
432
433 private String rolePrefix;
434
435
436
437
438 private CaseTransformation roleCaseTransformation;
439
440
441
442
443 private List<StringReplacement> roleStringReplacements;
444
445
446
447
448 public LdaptiveProperties() {
449 super();
450 }
451
452
453
454
455 public enum SearchScope {
456
457
458
459
460 OBJECT,
461
462
463
464
465 ONELEVEL,
466
467
468
469
470 SUBTREE,
471
472
473
474
475 SUBORDINATE
476 }
477
478
479
480
481 public enum AccountControlEvaluatorProperty {
482
483
484
485
486 NONE,
487
488
489
490
491 ACTIVE_DIRECTORY
492 }
493
494
495
496
497 public enum GroupFetchStrategy {
498
499
500
501
502 NONE,
503
504
505
506
507 USER_CONTAINS_GROUPS,
508
509
510
511
512 GROUP_CONTAINS_USERS
513 }
514
515
516
517
518
519
520 public enum Template {
521
522
523
524
525 ACTIVE_DIRECTORY,
526
527
528
529
530 OPEN_LDAP,
531
532
533
534
535 USER_CONTAINS_GROUPS,
536
537
538
539
540 GROUP_CONTAINS_USERS
541 }
542 }
543
544
545
546
547 @Data
548 public static class SimpleMapping {
549
550 private String source;
551
552 private String target;
553
554
555
556
557 public SimpleMapping() {
558 super();
559 }
560 }
561
562
563
564
565 public enum CaseTransformation {
566
567
568
569
570 NONE,
571
572
573
574
575 TO_UPPER_CASE,
576
577
578
579
580 TO_LOWER_CASE
581 }
582
583
584
585
586 @Data
587 public static class StringReplacement {
588
589
590
591
592
593 private String regex;
594
595
596
597
598 private String replacement;
599
600
601
602
603 public StringReplacement() {
604 super();
605 }
606 }
607
608
609
610
611 @Data
612 public static class ActuatorProperties {
613
614 private List<String> readRoles = new ArrayList<>();
615
616 private List<String> writeRoles = new ArrayList<>();
617
618
619
620
621 public ActuatorProperties() {
622 super();
623 }
624
625
626
627
628
629
630 public List<String> getReadRoles() {
631 if (isEmpty(readRoles)) {
632 return List.of("ROLE_ADMIN", "ROLE_ACTUATOR", "ROLE_ACTUATOR_ADMIN");
633 }
634 return readRoles;
635 }
636
637
638
639
640
641
642 public List<String> getWriteRoles() {
643 if (isEmpty(writeRoles)) {
644 return List.of("ROLE_ADMIN", "ROLE_ACTUATOR_ADMIN");
645 }
646 return writeRoles;
647 }
648 }
649
650 }