목표

  • CORS 트러블 슈팅

CORS 트러블 슈팅

상황

그냥 배포할 땐 큰 문제 없었는데, 배포된 테스트용 BE 서버에 프론트 분들이 localhost에서 프론트 dev서버를 띄워 배포된 BE 서버에 요청을 보내는 경우, domain이 달라져 브라우저에서 set cookie 등을 차단하는 문제가 발생했다.

그냥 API 통신은 Access-Control-Allow-Origin: * 정도만 설정해줘도 되지만, BE 서버가 브라우저에 cookie를 등록하고 전달받아야 하는 경우엔 훨씬 많은 처리가 필요하다.

정리

  • 배포된 테스트용 BE서버 : https://www.별글.site
  • 로컬 테스트용 FE서버 : http://localhost:5173
  • origin이 같지 않아 브라우저에서 cookie 세팅을 차단하는 문제
    • BE에서 HTTPS를 제공해야 함 (도메인 사서 Let's Encrypt 인증서 발급, NGINX에 HTTPS 설정! 학습메모 1 참고)
    • origin은 *이 아닌 정확한 도메인명 명시해야 함
      • ['https://www.xn--bj0b03z.site', 'http://localhost:5173']
      • 안되면 메소드명도 직접 명시
    • credentials를 포함하도록 FE, BE 모두 설정해야 함
      • 백에서는 enableCors에서 credentials: true 또는 Response 헤더에 Access-Control-Allow-Credentials: true 직접 설정
      • 프론트에서 axios, fetch등으로 요청할 때도 credentials: include 또는 withCredentials: true 설정을 해주어야 함
    • set cookie시 sameSite:none, secure:true 옵션을 설정해야 함
// cors 허용
app.enableCors({
  // Access-Control-Allow-Origin : 도메인 명시 (* 안됨)
  origin: ['https://www.xn--bj0b03z.site', 'http://localhost:5173'], 
  // Access-Control-Allow-Credentials : true
  credentials: true, 
  methods: ['GET', 'HEAD', 'POST', 'PUT', 'PATCH', 'DELETE', 'OPTIONS'],
});
...
// 쿠키 세팅 시
res.clearCookie(JwtEnum.ACCESS_TOKEN_COOKIE_NAME, {
  path: '/',
  httpOnly: true,
  sameSite: 'none',
  secure: true,
});
res.clearCookie(JwtEnum.REFRESH_TOKEN_COOKIE_NAME, {
  path: '/',
  httpOnly: true,
  sameSite: 'none',
  secure: true,
});
...
// FE에서 AJAX 요청 시
axios.defaults.withCredentials = true;

학습메모

  1. 배포 시 HTTPS 적용 with Let's Encrypt
profile
해커 출신 개발자

0개의 댓글