2 분 소요

프론트엔드와 협업프로젝트를 진행하던 중, CORS 이슈가 발생하였다. Spring Boot 프로젝트를 처음 EC2에 배포하고 있는데, 이거 생각보다 신경 쓸 것이 정말 많다.

CORS 관련해서는 이미 좋은 글이 많이 있어서, 포스트 아래에 관련한 링크들을 첨부해둔다. 이 포스트는 내가 공부한 내용을 간단하게 정리하고 다음번에 쉽게 기억해내기 위한 글이다.


1. CORS는 무엇?

  • SOP(Same Origin Policy), 즉 다른 출처의 리소스를 사용하는 것에 제한하는 보안 방식을 넘어서 접근을 가능하게 해주는 것.
  • CORS(Cross Origin Resource Sharing)
  • 어떠한 요청이 왔을 때, 그 요청이 요청한 클라이언트가 직접 보낸 것인지(악의적으로 우회하여 들어온 요청이 아닌지) 확인이 가능하며
  • 해당 클라이언트가 보낸 요청이 맞더라도, 그 클라이언트의 권한을 넘어서는 요청을 보내게 되면
  • (중요) HTTP 헤더를 사용하여 브라우저단에서 요청을 막는 보안 방식.
  • 이런 요청에서는 요청을 받게 된 서버는 작업을 하여 Response를 보내고, 브라우저가 이후에 Origin을 판단하여 동일 출처가 아니면 접근하지 못하도록 막음.
  • 즉, 브라우저가 주체인 작업이다.
  • 따라서, Spring Boot 범위에 들어오기 전에 Filter를 통해 걸러지게 된다. (벌써 쌔하죠?)

2. CORS 접근요청 방식?

  • 단순요청(Simple Request)

    • 요청을 보낼 때 CORS도 함께 체크하는 방식
  • 프리프라이트 요청(Preflight Request)

    • Preflight 요청을 먼저 보내서 서버와 미리 연락하는 방식
    • OPTIONS 메서드로 서버에 작업이 가능한지 확인
    • 요청이 가능하다면 실제 요청(Actual Request)를 보냄
    • 결국 2번의 요청이 가게 됨

    ** 왜 이런 비효율적인 방법으로 진행할까?*

    • GET 등의 비교적 안전(?)한 작업은 상관 없지만, DELETE와 같이 DB와 서버의 정보를 바꾸는 작업들은 허가가 되지 않은 정보가 왔을 때 브라우저단에서 미리 체크를 하고 진행하는 것이 훨씬 좋음!

      img

      위 이미지는 Preflight 방식의 CORS 요청 적용방식. 단순요청은 첫번째 요청으로 이미 Server는 필요한 작업을 하게 되는데, 작업을 다 하고보니 response를 주면 안될 클라이언트였다면??? 그래서 Preflight 방식이 필요함.

      (출처: https://medium.com/@x24mak/cross-origin-resource-sharing-cors-275e52b021b8)

      (+ 추가로 유튜브 댓글에서 은둔고수의 이야기를 보게 됨)

      Preflight가 왜 있는가에 대해서는 쉽게 말해서 
      CORS spec이 생기기 이전에 만들어진 서버들은 브라우저의 SOP(same origin policy) request만 가능하다는 가정하에 만들어졌는데, cross-site request가 CORS로 인해서 가능해졌기 때문에 이런 서버들은 cross-site request에 대한 security mechanism이 없다보니 보안적으로 문제가 생길수 있으니 이런 서버들을 보호하기 위해 CORS spec에 preflight request를 포함한겁니다. 
      Preflight request로 서버가 CORS를 인식하고 핸들할수있는지 먼저 확인을 함으로써 CORS를 인식하지 못하는 서버들을 보호할수있는 매커니즘 입니다.
      
  • 인증정보 포함 요청(Credentialed Request)

    • 쿠키, 세션, 토큰 등의 인증정보를 포함하여 연락하는 방식
    • 쌔하다. SpringBoot에서 인증하면 빠질 수 없는게 바로 Spring Security 아니겠는가???

3. 구현 방법

  • 필터 세팅이 필요하며, Security Config의 HttpSecurity에도 설정이 필요하다.

4. 참고자료

  • 전체적인 개념 설명 영상: https://youtu.be/-2TgkKYmJt4
  • 관련한 세팅 및 문제에 대해 잘 설명된 글: https://yousrain.tistory.com/22
  • 직접 필터클래스를 만드는 글: https://vvshinevv.tistory.com/62
  • 기타 참고한 포스트들
    • https://velog.io/@minchae75/Spring-boot-CORS-%EC%A0%81%EC%9A%A9%ED%95%98%EA%B8%B0 https://oingdaddy.tistory.com/243 https://dev-pengun.tistory.com/entry/Spring-Boot-CORS-%EC%84%A4%EC%A0%95%ED%95%98%EA%B8%B0#2.3.%20allowedMethods https://oddpoet.net/blog/2017/04/27/cors-with-spring-security/ https://docs.spring.io/spring-framework/docs/current/reference/html/web.html#mvc-web-security https://devlog-wjdrbs96.tistory.com/429 https://velog.io/@ooooorobo/%EB%8B%A4%EB%A5%B8-%EB%8F%84%EB%A9%94%EC%9D%B8%EC%97%90-%EC%BF%A0%ED%82%A4-%EC%84%A4%EC%A0%95%ED%95%98%EA%B8%B0

마지막 수정일시: 2022-11-11 02:44

댓글남기기