如何通过添加附加参数实现具有 spring 安全性的 OAuth2.0
How to implement OAuth2.0 with spring security by adding additional parameter
我正在基于以下 link.
使用 springboot2 实现具有 spring-安全性的 oauth2
https://www.devglan.com/spring-security/spring-boot-oauth2-jwt-example
而且我成功地实施了它。
这里我对上述代码在验证用户时有不同的用例。
我需要在 postman 的 "x-www-form-urlencoded" 选项卡中传递 companyid 以及用户名和密码以及 grant_type(密码)。
而且我必须根据用户名和 companyId 获取用户。
所以请帮我看看我需要对上面的 link 代码做哪些更改才能实现我的要求。
这里我只收到电子邮件。我需要电子邮件和 companyId。
@Override
@Transactional
public UserDetails loadUserByUsername(String email) throws UsernameNotFoundException {
User user = userRepository.findByEmail(email).orElseThrow(
() -> new UsernameNotFoundException("User Not Found with -> username or email : " + email));
return UserPrinciple.build(user);
}
Expected:
@Override
@Transactional
public UserDetails loadUserByUsername(String email) throws UsernameNotFoundException {
User user = userRepository.findByEmailAndCompanyId(email,companyId).orElseThrow(
() -> new UsernameNotFoundException("User Not Found with -> username or email : " + email));
return UserPrinciple.build(user);
}
目前使用用户名和密码可以正常工作。
但是在我的系统中,我将同一个用户映射到不同的 companies.if 将同一个用户映射到多个公司,我发现我遇到如下错误。
{
"error": "unauthorized",
"error_description": "query did not return a unique result: 2; nested exception is javax.persistence.NonUniqueResultException: query did not return a unique result: 2"
}
我需要根据用户名和密码以及 companyId 获取用户,这会导致单个用户。
如果您想要更多关于访问令牌的信息,您可以使用 TokenEnhancer class 来做到这一点。
CustomTokenEnhancer.java
public class CustomTokenEnhancer implements TokenEnhancer {
@Override
public OAuth2AccessToken enhance(OAuth2AccessToken accessToken, OAuth2Authentication authentication) {
User user = (User) authentication.getPrincipal();
final Map<String, Object> additionalInfo = new HashMap<>();
additionalInfo.put("id", user.getCompanyId());
additionalInfo.put("authorities", user.getAuthorities());
((DefaultOAuth2AccessToken) accessToken).setAdditionalInformation(additionalInfo);
return accessToken;
}
}
然后使用此 class 的实例来取消配置(AuthorizationServerEndpointsConfigurer endpoints)方法,如下所示
AuthorizationServerConfig.java
@Override
public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
endpoints.authenticationManager(authenticationManager)
.allowedTokenEndpointRequestMethods(HttpMethod.GET, HttpMethod.POST)
.tokenEnhancer(new CustomTokenEnhancer());
}
我正在基于以下 link.
使用 springboot2 实现具有 spring-安全性的 oauth2https://www.devglan.com/spring-security/spring-boot-oauth2-jwt-example
而且我成功地实施了它。
这里我对上述代码在验证用户时有不同的用例。
我需要在 postman 的 "x-www-form-urlencoded" 选项卡中传递 companyid 以及用户名和密码以及 grant_type(密码)。 而且我必须根据用户名和 companyId 获取用户。
所以请帮我看看我需要对上面的 link 代码做哪些更改才能实现我的要求。
这里我只收到电子邮件。我需要电子邮件和 companyId。
@Override
@Transactional
public UserDetails loadUserByUsername(String email) throws UsernameNotFoundException {
User user = userRepository.findByEmail(email).orElseThrow(
() -> new UsernameNotFoundException("User Not Found with -> username or email : " + email));
return UserPrinciple.build(user);
}
Expected:
@Override
@Transactional
public UserDetails loadUserByUsername(String email) throws UsernameNotFoundException {
User user = userRepository.findByEmailAndCompanyId(email,companyId).orElseThrow(
() -> new UsernameNotFoundException("User Not Found with -> username or email : " + email));
return UserPrinciple.build(user);
}
目前使用用户名和密码可以正常工作。
但是在我的系统中,我将同一个用户映射到不同的 companies.if 将同一个用户映射到多个公司,我发现我遇到如下错误。
{ "error": "unauthorized", "error_description": "query did not return a unique result: 2; nested exception is javax.persistence.NonUniqueResultException: query did not return a unique result: 2" }
我需要根据用户名和密码以及 companyId 获取用户,这会导致单个用户。
如果您想要更多关于访问令牌的信息,您可以使用 TokenEnhancer class 来做到这一点。
CustomTokenEnhancer.java
public class CustomTokenEnhancer implements TokenEnhancer {
@Override
public OAuth2AccessToken enhance(OAuth2AccessToken accessToken, OAuth2Authentication authentication) {
User user = (User) authentication.getPrincipal();
final Map<String, Object> additionalInfo = new HashMap<>();
additionalInfo.put("id", user.getCompanyId());
additionalInfo.put("authorities", user.getAuthorities());
((DefaultOAuth2AccessToken) accessToken).setAdditionalInformation(additionalInfo);
return accessToken;
}
}
然后使用此 class 的实例来取消配置(AuthorizationServerEndpointsConfigurer endpoints)方法,如下所示
AuthorizationServerConfig.java
@Override
public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
endpoints.authenticationManager(authenticationManager)
.allowedTokenEndpointRequestMethods(HttpMethod.GET, HttpMethod.POST)
.tokenEnhancer(new CustomTokenEnhancer());
}