CORS 이슈 해결 1 : 동일 출처

HeoSeungYeon·2022년 1월 30일
1
post-thumbnail

🗯️ 문제


프론트와 연동하는 과정에서 다음과 같은 오류가 발생했다.

에러 메세지를 보면 CORS 정책에 의해 HTTP 요청이 block 처리 되었다는 것을 알 수 있었다.

일단 CORS 정책이 뭔지 왜 필요한지 짚고 넘어갈 필요가 있다.

웹 브라우저에서 통신을 할 때, 보안을 위해 출처(Origin)에 따라 리소스를 공유하는 행위를 막는 정책은 크게 두가지 정책이 있다.

하나는 위에서 나온 CORS(Cross Origin Resourse Sharing : 교차 출처 자원 공유) 정책이고, 또 하나는 SOP(Same Origin Policy : 동일 출처 정책)이다. 직역으로 인해 “교차 출처”라는 말이 잘 와닿지 않을 수 있는데 참고한 포스팅에서 “다른 출처”라는 표현을 추천해줬는데 해석하기 더 용이한 것 같다.

그러면 출처가 서로 같고 다른 것은 어떤 기준으로 판단할까?

출처를 의 동일함을 판단하는 기준은 두 URL의 구성 요소 중에서 SchemeHostPort 이다.

예를 들어, API 개발자가 설정하는 요소인 경로(path), query parameter가 다른 값이라도 위 3가지 요소가 같으면 같은 출처로 판단한다.

🔥 해결 방법


CORS에 대한 사전 지식은 위에 작성한 것으로 충분한 것 같다.

우리 프로젝트(에브리벤트)에서는 CorsFilter를 bean으로 등록하고, WebSecurityConfig에서 filter를 추가하는 방식으로 CORS 정책에 대한 설정을 하고 있다. 아래의 코드를 보면 허용 출처(AllowedOrigin)를 설정하는 코드를 작성했는데 프론트 로컬 테스트 출처인 “http://localhost:3000”와 prod 출처인 “https://everevent-be69d.web.app:443” 만 허용 출처로 추가를 한 상태였다.

@Configuration
public class CorsConfig {

  @Bean
  publicCorsFilter corsFilter(){
      UrlBasedCorsConfigurationSource source =newUrlBasedCorsConfigurationSource();
      CorsConfiguration config =newCorsConfiguration();
      config.setAllowCredentials(true);
      config.addAllowedOrigin("http://localhost:3000");
      config.addAllowedOrigin("https://everevent-be69d.web.app:443");
      config.addAllowedHeader("*");
      config.addAllowedMethod("*");
      config.addExposedHeader("X-AUTH-TOKEN");
      source.registerCorsConfiguration("/api/v1/**", config);

      return newCorsFilter(source);
    }

}

그런데 왜 위 오류가 발생했지? 🤔

Json이 보내준 포스팅에 따르면 동일 출처를 판단하는 기준 중 포트 번호를 명시한 출처는 브라우저의 구현 로직에 따라 동일 출처로 판단하지 않을 수 있다.

예를 들어 “https://www.example.com”에서 서버에 요청을 날렸을 때, 서버 측 CORS 설정이 “https://www.example.com:443”일 경우 둘 간의 출처에 대한 판단이 브라우저마다 상이하다는 것이다.

해결 방안

위 내용을 참고하여, 아래와 같이 포트번호를 생략한 URL을 CORS 설정의 허용 출처에 추가하였다.

config.setAllowCredentials(true);
config.addAllowedOrigin("http://localhost:3000");
config.addAllowedOrigin("https://everevent-be69d.web.app");
config.addAllowedOrigin("https://everevent-be69d.web.app:443");
config.addAllowedHeader("*");
config.addAllowedMethod("*");
config.addExposedHeader("X-AUTH-TOKEN");
source.registerCorsConfiguration("/api/v1/**", config);

📖 참고문서


CORS는 왜 이렇게 우리를 힘들게 하는걸까?

0개의 댓글