我想将基于角色的身份验证添加到我的get user API中,但我的实现是-SecurityConfigs.java
public class SecurityConfig {
private final JwtAuthConverter jwtAuthConverter;
@Bean
public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
http
.csrf()
.disable()
.authorizeHttpRequests()
.anyRequest().permitAll();
http
.oauth2ResourceServer()
.jwt()
.jwtAuthenticationConverter(jwtAuthConverter);
http
.sessionManagement()
.sessionCreationPolicy(STATELESS);
return http.build();
}
和JwtAuthConvert类:
private final JwtGrantedAuthoritiesConverter jwtGrantedAuthoritiesConverter =
new JwtGrantedAuthoritiesConverter();
@Value("${jwt.auth.converter.principle-attribute}")
private String principleAttribute;
@Value("${jwt.auth.converter.resource-id}")
private String resourceId;
@Override
public AbstractAuthenticationToken convert(@NonNull Jwt jwt) {
Collection<GrantedAuthority> authorities = Stream.concat(
jwtGrantedAuthoritiesConverter.convert(jwt).stream(),
extractResourceRoles(jwt).stream()
).collect(Collectors.toSet());
return new JwtAuthenticationToken(
jwt,
authorities,
getPrincipleClaimName(jwt)
);
}
private String getPrincipleClaimName(Jwt jwt) {
String claimName = JwtClaimNames.SUB;
if (principleAttribute != null) {
claimName = principleAttribute;
}
return jwt.getClaim(claimName);
}
private Collection<? extends GrantedAuthority> extractResourceRoles(Jwt jwt) {
Map<String, Object> resourceAccess;
Map<String, Object> resource;
Collection<String> resourceRoles;
if (jwt.getClaim("resource_access") == null) {
return Set.of();
}
resourceAccess = jwt.getClaim("resource_access");
if (resourceAccess.get(resourceId) == null) {
return Set.of();
}
resource = (Map<String, Object>) resourceAccess.get(resourceId);
resourceRoles = (Collection<String>) resource.get("roles");
return resourceRoles
.stream()
.map(role -> new SimpleGrantedAuthority("ROLE_" + role))
.collect(Collectors.toSet());
}
获取用户API
@GetMapping(path = "/{userName}")
@PreAuthorize("hasRole('PROF')")
public List<UserRepresentation> getUser(@PathVariable("userName") String userName){
List<UserRepresentation> user = userservice.getUser(userName);
return user;
}
问题:当我尝试使用PROF角色使用Get API时,我得到Status Code 403 Forbidden错误,尽管我允许PROF角色执行此操作。我得到以下日志
2023-06-23T11:26:54.564+01:00 DEBUG 7428 --- [nio-8090-exec-3] .s.r.w.a.BearerTokenAuthenticationFilter : Set SecurityContextHolder to JwtAuthenticationToken [Principal=org.springframework.security.oauth2.jwt.Jwt@b3eb5836, Credentials=[PROTECTED], Authenticated=true, Details=WebAuthenticationDetails [RemoteIpAddress=0:0:0:0:0:0:0:1, SessionId=null], Granted Authorities=[SCOPE_email, SCOPE_profile]]
2023-06-23T11:26:54.565+01:00 DEBUG 7428 --- [nio-8090-exec-3] o.s.security.web.FilterChainProxy : Secured GET /user/nouhaila
2023-06-23T11:26:54.571+01:00 DEBUG 7428 --- [nio-8090-exec-3] horizationManagerBeforeMethodInterceptor : Authorizing method invocation ReflectiveMethodInvocation: public java.util.List com.codetech.authserver.controller.UserController.getUser(java.lang.String); target is of class [com.codetech.authserver.controller.UserController]
2023-06-23T11:26:54.609+01:00 DEBUG 7428 --- [nio-8090-exec-3] horizationManagerBeforeMethodInterceptor : Failed to authorize ReflectiveMethodInvocation: public java.util.List com.codetech.authserver.controller.UserController.getUser(java.lang.String); target is of class [com.codetech.authserver.controller.UserController] with authorization manager org.springframework.security.config.annotation.method.configuration.DeferringObservationAuthorizationManager@7fdea099 and decision ExpressionAuthorizationDecision [granted=false, expressionAttribute=hasAuthority('ROLE_PROF')]
1条答案
按热度按时间bttbmeg01#
您的
SecurityConfig
可能没有示例化(缺少@Configuration
装饰器?)。在securityFilterChain
@Bean
定义中设置一个断点,以检查您的自定义SecurityFilterChain
bean是否已示例化。除此之外,使用以下代码可能会更简单/更安全
...
或者使用"my" starters,它已经完成了这种检查,并且支持从多个声明中检索角色(
realm_access.roles
和一个或多个resource_access.{clientId}.roles
)