브라우저에서는 보안의 문제로 인해 cross-origin
(원래 주소에서의 요청이 아닌것) HTTP 요청을 제한한다.그래서 cross-origin 요청을 하려면 서버의 동의가 필요한데, 만약 서버가 동의한다면 요청을 허락하고 동의하지 않는다면 브라우저에서 거절한다.
이러한 허락을 구하고 거절하는 메커니즘은 HTTP-header를 이용하여 가능하게 하는 것을 바로 CORS(Cross-Origin Resource Sharing)
이라고 부른다.
위에 3가지 중에 한 가지라도 다른 경우는 cross-origin
이다.
CORS가 없이 모든 곳에서 데이터를 요청할 수 있게되면, 다른 사이트에서 원래 사이트를 흉내낼 수 있다. 예를 들어서 기존의 사이트와 완전히 동일하게 동작하도록하여 사용자가 로근인을 하도록 만들고, 로그인했던 세션을 탈취하여 악의적으로 정보를 추출하거나 다른 사람의 정보를 입력하는 등 공격을 할 수 있다. 이런 공격을 할 수 없도록 브라우저에서 보호하고 필요한 경우에만 서버와 협의하여 요청할 수 있도록 하기 위해서 cors는 필요하다.
Access-Control-Request-Headers
의 값을 비교하여 유효한 요청이라면 리소스를 응답한다. 만약 유효하지 않다면 브라우저에서 에러를 발생시킨다.HTTP method
자동으로 설정되는 헤더는 제외하고, 설정할 수 있는 헤더
Content-Type
HTTP method경우는 그리 어렵지 않은 조건이지만 헤더와 content-type과 같은 조건은 까다롭다. 헤더 조건은 사용자 인증에서 사용하는 authorization 헤더도 포함되지 않아 까다로운 조건이며, 많은 REST API들이 content-type으로 application/json을 사용하기 때문에 지켜지기 어려운 조건이다.
preflight 요청은 서버에 예비 요청을 보내서 안전한지 판단한 후 본 요청을 보내는 방법이다. 다음 그림은 preflight 요청 동작을 나타낸다.
Preflight 요청은 실제 리소스를 요청하기 전에 OPTIONS라는 메서드를 통해 실제 요청을 전송할지 판단한다.
OPTIONS 메서드로 서버에 예비 요청을 먼저 보내고, 서버는 이 예비 요청에 대한 응답으로 Access-Control-Allow-Origin 헤더를 포함한 응답을 브라우저에 보낸다. 브라우저는 단순 요청과 동일하기 헤더를 확인하여 CORS 동작을 수행할지 판단한다.