'React Spring Oauth2 authorization code grant
I need help to resolve following CORS error.
Access to fetch at 'http://localhost/auth/realms/demo/protocol/openid-connect/auth?response_type=code&client_id=oauth2-demo&scope=openid&state=QQnjRZQ82U2KwgAczZ98u-JR0pUhDXgM4z0wlUOPPhM%3D&redirect_uri=http://localhost:8080/login/oauth2/code/oauth2-demo&nonce=ayTCEaqST3A0oRufr9JBDxvPdHx3SWL3GOTilDBASbE' (redirected from 'http://localhost:8080/authenticate') from origin 'http://localhost:3000' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource. If an opaque response serves your needs, set the request's mode to 'no-cors' to fetch the resource with CORS disabled.
I am using Spring Boot Oauth2 client to interact with keycloak Oauth server. I am using react login button to call and fetch the access token from Spring Boot Oauth client by calling URI "http:localhost:8080/authenticate".
When I call the same URL from browser everything works fine and oauth flow completes successfully and return the access token however when I call it from react APP Oauth2 redirects fails with CORS error.
@Configuration
@EnableWebSecurity
public class OAuth2LoginSecurityConfig {
@Bean
public SecurityFilterChain filterChain2(HttpSecurity http) throws Exception {
http.cors().configurationSource(corsConfigurationSource()).and().csrf().disable();
http.authorizeHttpRequests((authz) -> authz.anyRequest().authenticated()).oauth2Login();
return http.build();
}
@Bean
CorsConfigurationSource corsConfigurationSource() {
CorsConfiguration configuration = new CorsConfiguration();
configuration
.setAllowedOrigins(Arrays.asList("http://localhost:3000", "http://localhost", "http://localhost:8080"));
configuration.setAllowedMethods(Arrays.asList("HEAD", "GET", "PUT", "POST", "DELETE", "PATCH", "OPTIONS"));
configuration.setAllowCredentials(false);
// the below three lines will add the relevant CORS response headers
configuration.addAllowedOrigin("*");
configuration.addAllowedHeader("*");
configuration.addAllowedMethod("*");
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
source.registerCorsConfiguration("/**", configuration);
return source;
}
@Bean
public RequestCache refererRequestCache() {
return new HttpSessionRequestCache() {
@Override
public void saveRequest(HttpServletRequest request, HttpServletResponse response) {
String referrer = request.getHeader("referer");
if (referrer != null) {
request.getSession().setAttribute("SPRING_SECURITY_SAVED_REQUEST", new SimpleSavedRequest(referrer));
}
}
};
}
}
Below is the CORS Filter
@Slf4j
public class CORSFilter implements Filter {
@Override
public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain)
throws IOException, ServletException {
HttpServletRequest request = (HttpServletRequest) req;
HttpServletResponse response = (HttpServletResponse) res;
String check = "xsrf-token,X-Total-Results,Authorization";
response.setHeader("Access-Control-Allow-Origin",request.getHeader("Origin"));
System.err.println(request.getHeader("Origin"));
response.setHeader("Access-Control-Allow-Credentials", "true");
response.setHeader("Access-Control-Allow-Methods", "POST, GET, PUT, OPTIONS, DELETE, FETCH");
response.setHeader("Access-Control-Max-Age", "3600"); //
response.setHeader("Access-Control-Allow-Headers",
"Content-Type, Accept, X-Requested-With, remember-me, Authorization");
response.setHeader("Access-Control-Allow-Headers", "*");
response.setHeader("Access-Control-Expose-Headers", check);
if ("OPTIONS".equalsIgnoreCase(request.getMethod())) {
log.warn("Request get method call status SC_OK.");
response.setStatus(HttpServletResponse.SC_OK);
} else {
log.warn("Request get method not work chain start.");
chain.doFilter(req, res);
}
}
@Override
public void init(FilterConfig filterConfig) {
}
@Override
public void destroy() {
}
}
I noticed that JSESSIONID is missing while invoking the url from react app while the same is present while invoking from standalone browser. Also invoking in a pop up window oauth2 flow is getting completed. I am wondering what wrong with react without pop-up
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|
