OAuth2Client每次都返回相同的令牌

时间:2018-06-22 06:48:06

标签: java spring oauth-2.0 token spring-security-oauth2

我有AuthorizationServer。除标准功能外,我还有允许创建用户的控制器。用户成功创建后,该方法必须为该用户返回令牌。问题在于该方法仅在第一次调用时才返回有效令牌。在下次通话时-后续用户将获得第一个用户的令牌。我尝试为restTemplate设置scope(request)-但获得了错误:“范围'request'对于当前线程无效”

@Configuration
@EnableAuthorizationServer
public class AuthorizationServerConfig extends AuthorizationServerConfigurerAdapter {  

    @Override
    public void configure(ClientDetailsServiceConfigurer configurer) throws Exception {
      ...
    }
    @Override
    public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
     ...
    }

    protected ResourceOwnerPasswordResourceDetails getOwnerPasswordResource(){
        ResourceOwnerPasswordResourceDetails resource = new ResourceOwnerPasswordResourceDetails();
        List scopes = new ArrayList<String>(3);
        scopes.add(SCOPE_READ);
        scopes.add(SCOPE_WRITE);
        scopes.add(SCOPE_TRUST);
        resource.setAccessTokenUri(tokenUrl);
        resource.setClientId(CLIENT_ID);
        resource.setClientSecret(CLIENT_SECRET_UNCODED);
        resource.setGrantType(GRANT_TYPE_PASSWORD);
        resource.setScope(scopes);
        return resource;
    }
}

这里是OAuth2Client:

@EnableOAuth2Client
@Configuration
public class ClientConfig {
    @Autowired
    AuthorizationServerConfig authorizationServerConfig;

    @Bean
    //@Scope("request")
    public OAuth2RestOperations restTemplate() {
        AccessTokenRequest atr = new DefaultAccessTokenRequest();

        return new OAuth2RestTemplate(authorizationServerConfig.getOwnerPasswordResource(), new DefaultOAuth2ClientContext(atr));
    }

}

还有我的控制器:

@RestController
public class UserRestController {
    @Autowired
    private OAuth2RestOperations restTemplate;

    @PostMapping("/user")
    public OAuth2AccessToken createUserCredential(@RequestBody UserCredential user) {
        user.validate();
        userCredentialService.checkAndSaveUser(user, getClientIp(request));

        restTemplate.getOAuth2ClientContext().getAccessTokenRequest().set("username", user.getLogin());
        restTemplate.getOAuth2ClientContext().getAccessTokenRequest().set("password", user.getPassword);
        return restTemplate.getAccessToken();
    }
}

可能是在AuthorizationServer内部获取令牌的更正确方法吗?

2 个答案:

答案 0 :(得分:0)

我认为有一些特殊的方法..但是没有找到。并按照以下方式解决了问题

 @EnableOAuth2Client
@Configuration
public class OAuthClientConfig {

    @Autowired
    AuthorizationServerConfig authorizationServerConfig;

    public OAuth2RestOperations restTemplate() {
        AccessTokenRequest atr = new DefaultAccessTokenRequest();

        return new OAuth2RestTemplate(authorizationServerConfig.getOwnerPasswordResource(), new DefaultOAuth2ClientContext(atr));
    }
}

还有我的控制器:

@RestController
public class UserRestController {

    @Autowired
    private OAuthClientConfig oAuthClientConfig;

    @PostMapping("/user")
    public OAuth2AccessToken createUserCredential(@RequestBody UserCredential user) {
        user.validate();
        userCredentialService.checkAndSaveUser(user, getClientIp(request));

        OAuth2RestOperations restTemplate = oAuthClientConfig.restTemplate();
        restTemplate.getOAuth2ClientContext().getAccessTokenRequest().set("username", user.getLogin());
        restTemplate.getOAuth2ClientContext().getAccessTokenRequest().set("password", user.getPassword);
        return restTemplate.getAccessToken();
    }
}

也许会对某人有帮助

答案 1 :(得分:0)

我面临着同样的问题,我发现用其他方法可以使它起作用

@Bean
@Primary
@Scope(value = WebApplicationContext.SCOPE_REQUEST, proxyMode = ScopedProxyMode.TARGET_CLASS)
public OAuth2RestTemplate oauth2RestTemplate(OAuth2ClientContext context,
            OAuth2ProtectedResourceDetails details) {

        AccessTokenRequest atr = new DefaultAccessTokenRequest();
        OAuth2RestTemplate template = new OAuth2RestTemplate(resource(), new DefaultOAuth2ClientContext(atr));
        AccessTokenProvider accessTokenProvider = new AccessTokenProviderChain(Arrays.<AccessTokenProvider>asList(
                new AuthorizationCodeAccessTokenProvider(), new ImplicitAccessTokenProvider(),
                new ResourceOwnerPasswordAccessTokenProvider(), new ClientCredentialsAccessTokenProvider()));
        template.setAccessTokenProvider(accessTokenProvider);
        return template;

    }

然后我刚进行注射

private final OAuth2RestTemplate oauth2RestTemplate;
    @GetMapping(path = "/token")
    public String token(Credentials  credentials) {
    oauth2RestTemplate.getOAuth2ClientContext()
             .getAccessTokenRequest().add("username", credentials.getEmail());
    oauth2RestTemplate.getOAuth2ClientContext()
             .getAccessTokenRequest().add("password", credentials.getPass());
    final OAuth2AccessToken accessToken = oauth2RestTemplate.getAccessToken();
    final String accessTokenAsString = accessToken.getValue();
    return accessTokenAsString ;
    }