關於SpringBoot Security oauth2使用Cors問題(登出無效)

前言

以下是登出遇到問題發現http.cors()不好使,創建CorsFilter也不好使。

 : /logout at position 1 of 10 in additional filter chain; firing Filter: 'WebAsyncManagerIntegrationFilter'
 : /logout at position 2 of 10 in additional filter chain; firing Filter: 'SecurityContextPersistenceFilter'
 : /logout at position 3 of 10 in additional filter chain; firing Filter: 'HeaderWriterFilter'
 : /logout at position 4 of 10 in additional filter chain; firing Filter: 'LogoutFilter'

需要加上http.cors()纔會有CorsFilter,並且CorsFilter會在LogoutFilter之前。如果沒有CorsFilter或者CorsFilter不在LogoutFilter之前就會出現報錯。

ResourceServerConfig中加上http.cors()是會在FilterChains中第二個的DefaultSecurityFilterChain裏面的LogoutFilter之前產生CorsFilter,但是第一個DefaultSecurityFilterChain始終沒有CorsFilter。

AuthorizationServerSecurityConfiguration order(0),所以第一個DefaultSecurityFilterChain來自於此,但是沒有加入http.cors(),所以找到原因所在。

解決方案一

都加上

ResourceServerConfig:
@Override
   public void configure(HttpSecurity http) throws Exception {
	http.cors();
	//...
}

@Bean
public CorsConfigurationSource corsConfigurationSource() {
    CorsConfiguration configuration = new CorsConfiguration();
    configuration.setAllowedOrigins(Arrays.asList("*"));
    configuration.setAllowedMethods(Arrays.asList("GET", "POST", "HEAD", "DELETE", "OPTION"));
    configuration.setAllowedHeaders(Arrays.asList("*"));
    configuration.addExposedHeader("Authorization");
    UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
    source.registerCorsConfiguration("/**", configuration);
    return source;
}

@Bean
public CorsFilter corsFilter() {
    return new CorsFilter(corsConfigurationSource());
}

兩個都加上
就會下如下圖這樣,除了在springSecurityFilterChain下面有corsFilter,也會在裏面有。
在這裏插入圖片描述

在這裏插入圖片描述

解決方案二

@Configuration
public class CorsFilterConfig {

    @Bean
    public CorsConfigurationSource corsConfigurationSource() {
        CorsConfiguration configuration = new CorsConfiguration();
        configuration.setAllowedOrigins(Arrays.asList("*"));
        configuration.setAllowedMethods(Arrays.asList("GET", "POST", "HEAD", "DELETE", "OPTION"));
        configuration.setAllowedHeaders(Arrays.asList("*"));
        configuration.addExposedHeader("Authorization");
        UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
        source.registerCorsConfiguration("/**", configuration);
        return source;
    }

    @Bean
    public CorsFilter corsFilter() {
        return new DefaultCorsFilter(corsConfigurationSource());
    }

    @Data
    static class DefaultCorsFilter extends CorsFilter implements OrderedFilter {

        /**
         * Constructor accepting a {@link CorsConfigurationSource} used by the filter
         * to find the {@link CorsConfiguration} to use for each incoming request.
         *
         * @param configSource
         * @see UrlBasedCorsConfigurationSource
         */
        public DefaultCorsFilter(CorsConfigurationSource configSource) {
            super(configSource);
        }

        @Override
        public int getOrder() {
            return -104;
        }
    }

}

這樣直接指定corsFilter在springSecurityFilterChain之前
(OrderedRequestContextFilter是-105)

解決方案三

AuthorizationServerConfig:
@Override
public void configure(AuthorizationServerSecurityConfigurer oauthServer) {
	oauthServer.addTokenEndpointAuthenticationFilter(new 	CorsFilter(corsConfigurationSource()));
		//...
}

ResourceServerConfig
@Override
public void configure(HttpSecurity http) throws Exception {
	http.cors();
	//...
}

還有很多方式,以上參考

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章