-
Notifications
You must be signed in to change notification settings - Fork 138
/
GlassFishPrincipalMapper.java
97 lines (77 loc) · 3.31 KB
/
GlassFishPrincipalMapper.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
package com.sun.enterprise.security.ee.authorize;
import jakarta.security.jacc.PrincipalMapper;
import java.security.Principal;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import javax.security.auth.Subject;
import org.glassfish.deployment.common.SecurityRoleMapper;
import org.glassfish.deployment.common.SecurityRoleMapperFactory;
import org.glassfish.internal.api.Globals;
public class GlassFishPrincipalMapper implements PrincipalMapper {
private final SecurityRoleMapper roleMapper;
private final Map<String, Set<String>> groupToRoles;
private final Map<String, Set<String>> callerToRoles;
private final boolean oneToOneMapping;
private final boolean anyAuthenticatedUserRoleMapped;
public GlassFishPrincipalMapper(String contextId) {
roleMapper =
Globals.get(SecurityRoleMapperFactory.class)
.getRoleMapper(contextId);
groupToRoles = roleMapper.getGroupToRolesMapping();
callerToRoles = roleMapper.getCallerToRolesMapping();
oneToOneMapping =
groupToRoles.isEmpty() &&
callerToRoles.isEmpty() &&
roleMapper.isDefaultPrincipalToRoleMapping();
// Jakarta Authorization spec 3.2 states:
//
// "For the any "authenticated user role", "**", and unless an application specific mapping has
// been established for this role,
// the provider must ensure that all permissions added to the role are granted to any
// authenticated user."
//
// Here we check for the "unless" part mentioned above. If we're dealing with the "**" role here
// and groups is not
// empty, then there's an application specific mapping and "**" maps only to those groups, not
// to any authenticated user.
anyAuthenticatedUserRoleMapped =
groupToRoles.values()
.stream()
.flatMap(roles -> roles.stream())
.anyMatch(role -> role.equals("**"));
}
@Override
public Principal getCallerPrincipal(Subject subject) {
return roleMapper.getCallerPrincipal(subject);
}
@Override
public Set<String> getMappedRoles(Subject subject) {
// Check for groups that have been mapped to roles
Set<String> mappedRoles = mapGroupsToRoles(roleMapper.getGroups(subject));
Principal callerPrincipal = getCallerPrincipal(subject);
// Check if the caller principal has been mapped to roles
if (callerPrincipal != null && callerToRoles.containsKey(callerPrincipal.getName())) {
mappedRoles = new HashSet<>(mappedRoles);
mappedRoles.addAll(callerToRoles.get(callerPrincipal.getName()));
}
return mappedRoles;
}
@Override
public boolean isAnyAuthenticatedUserRoleMapped() {
return anyAuthenticatedUserRoleMapped;
}
private Set<String> mapGroupsToRoles(Set<String> groups) {
if (oneToOneMapping) {
// There is no mapping used, groups directly represent roles.
return groups;
}
Set<String> roles = new HashSet<>();
for (String group : groups) {
if (groupToRoles.containsKey(group)) {
roles.addAll(groupToRoles.get(group));
}
}
return roles;
}
}