CORS 해결 과정

Circlewee·2022년 8월 10일
0

Project

목록 보기
1/2

처음 진행한 프로젝트에서 해결한 문제를 노션에 기록하였었고 그것을 옮긴 게시글 입니다.
배포 후 발생한 CORS문제를 해결한 게시글도 있습니다.

CORS

  • CORS는 Cross-Origin-Resource-Sharing의 약자로 교차 출처 리소스 공유의 약자이다.(MDN)
    이것은 SOP라 불리는 동일 출처 정책의 예외이고 SOP를 어겼을 때 CORS마저 지키지 않는다면 브라우저는 오류를 내뱉게 되는 것이다.
  • 먼저 SOP에 대해 알아보자.
    같은 출처가 아닌 다른 출처에서 불러온 문서나 스크립트와 상호작용하는 것을 제한하는 아주 중요한 보안 방식이다.
    여기서 출처라는 것은 두 URL의 프로토콜, 포트, 호스트가 모두 같아아 동일한 출처라고 할수 있다.

  • 다음으로 CORS다. 항상 같은 출처에서만 데이터를 요청할수는 없기 때문에 예외인 CORS 정책을 지킨다면 브라우저는 서버로 부터 받아온 데이터를 JS에 넘겨준다.

    작동 방식은 간단하다. 먼저 JS에서 AJAX를 이용해 요청을 보내면 브라우저는 예비 요청을 먼저 서버에 보낸다. 서버는 예비요청에 해당하는 예비 응답을 보내주고 브라우저가 응답의 헤더에 담긴 Access-Control-Allow-Origin을 확인한다.

    만약 여기에 명시된 값이 요청을 보내는 페이지의 URL과 일치하거나 *이면 CORS를 지킨것을 확인하고 본 요청을 다시 보내고 본 응답을 받아 JS에 건내주며 통신은 마무리 된다.

    여기서 주의해야할 점이 *인데 개발할때 만약 포트번호나 주소가 계속 바뀐다면 서버에서 이렇게 명시해주는 것이 편할지는 몰라도 모든 주소의 요청을 허용한다는 뜻이므로 매우 위험한 상태이다.

    하지만 ACAO에서만 명시해 준다고 완벽하게 해결한 것은 아니다. 요청 메소드와 헤더등에 따라서도 제한할 수 있다. 자세히 명시할 수록 보안성을 올릴 수 있을 것이다.

프로젝트에서의 해결

  • 최근에 가장 오랜 시간을 투자해 해결한 CORS오류가 있다. 미니 프로젝트 진행 중에 서버로 사용자의 토큰이 유효한지 판단한 후 axios.get(URL)을 통해 해당 사용자의 글 데이터를 받아오는 것이었는 데 쿠키에 저장된 토큰이 요청의 헤더에 포함되지 않아서 CORS에러가 뜬 것이다.
    (물론 이때는 포트번호까지 같아야 하는 줄 몰랐었다.)

    구글을 통해 열심히 찾아본 결과 서버 구현에서 쿠키에 들어있는 토큰의 유효여부를 판단한 뒤 원하는 요청을 처리해주는 방식이었는데 CORS에서는 기본적으로 보안 때문에 헤더에 쿠키를 추가해 보낼수가 없었다. 하지만 우리의 경우처럼 인증을 처리해야하는 경우에 사용할 수 있는 옵션이 바로 아래이다.

// 프론트엔드에서 처리
axios.defaults.withCredentials = true;
    
// 백엔드에서 처리
app.use(cors({
	...
	credential: 'true',
})
  • origin 에서 *이 위에서 설명한 것처럼 모든 접근을 허용하겠다는 뜻이기 때문에 이대로 배포하는 것은 그냥 문을 활짝 열어두겠다는 뜻이므로 안하느니만 못한 경우가 되버린다. 따라서 특정 URL을 명시해주거나 다양한 방법으로 관리해주는 것이 좋다.

  • 또 다른 방법으로는 프록시를 사용하는 것이다. 서버와 동일한 주소를 가진 프록시 서버를 만든 후 브라우저는 프록시 서버를 통해 본 서버와 통신하게 된다.(같은 출처에 해당) 사실 프로젝트에서는 위의 방법을 사용했다가 편하게 관리하기 위해 프록시를 사용하고 있다.

느낀 점

처음 이 에러를 마주했을 땐 엄청 까다로운 녀석이라고 생각했다. 하지만 가만히 돌아보면 최소한의 기본적인 방어책이라는 생각도 든다. 만약 API서버의 주소가 유출되고 아무 서비스의 요청을 모두 받아주게된다면 어떤 결과로 이루어 질지는 상상만 해도 끔찍하다.

지금은 공부하면서 미니, 클론코딩 정도의 프로젝트만 진행하느라 로컬환경에서만 개발하지 배포할 일은 없어서 보안에 대한 경우는 신경쓰지 않았었다. 앞으로 규모가 있는 프로젝트를 하고 싶은 욕심도 있고 현업에서 일을 하면서 필수적으로 고려해야할 요소이므로 이번 기회에 잘 배울 수 있었다고 생각한다.

Reference
MDN CORS

profile
공부할 게 너무 많아요

0개의 댓글