我正在使用InMemoryTokenStore,当用户注销时,我会将access_token发送到我的rest api,以从tokenStore中“删除”它。 第一次,它可以工作并返回200。 当我尝试使用相同的access_token访问该端点时,它写的AccessToken为null,太好了……但是我可以自由地将该令牌用于所有其他端点,因此它并没有被真正删除……尽管它写了,但它并不是在tokenStore中,但是我可以用它来访问端点...
@Autowired
private TokenStore tokenStore;
@RequestMapping(value = "/oauth/revoke-token", method = RequestMethod.POST)
@ResponseStatus(HttpStatus.OK)
public void logout(HttpServletRequest request) {
String authHeader = request.getHeader("Authorization");
System.out.println("HEJOHEJO");
if (authHeader != null) {
String tokenValue = authHeader.replace("Bearer", "").trim();
OAuth2AccessToken accessToken = tokenStore.readAccessToken(tokenValue);
tokenStore.removeAccessToken(accessToken);
}
}
Configuration
@EnableAuthorizationServer
public class AuthorizationServerConfig extends AuthorizationServerConfigurerAdapter {
private static final String GRANT_TYPE_PASSWORD = "password";
private static final String AUTHORIZATION_CODE = "authorization_code";// "implicit"; "authorization_code";
private static final String REFRESH_TOKEN = "refresh_token";
private static final String SCOPE_READ = "read";
private static final String SCOPE_WRITE = "write";
private static final String TRUST = "trust";
private static final int VALID_FOREVER = -1;
@Autowired
private AuthenticationManager authenticationManager;
@Value("${jwt.privateKey}")
private String privateKey;
@Value("${jwt.publicKey}")
private String publicKey;
@Override
public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
clients
.inMemory()
.withClient(Const.CLIENT_ID)
.secret(Const.CLIENT_SECRET)
.authorizedGrantTypes(GRANT_TYPE_PASSWORD, AUTHORIZATION_CODE, REFRESH_TOKEN)
.scopes(SCOPE_READ, SCOPE_WRITE, TRUST)
.accessTokenValiditySeconds(300)
.refreshTokenValiditySeconds(VALID_FOREVER);
}
@Bean
protected InMemoryTokenStore tokenStore() {
return new InMemoryTokenStore();
}
@Bean
protected JwtAccessTokenConverter jwtTokenEnhancer() {
JwtAccessTokenConverter converter = new JwtAccessTokenConverter();
KeyStoreKeyFactory keyStoreKeyFactory =
new KeyStoreKeyFactory(new ClassPathResource("test.jks"), "password".toCharArray());
converter.setKeyPair(keyStoreKeyFactory.getKeyPair("test"));
return converter;
}
@Override
public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
endpoints
.tokenStore(tokenStore()).reuseRefreshTokens(false)
.tokenEnhancer(jwtTokenEnhancer())
.authenticationManager(authenticationManager);
}
}
@Configuration
@EnableResourceServer
public class ResourceServerConfig extends ResourceServerConfigurerAdapter {
@Value("${jwt.publicKey}")
private String publicKey;
@Override
public void configure(ResourceServerSecurityConfigurer config) {
config.tokenStore(tokenStoree());
}
@Bean
public TokenStore tokenStoree() {
return new JwtTokenStore(jwtTokenEnhancerr());
}
@Bean
protected JwtAccessTokenConverter jwtTokenEnhancerr() {
JwtAccessTokenConverter converter = new JwtAccessTokenConverter();
Resource resource = new ClassPathResource("public.txt");
String publicKey = null;
try {
publicKey = IOUtils.toString(resource.getInputStream());
} catch (final IOException e) {
throw new RuntimeException(e);
}
converter.setVerifierKey(publicKey);
return converter;
}
@Override
public void configure(HttpSecurity http) throws Exception {
http.
anonymous().disable()
.authorizeRequests()
.antMatchers("/documents/**").authenticated()
.antMatchers("/users/**").authenticated()
.and().exceptionHandling().accessDeniedHandler(new OAuth2AccessDeniedHandler())
.and()
.sessionManagement()
.sessionCreationPolicy(SessionCreationPolicy.STATELESS)
.and()
.csrf().disable();
}
}
@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true, securedEnabled = true)
public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
private UserService userService;
@Autowired
private UserDetailsService userDetailsService;
private PasswordEncoder passwordEncoder = new BCryptPasswordEncoder();
@Override
@Bean
public AuthenticationManager authenticationManagerBean() throws Exception {
return super.authenticationManagerBean();
}
@Autowired
public void globalUserDetails(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(userDetailsService).passwordEncoder(passwordEncoder);
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http.requiresChannel().anyRequest().requiresSecure();
}
@Bean
public RequestContextListener requestContextListener(){
return new RequestContextListener();
}