본문 바로가기
프로젝트/Django - How Dimt?

Django poj.c E5) CSRF token에 대하여, 토큰 검증 문제 해결 - 프로젝트 마감 추가글 2번

by Fola 2022. 6. 1.

Code E - Server 5번 글, 6월 1일 (수)

 

자격증 시험 준비로 미뤄 두었던

프로젝트 34~35일 차 (5월 21일~22일) 프로젝트 진행 과정 기록

( 프로젝트 마감 추가글 2번 )

 

 

< CSRF 검증 실패(CSRF trust) 문제 해결 >

 

 

 

 

 

1. Error 상황

 

(캡쳐) CSRF 검증 실패 403 Forbidden 에러

CSRF 토큰을 사용하는 form 태그의 post 요청 시 

접근하고 있는 호스트가 신뢰할 수 있는 origins 목록에 없다는 Debug 메시지와 함께

403 forbidden 에러가 발생하였다.

 

 

 

 

 

 

2. CSRF 토큰?

 

Django Framework는 form tag로 데이터를 전송할 때 필수로 {% csrf_token %} 코드를 요구한다.

 

CSRF는 Cross-site Request Forgery의 약자이다.

사이트 간 위조 요청 정도로 해석할 수 있다.

 

csrf_token의 작동 원리는 다음과 같다.

서버는 클라이언트의 세션에 무작위 난수를 저장한다.

이후 클라이언트가 {% csrf_token %} 코드를 포함한 모든 request에 대해

서버에 저장된 난수 값과 클라이언트 세션에 저장된 난수 값이 동일한지 확인한다.

 

따라서 위조된 페이지는 서버가 발행한 token값이 일치하지 않으므로 접근이 불가능하다.

이러한 보안 시스템을 무력화시키기 위해서는

정상 발행된 페이지에서 token값을 탈취 한 이후 새로고침 되어 token 값이 교체되기 전에

위조된 페이지를 만들어 접근해야 하며 이를 위해서는 까다로운 기술이 필요하다고 한다.

 

 

 

 

 

 

3. 잘못된 해결방법

많은 문서들이 내가 처한 에러를 해결하기 위해서 CSRF token 기능을 제거하는 방법을 안내하고 있었다.

 

'POST' method 가 포함된 함수에서 csrf_exempt 데코레이터를 이용하여 토큰을 면제하거나

settings.py의 MIDDLEWARE 목록의 csrf 미들웨어를 주석 처리함으로써

에러 상황을 피하는 방법이 많이 공유되고 있었다.

 

그러나 필요에 의해 만들어진 보안 툴을 무력화시키는 방법이 옳지 않다고 느꼈다.

CSRF token의 막강한 보안 기능을 유지하면서도 에러를 해결할 수 있는 옳은 방법이 있을 게 분명했다.

 

해답은 공식 문서에 있었다.

 

 

 

 

 

 

4. 공식 문서의 안내를 따른 문제 해결

 

(캡쳐) Django 공식 문서 - CSRF_TRUSTED_ORIGINS 항목

문서 링크:

https://docs.djangoproject.com/en/4.0/ref/settings/#std-setting-CSRF_TRUSTED_ORIGINS

 

 

문서를 곰곰이 읽어본 결과

Django 서버는 'POST' request 가 들어왔을 때 method를 요청하는 호스트의 헤더의 Referer 속성을 를 확인하여

허가되지 않은 호스트의 경우 403 forbidden error를 발생시키고 있었다.

 

문서의 안내를 따라 정상적인 접근 목록 - allowlist를 설정하였다. 

이는 settings.py > CSRF_TRUSTED_ORIGINS 값으로 정상적인 접근 도메인 값을 명시하면 된다.

 

처음에는 "http://ip주소:포트번호" 를 allowlist로 주었고

도메인 구입, 연결 이후에는 도메인 값을 주었다.

 

CSRF_TRUSTED_ORIGINS = ["http://www.howdimt.xyz", "https://www.howdimt.xyz"]

 

만약 다른 호스트나 봇, 악성 애플리케이션 등의 비정상적인 방법으로 'POST' requst를 던져도 

위의 도메인으로 접근하지 않는다면 403 forbidden error 페이지를 보게 된다.

 

 

 

 

 

 

5.

 

로컬에서 문제없이 잘 돌아가던 애플리케이션이 실 서버에서는 많은 문제를 일으키고 있다.

 

문제를 해결한다는 관점에서는 똑같은 행위지만

실제 서비스를 위한 서버를 만들며 겪는 시행착오는

코딩을 공부할 때와는 사뭇 다른 느낌이다.

 

코드를 공부하고 작성하여 프로그램을 만드는 것도 재미있지만,

내가 만든 프로그램을 세상에 내보내는 과정에서도 큰 보람을 느낀다.

 

 

댓글