JWT의 이해
JWT는 JSON Web Token의 약자로, 데이터가 JSON으로 이루어져 있는 토큰을 의미합니다. 두 개체가 서로 안전하게 정보를 주고받을 수 있도록 웹 표준으로 정의된 기술입니다.
세션 기반 인증과 토큰 기반 인증의 차이
세션 기반 인증 시스템
서버가 사용자가 로그인 중임을 기억하고 있다.
사용자 로그인
—> 서버는 세션 저장소에 사용자의 정보를 조회 후, 세션 id 발급
—> 발급된 id는 주로 브라우저의 쿠키에 저장
—> 그 다음에 사용자가 다른 요청을 보낼 때마다 서버는 세션 저장소에서 세션을 조회한 후, 로그인 여부를 결정하여 작업을 처리하고 응답
단점
-
서버를 확장하기가 번거로워질 수 있다는 점
-
만약 서버의 인스턴스가 여러 개가 된다면, 모든 서버끼리 같은 세션을 공유해야 하므로 세션 전용 데이터베이스를 만들어야 할 뿐 아니라 신경 써야 할 것이 많아짐
토큰 기반 인증 시스템
토근은 로그인 이후 서버가 만들어 주는 문자열입니다.
해당 문자열 안에는 사용자의 로그인 정보가 들어 있고, 해당 정보가 서버에서 발급되었음을 증명하는 서명이 들어 있습니다.
서명 데이터는 해싱 알고리즘을 통해 만들어지고, 주로 HMAC SHA256 혹은 RSA SHA256 알고리즘이 사용됩니다.
사용자 로그인
—> 서버에서 사용자에게 해당 사용자의 정보를 지니고 있는 토큰을 발급
—> 사용자가 다른 요청 보낼 때, 발급받은 토큰과 함께 요청
—> 서버는 해당 토큰이 유효한지 검사하고, 결과에 따라 작업을 처리하고 응답
장점
-
서버에서 사용자 로그인 정보를 기억하기 위해 사용하는 리소스가 적다.
-
사용자 쪽에서 로그인 상태를 지닌 토큰을 가지고 있으므로 서버의 확장성이 매우 높다.
-
서버의 인스턴스가 여러 개로 늘어나도 서버끼리 사용자의 로그인 상태를 공유할 필요가 없음
JWT 토큰 발급하기
1) jsonwebtoken 모듈 설치
$ yarn add jsonwebtoken
;
2) 비밀키 설정하기
-
.env 파일에 비밀키 입력
-
macOS/리눅스에선
$ openssl rand -hex 64
명령어를 실행하면 랜덤 문자열을 만들어 준다. -
.env 파일에 JWT_SECRET 값으로 설정
-
절대 외부에 공개 되면 안됨!!
-
JWT 토큰 사용하기
1) 브라우저의 localStorage 혹은 sessionStorage
브라우저의 localStorage 혹은 sessionStorage에 토큰을 담으면 사용하기가 매우 편리하고 구현하기도 쉽습니다.
하지만 누군가가 페이지에 악성 스크립트를 삽입한다면 쉽게 토큰을 탈취할 수 있습니다. - XSS(Cross Site Scripting)
2) 브라우저의 쿠키
쿠키도 XSS 문제가 발생할 수 있지만, httpOnly라는 속성을 활성화하면 자바스크립트를 통해 쿠키를 조회할 수 없으므로 악성 스크립트로부터 안전합니다.
그 대신 CSRF(Cross Site Request Forgery)라는 공격에 취약해질 수 있습니다. 이 공격은 사용자가 서버로 요청할 때 무조건 토큰이 함께 전달되는 점을 이용해서, 사용자가 모르게 원하지 않는 API 요청을 하게 만듭니다. 그래서 사용자가 자신도 모르는 상황에서 어떠한 글을 작성하거나 삭제하거나, 또는 탈퇴하게 만들 수도 있습니다.
단, CSRF는 CSRF 토큰 사용 및 Referer 검증 등의 방식으로 제대로 막을 수 있는 반면, XSS는 보안장치를 적용해 놓아도 개발자가 놓칠 수 있는 다양한 취약점을 통해 공격을 받을 수 있습니다.
토큰 발급
1) jsonwebtoken 모듈 설치
$ yarn add jsonwebtoken
;
2) 비밀키 설정하기
-
.env 파일에 비밀키 입력
-
macOS/리눅스에선
$ openssl rand -hex 64
명령어를 실행하면 랜덤 문자열을 만들어 준다. -
.env 파일에 JWT_SECRET 값으로 설정
-
절대 외부에 공개 되면 안됨!!
-
출처
- 김민준, 리액트를 다루는 기술(개정판)