아래는 클라이언트 측인 브라우저에서 발생하는 CORS(Cross Origin Resource Sharing)에 대하여 간단하게 이해 및 정리한 내용입니다.


! 골치 아픈 에러 CORS... 언제 그리고 왜?
API를 사용하는 경우 누구나 한 번은 CORS 에러를 경험한 적이 있을 것입니다. 이 에러가 발생할 경우 제대로 된 API 통신이 이루어지지 않으며 브라우저는 CORS 에러 메시지를 출력하게 되죠. 그렇다면 왜 이런 에러가 발생하게 될까요?

"CORS는 무엇이고 언제 왜 발생하게 되나..."



먼저 CORS는 무엇일까요? CORS는 말 그대로 요청에 대하여 Origin을 지나서 함께 공유하는 것을 의미합니다. 즉 Origin이 다른 경우에도 Resource를 공유할 수 있음을 의미합니다. 웹브라우저의 경우 AJAX를 사용하는 비동기 통신의 경우 Origin과 Referer를 확인하여 송수신 허용을 결정하게 됩니다. 이는 Same Origin Policy인 동일 출처 정책을 말하는데요 동일한 요청에만 정상적인 응답을 반환하는 것을 기본으로 하는 정책을 가지고 있습니다.

!! 다시 정리하자면...
자바스크립트를 사용하여 ajax로 데이터를 fetching 할 경우 CORS 에러가 발생할 수 있고 이는 Same Origin Policy에 따라 발생하게 됩니다. 이때 Origin의 기준은 host 뿐만 아니라 port, subdomain 등도 여기에 해당하게 됩니다.


! 동일 출처 원칙(Same Origin Policy)이 필요한 이유는?
가장 큰 목적은 당연히 보안입니다... 즉 허용되지 않은 호스트의 호출 응답을 방지하기 위함입니다. 예를들어 위험성이 높은 외부 접근자가 악의적인 목적으로 사용되는 것을 방지하기 위한 브라우저의 기본 기능 중 하나입니다.

만약 CORS가 느슨한 경우에는 해커등의 공격 대상이 될 수 있습니다. 간단하게 예를들면 하나의 서버에 무수히 많은 ajax 시도를 통해서 서버에 부하를 주는 DDOS 공격을 발생할 수도 있겠습니다. Request 요청은 파라미터나 쿠키(Cookie) 크기에 따라 차이가 많죠.


[참고 1] CrossDomainAttack의 예
만약 A라는 사이트는 B 이름의 사이트에게서 정보를 얻을 수 있는 호스트 권한을 가진다고 가정해봅니다.

"A 서버(host A)에서는 -> B 서버(host B)의 정보를 가져올 수 있음"


이때 A 사이트를 사용하여 Code Injection 등의 방법으로 B에 정보를 요청할 수 있다면 어떨까요? B의 정보를 가져오는 것도 가능할 수 있겠습니다. 물론 A 사이트가 아닌 경우라면 same origin policy에 의하여 동작이 자체가 안되겠죠.


[참고 2] CORS를 브라우저에서 피하는 방법이 있을까?
로컬인 경우 가능한 방법이 있기는 합니다. 이 경우 브라우저의 플러그인을 추가로 설치하는 방법이 있는데요~ 이 경우 반드시 로컬에 한하며... 또 내부 개발 목적인 경우에만 사용이 가능하겠습니다.


# 그래서 CORS는 어떻게 동작하는가?
다시 돌아와서... 브라우저는 스크립트를 사용한 다른 서버로의 요청이 동일한 origin인지 우선 확인합니다. 즉 프론트 서버와 백엔드 서버의 도메인을 확인하고 이때 호스트 외에 프로토콜, 포트의 동일 여부도 확인합니다.

프론트의 요청은 기본적으로 아래와 같이 Origin 정보를 포함하게됩니다.
Origin: https//localhost:8000
요청을 받은 서버는 응답 헤더를 전송하게 됩니다. 이 경우 응답 헤더에는 받을 수 있는 메소드 정보를 포함하면서 동시에 Access-Control-Allow-Origin이라는 값을 보낼 수 있습니다. 즉 어떤 Origin에 허용이 가능한지 헤더에 담아서 알려줄 수 있습니다.

이 방법을 사용하여 서버는 Origin을 제한할 수 있고 반대로 특정 도메인을 허용하는 것이 가능합니다. 예를들어 다음과 같이 하나나 모든 도메인을 허용할 수 있습니다.
Access-Control-Allow-Origin: * (모든 허용을 의미, 와일드카드)

브라우저는 이 두 값인 Origin과 Access-Control-Allow-Origin을 비교하여 허용할지 아니면 거부할 것 인지를 알려주게 됩니다. 즉 거부되는 경우라면 CORS 에러를 발생하게 되겠습니다.


! CORS를 해결하기 위한 방법
정리하자면... CORS 에러를 피하기 위해서는 request origin과 response origin의 값을 일치하는 작업이 필요합니다. 많이 사용되는 OpenAPI 등이 이런 방식을 사용하게 되겠죠.

그리고 또 다른 방법이 있다면 프록시 서버를 사용하는 방법이 있습니다. 즉 중간에 다른 서버를 사용하여 요청 정보를 전달 받은 뒤 다시 전달하는 방법입니다. 프록시 서버의 경우 이미 제공하는 프록시 서버를 사용할 수도 있고 아니면 직접 만들어 사용하는 것도 가능함.

여기까지 CORS 및 Same Origin Policy 등에 대하여 간략하게 알아보았습니다.