CORS(Cross-Origin Resource Sharing) 란?
- 교차 출처 자원 공유라는 말로 서로 다른 출처간에 리소스를 공유하는 것을 허용하는 정책을 의미한다.
- 서로 다른 출처 공유에 대해서는 기본적으로 제한되어있다. (이를 SOP라 한다.)
*SOP (Same-Origin Policy) : 같은 출처끼리만 리소스를 공유할 수 있다는 정책
HTML태그를 통한 이미지, CSS, Script 요청은 SOP에 제한이 되지 않음
Origin : 출처를 의미하며, URL구조 / 프로토콜 + 호스트 + 포트를 합친 것을 말함
Port가 다른 경우에 다른 출처로 인식한다.
HTTP 포트 : 80 / HTTP 포트 : 443 생략 가능
CORS가 정의된 이유
SOP(Same-Origin Policy)의 장점
동일 출처 정책을 지키면 외부 리소스를 가져오지 못해 불편하지만, 동일 출처 정책은 보안 취약점을 노린 공격을 방어할 수 있다.
그런데 이런 SOP에도 한계가 있다.
SOP의 한계
현실적으로는 외부 리소스를 참고하는 것은 필요하기 때문에 외부 리소스를 가져올 수 있는 방법이 존재해야 한다.
외부 리소스를 사용하기 위한 SOP의 예외 조항이 CORS다.
1. Simple request (단순 요청 방법은 서버에게 바로 요청을 보내는 방법)
단순 요청은 서버에 API를 요청하고, 서버는 Access-Control-Allow-Origin 헤더를 포함한 응답을 브라우저에 보낸다. 브라우저는 Access-Control-Allow-Origin 헤더를 확인해서 CORS 동작을 수행할지 판단한다.
단순 요청으로 동작하기 위해서 서버로 전달하는 요청(request)이 만족해야하는 조건
1) 요청 메서드는 GET, HEAD, POST 중 하나여야 한다.
2) Accept, Accept-Language, Content-Language, Content-type, DPR, DOwnlink, Save-Data, Viewport-Width, Width 의의 헤더를 사용하면 안된다.
3) Content-type 헤더는 application/x-www-form-urlencoded, multipart/form-data, text/plain 중 하나를 사용해야 한다.
Preflight request
서버에 예비 요청을 보내서 안전한지 판단한 후 본 요청을 보내는 방법
실제 리소스를 요청하기 전에 OPTIONS이라는 메서드를 통해 실제 요청을 전송할지 판단한다.
OPTIONS 메서드로 서버에 예비 요청을 먼저 보내고, 서버는 이 예비 요청에 대한 응답으로 Access-Control-Allow-Origin 헤더를 포함한 응답을 브라우저에 보낸다. 브라우저는 단순 요청과 동일하게 Access-Control-Allow-Origin 헤더를 확인해서 CORS 동작을 수행할지 판단한다.
Preflight를 날리는 이유
브라우저가 CORS를 지원하지 않은 서버에 도달하면 요청에 대한 응답을 보내지 않아 실제 요청이 수행되지 않도록 보호하기 위함.
먼저 OPTIONS 메서드를 통해 다른 도메인의 리소스로 HTTP 요청을 보내 실제 요청이 전송하기에 안전한지 확인한다. cross-origin 요청은 유저 데이터에 영향을 줄 수 있기 때문에 이와같이 미리 전송(preflighted)합니다.
CORS 에러 해결 방법
- 서버에서 응답 헤더에 특정 헤더를 포함하는 방식으로 해결할 수 있다.
Access-Control-Allow-Origin : 특정 origin이 리소스에 접근이 가능하도록 허용한다.
Access-Control-Allow-Method : 특정 HTTP Method만 리소스에 접근이 가능하도록 허용한다.
Access-Control-Expose-Headers : JavaScript에서 헤더에 접근할 수 있도록 허용한다.
credentials request에 대해서는 추후에 추가 예정.
'BackEnd > Express' 카테고리의 다른 글
[Express] Express로 하는 MVC 패턴 예제 (feat. MongoDB) (0) | 2025.02.23 |
---|---|
[NodeJS/Express] Express에 대해서 (0) | 2024.06.29 |