우아한테크코스/테코톡
CORS
newwisdom
2021. 8. 6. 14:20
반응형
2021-06-16글
[10분 테코톡] 🌳 나봄의 CORS을 들으며 정리한 글입니다.
배경 지식
SOP(Same Origin Policy)
- 다른 출처의 리소스를 사용하는 것에 제한하는 보안 방식
왜 SOP?
- CSRF Attack 때문!
- 사용자는 인증 토큰을 가지고 있는 상태
- 해커가 만든 주소로 이동하는데, 여기다 해커는 악의적인 스크립트를 심음
- 해커는 인증 토큰을 가지고 악의적인 스크립트를 실행할 수 있음
- 만약 송금이나 민감한 정보를 건드릴 시 굉장히 위험
여기서 SOP가 위력을 발휘
- 웹사이트 입장에서는 자신과 다른 출처를 가지기 때문에 위 요청은 받을 수 없다고 판단
출처(Origin)란?
- Protocol, Host, Port 세가지가 같아야 같은 출처라고 판단
- 참고로 인터넷 익스플로어는 출처판단에 Port가 포함되지 않음
🤔 그러면 다른 출처 리소스가 필요하면 어떻게해??
CORS!!
CORS란?
교차 출처 리소스 공유(Cross-Origin Resource Sharing, CORS)는 추가 HTTP 헤더를 사용하여, 한 출처에서 실행중인 웹 애플리케이션이 다른 출처의 선택한 자원에 접근할 수 있는 권한을 부여하도록 브라우저에 알려주는 체제입니다. - MOZILLA
CORS 접근제어 시나리오
단순 요청 (Simple Request)
- Preflight 요청 없이 바로 요청
조건을 모두 만족해야 함
- 메서드는 아래만 허용
- GET, POST, HEAD
- Content-Type은 아래만 허용
- application/x-www-form-urlencoded
- multipart/form-data
- test/plain
- Header는 아래만 허용
- Accept
- Accept-Language
- Content-Language
- Content-Type
프리플라이트 요청 (Preflight Request)
- 쉽게 말하자면 사전 확인 작업
- OPTIONS 메서드를 통해 다른 출처의 리소스에 요청이 가능한지 확인하는 작업
- 요청이 가능하면 실제 요청(Actual Request)을 보냄
- 클라이언트가 사전 요청을 보냄
- 서버는 이에 응답
- 만약 이 요청이 거부된다면 Actual Request는 보내지 않음
Preflight Request 포맷
- Origin : 요청 출처
- Access-Control-Request-Method : 실제 요청의 메서드
- Access-Control-Request-Headers : 실제 요청의 추가 헤더
Preflight Response 포맷
- Access-Control-Allow-Origin : 서버 측 허가 출처
- Access-Control-Allow-Methods : 서버 측 허가 메서드
- Access-Control-Allow-Headers : 서버 측 허가 헤더
- Access-Control-Max-Age: Preflight 응답 캐시 기간
- 사전 요청과 실제 요청을 매번 보내면 효율적이지 않으니 브라우저는 사전 요청을 캐싱해둠
Preflight Response 특징
- 응답 코드는 200대여야 함
- 응답 바디는 비어있는 것이 좋음
왜 Preflight가 필요할까?
- 사전 요청이 없으면 서버는 요청에 대해 모든 로직을 일단 수행함
- 그리고 나서 Origin을 판단
- 일단 로직이 수행된 후 CORS 이슈가 발생
- 사전 요청이 있으면 요청을 수행하기 전 Origin을 판단
- 때문에 서버는 안전히 잘 지켜짐
인증정보 포함 요청 (Credentialed Request)
- 인증 관련 헤더를 포함할 때 사용하는 요청
- 클라이언트 측
credentials : include
- 서버 측
Access-Control-Allow-Credentials : true
- 대신 이러면 아래와 같은 조건이 충족되어야 함
조건
Access-Control-Allow-Origin
에는*
를 사용할 수 없으며, 명시적인 URL이어야함- 응답 헤더에는 반드시
Access-Control-Allow-Credentials: true
가 존재해야함
🚨 Access to fetch at ’https://localhost:8080’ from origin ’http://localhost:8000’ has been blocked by CORS policy: The value of the ‘Access-Control-Allow-Origin’ header in the response must not be the wildcard ’*’ when the request’s credentials mode is ‘include’.
CORS 해결하기!
프론트 프록시 서버 설정(개발 환경)
- 브라우저 입장에서는 origin과 target이 같기 때문에
same origin
추가
스프링 부트 이용
@CrossOrigin 어노테이션 사용
참고
- Origin을 설정 안해주면 Default 값으로 모든 Origin을 허용함
- 때문에 설정해주는 것이 좋음
전역으로 설정하는 방법 - Config
참고 자료
반응형