本文就來說一講spring security oauth2的refresh token方式html
oauth2官方只有4種受權方式,不過spring security oauth2把refresh token也歸爲authorizedGrantTypes的一種,所以配置的時候只須要這樣就把全部方式都支持了spring
@Configuration @EnableAuthorizationServer //提供/oauth/authorize,/oauth/token,/oauth/check_token,/oauth/confirm_access,/oauth/error public class OAuth2ServerConfig extends AuthorizationServerConfigurerAdapter { @Override public void configure(ClientDetailsServiceConfigurer clients) throws Exception { clients.inMemory() .withClient("demoApp") .secret("demoAppSecret") .redirectUris("http://localhost:8081/callback") //新增redirect_uri .authorizedGrantTypes("authorization_code", "client_credentials", "refresh_token", "password", "implicit") .scopes("all") .resourceIds("oauth2-resource") .accessTokenValiditySeconds(120) .refreshTokenValiditySeconds(60); } }
要使用refresh_token的話,須要額外配置userDetailsServicejson
@Autowired private UserDetailsService userDetailsService; @Override public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception { endpoints.authenticationManager(authenticationManager); endpoints.userDetailsService(userDetailsService); }
不然報錯以下app
HTTP/1.1 500 X-Content-Type-Options: nosniff X-XSS-Protection: 1; mode=block Cache-Control: no-cache, no-store, max-age=0, must-revalidate Pragma: no-cache Expires: 0 X-Frame-Options: DENY X-Application-Context: application Cache-Control: no-store Pragma: no-cache Content-Type: application/json;charset=UTF-8 Transfer-Encoding: chunked Date: Wed, 06 Dec 2017 13:35:33 GMT Connection: close {"error":"server_error","error_description":"UserDetailsService is required."}
curl -i -d "grant_type=authorization_code&code=uKGjVz&client_id=demoApp&client_secret=demoAppSecret&redirect_uri=http://localhost:8081/callback" -X POST http://localhost:8080/oauth/token
curl -i -X POST -u 'demoApp:demoAppSecret' -d 'grant_type=refresh_token&refresh_token=95844d87-f06e-4a4e-b76c-f16c5329e287' http://localhost:8080/oauth/token
HTTP/1.1 200 X-Content-Type-Options: nosniff X-XSS-Protection: 1; mode=block Cache-Control: no-cache, no-store, max-age=0, must-revalidate Pragma: no-cache Expires: 0 X-Frame-Options: DENY X-Application-Context: application Cache-Control: no-store Pragma: no-cache Content-Type: application/json;charset=UTF-8 Transfer-Encoding: chunked Date: Wed, 06 Dec 2017 13:51:47 GMT {"access_token":"eb45f1d4-54a5-4e23-bf12-31d8d91a902f","token_type":"bearer","refresh_token":"efa96270-18a1-432c-b9e6-77725c0dabea","expires_in":1199,"scope":"all"}
access_token會變,並且expires延長,refresh_token根據設定的過時時間,沒有失效則不變curl
HTTP/1.1 200 X-Content-Type-Options: nosniff X-XSS-Protection: 1; mode=block Cache-Control: no-cache, no-store, max-age=0, must-revalidate Pragma: no-cache Expires: 0 X-Frame-Options: DENY X-Application-Context: application Cache-Control: no-store Pragma: no-cache Content-Type: application/json;charset=UTF-8 Transfer-Encoding: chunked Date: Wed, 06 Dec 2017 14:03:50 GMT {"access_token":"a78999d6-614a-45fe-be58-d5e0b6451bdb","token_type":"bearer","refresh_token":"bb2a0165-769d-43b0-a9a5-1331012ede1f","expires_in":119,"scope":"all"}
access_token會變,並且expires延長,refresh_token根據設定的過時時間,沒有失效則不變ide
HTTP/1.1 401 X-Content-Type-Options: nosniff X-XSS-Protection: 1; mode=block Cache-Control: no-cache, no-store, max-age=0, must-revalidate Pragma: no-cache Expires: 0 X-Frame-Options: DENY X-Application-Context: application Cache-Control: no-store Pragma: no-cache WWW-Authenticate: Bearer error="invalid_token", error_description="Invalid refresh token (expired): 95844d87-f06e-4a4e-b76c-f16c5329e287" Content-Type: application/json;charset=UTF-8 Transfer-Encoding: chunked Date: Wed, 06 Dec 2017 14:09:57 GMT {"error":"invalid_token","error_description":"Invalid refresh token (expired): 95844d87-f06e-4a4e-b76c-f16c5329e287"}
失效時間爲配置文件中指定的值
)