Enabling CORS in SpringBoot Applications

This article explains what CORS is, shows the typical browser error caused by missing CORS headers, and provides step‑by‑step SpringBoot configuration and filter code to enable cross‑origin requests and control filter execution order for reliable backend support.

Full-Stack Internet Architecture
Full-Stack Internet Architecture
Full-Stack Internet Architecture
Enabling CORS in SpringBoot Applications

CORS (Cross‑Origin Resource Sharing) is a W3C standard that allows browsers to send Ajax requests to cross‑origin servers, breaking the same‑origin restriction.

In a front‑back separated architecture, CORS problems often appear as browser errors such as

No 'Access-Control-Allow-Origin' header is present on the requested resource.

.

SpringBoot Handling CORS

In SpringBoot the backend can enable CORS with a simple configuration class.

/**
 * Spring Boot 2.0 solution for CORS issues
 * @Author javadaily
 */
@Configuration
public class WebMvcConfiguration implements WebMvcConfigurer {

    @Bean
    public CorsFilter corsFilter() {
        final UrlBasedCorsConfigurationSource urlBasedCorsConfigurationSource = new UrlBasedCorsConfigurationSource();
        final CorsConfiguration corsConfiguration = new CorsConfiguration();
        /* Whether to allow credentials */
        corsConfiguration.setAllowCredentials(true);
        /* Allowed origins */
        corsConfiguration.addAllowedOrigin("*");
        /* Allowed request headers */
        corsConfiguration.addAllowedHeader("*");
        /* Allowed HTTP methods */
        corsConfiguration.addAllowedMethod("*");
        urlBasedCorsConfigurationSource.registerCorsConfiguration("/**", corsConfiguration);
        return new CorsFilter(urlBasedCorsConfigurationSource);
    }
}

The configuration injects a CorsFilter and sets permissive values; replace the asterisks with specific origins, headers, or methods as needed.

Special Cases

If a custom filter writes directly to the response using response.getWriter().print(), the filter chain stops and the CORS filter may never run, because custom filters have higher priority than the WebMvcConfigurer filter.

Solution

Define a custom CORS filter that extends CorsFilter and registers it before other filters.

public class CustomerCorsFilter extends CorsFilter {

    public CustomerCorsFilter() {
        super(configurationSource());
    }

    private static UrlBasedCorsConfigurationSource configurationSource() {
        // CORS configuration
        CorsConfiguration config = new CorsConfiguration();
        config.setAllowCredentials(true);
        config.addAllowedOrigin("*");
        config.addAllowedHeader("*");
        config.addAllowedMethod("*");
        config.addExposedHeader(HttpHeaders.SET_COOKIE);
        config.setMaxAge(3600L);
        UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
        source.registerCorsConfiguration("/**", config);
        return source;
    }
}

Specify filter order in a configuration class to ensure the CORS filter runs before custom filters.

@Configuration
public class FilterConfig {

    @Bean
    public Filter authFilter() {
        return new AuthFilter();
    }

    /**
     * WARNING: CORS filter, must execute after AuthFilter
     */
    @Bean
    public FilterRegistrationBean corsFilterRegistration() {
        FilterRegistrationBean registration = new FilterRegistrationBean();
        registration.setFilter(new CustomerCorsFilter());
        List<String> urlList = new ArrayList<>();
        urlList.add("/*");
        registration.setUrlPatterns(urlList);
        registration.setName("CorsFilter");
        registration.setOrder(-1); // smaller order = higher priority
        return registration;
    }

    @Bean
    public FilterRegistrationBean authFilterRegistration() {
        FilterRegistrationBean registration = new FilterRegistrationBean();
        registration.setFilter(authFilter());
        List<String> urlList = new ArrayList<>();
        urlList.add("/*");
        registration.setUrlPatterns(urlList);
        registration.setName("authFilter");
        registration.setOrder(1);
        return registration;
    }
}

Using setOrder() ensures the CORS filter has a higher priority (lower order value) than other custom filters, preventing CORS errors in special scenarios.

Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

BackendjavaCORSCross-OriginSpringBootfilter
Full-Stack Internet Architecture
Written by

Full-Stack Internet Architecture

Introducing full-stack Internet architecture technologies centered on Java

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.