[Spring] 스프링의 CORS설정

이멀젼씨

·

2021. 6. 23. 16:45

목적

CORS를 이해하여 서로 다른 출처간의 자원공유를 원활히 하기 위함

목차

  1. CORS란
  2. 스프링의 CORS설정
  3. 스프링 시큐리티의 CORS설정
  4. 스프링의 CORS? 스프링 시큐리티의 CORS?

1. CORS란?

CORS란Cross-Origin Resource Sharing, 교차 출처 리소스 공유의 약자이다.

서로 출처가 다른 웹 애플리케이션에서 자원을 공유하는 것을 말한다.

여기서 출처는 '프로토콜://도메인:포트' 이다. 예를 들자면 http://localhost:8080 이다.

CORS에러

[cors에러]

프론트엔드와 백엔드의 출처가 다르면 위와 같은 에러를 심심치 않게 볼 수 있다.

브라우저는 보안상의 이유로 교차 출처 HTTP요청을 제한한다.

이를 해결하기 위해선 백엔드에 CORS관련 설정을 해주어야 한다.

CORS헤더

서버가 접근 제어 요청을 위해 보내는 응답 헤더들이다.

  • Access-Control-Allow-Origin

    • 서버의 자원에 접근할 수 있는 출처를 명시한다.
    • 와일드카드(*)를 사용하면 아무 출처에서나 서버의 자원에 접근할 수 있다.
  • Access-Control-Expose-Headers

    • 브라우저에게 표시할 헤더를 명시한다.
    • ABC라는 헤더를 브라우저에서 확인할 수 있게 하려면 위의 헤더를 사용하여 ABC헤더를 명시해주면 된다.
  • Access-Control-Max-Age

    • preflight 요청 결과를 캐시할 수 있는 시간을 의미한다.
  • Access-Control-Max-Age

    • preflight 요청 결과를 캐시할 수 있는 시간을 의미한다.
  • Access-Control-Allow-Credentials

    • 같은 출처라면 기본적으로 쿠키가 request헤더에 자동으로 설정된다.
    • 하지만 CORS는 다른출처간의 통신이기 때문에 자동으로 설정되지 않는다.
    • 응답헤더에 헤더의 속성을 true주면 클라이언트에서 보낸 쿠키를 받을 수 있다.
  • Access-Control-Allow-Method

    • 요청이 허용되는 메소드를 지정한다.
    • 와일드카드(*)를 통해 모든 메소드를 허용할 수 있다.
  • Access-Control-Allow-Headers

    • 요청이 허용되는 메소드를 지정한다.
    • 와일드카드(*)를 통해 모든 메소드를 허용할 수 있다.
  • Access-Control-Allow-Headers

    • 서버로 요청 시 사용할 수 있는 헤더를 명시한다.

아래는 웹브라우저가 서버로 요청을 보낼때 사용하는 요청 헤더들이다.

  • Origin

    • 출처를 나타낸다.
    • 요청이 시작된 서버의 경로정보는 포함하지 않고, '프로토콜://도메인:포트' 만을 포함한다.
  • Access-Control-Request-Method

    • 어떤 메소드를 사용할지 서버에게 알려준다.
  • Access-Control-Allow-Headers

    • 어떤 헤더를 사용할지 서버에게 알려준다.

2. 스프링에서의 설정

WebMvcConfigurer를 상속하는 클래스를 하나 만든다음

addCorsMappings를 재정의 해주면 된다.

필자의 경우엔 모든 경로에 대해 cors를 적용하기 위해 addMapping("/**")를 사용했다.

JWT로그인을 위해 클라이언트에서 X-AUTH-TOKEN헤더에 에 접근할 수 있도록 exposedHeaders("X-AUTH-TOKEN")

클라이언트에서 쿠키를 받기 위해 allowCredentials(true)

내 컴퓨터의 프론트엔드 서버에서만 요청을 받기 위해 allowedOrigins("http://localhost:3000") 설정하였다.

3. 스프링 시큐리티에서의 설정

WebSecurityConfigurerAdapter를 상속하는 클래스를 하나 만든다음

configure를 재정의해주면 된다.

여기선 cors()메소드만 사용하면 된다.

4. 스프링의 CORS? 스프링 시큐리티의 CORS?

스프링에서 cors설정을 해야하는지, 스프링 시큐리티에서 cors설정을 해야하는지 헷갈릴 것이다.

스프링과 스프링 시큐리티를 함께 사용중이라면 CORS설정은 두 가지 방법으로 할 수 있다.

  1. 스프링에서 WebConfigurerAdapter를 상속하는 클래스에 addCorsMappings메소드를 재정의한다.
  2. 스프링 시큐리티에서 CorsConfigurationSource 클래스를 만들고 내부에 CorsConfiguration을 세팅한다.

둘 중 하나를 하더라도 스프링 시큐리티를 사용중이라면 WebSecurityConfigurerAdapter를 상속하는 클래스에서 configure를 재정의하여 cors()를 사용해야한다.

1번과 같이 선언하였다면 스프링 시큐리티에서는 스프링에 선언된 CORS구성을 활용하기 때문에 따로 CORS관련 필터를 정의할 필요가 없다.

자세한 내용은 여기를 참조하기 바란다.