일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | |||||
3 | 4 | 5 | 6 | 7 | 8 | 9 |
10 | 11 | 12 | 13 | 14 | 15 | 16 |
17 | 18 | 19 | 20 | 21 | 22 | 23 |
24 | 25 | 26 | 27 | 28 | 29 | 30 |
- 리액트
- REACT
- 파이썬 for in
- 파이썬 slice
- 타입스크립트
- 리액트 훅
- 코딩테스트
- 한글 공부 사이트
- 타입스크립트 props
- tanstack query
- typeScript
- 파이썬 딕셔너리
- 내일배움캠프
- 내배캠 프로젝트
- 프로그래머스
- 파이썬 list
- 내일배움캠프 프로젝트
- 파이썬 for
- JavaScript
- 타입스크립트 리액트
- js
- 리액트 프로젝트
- 내일배움캠프 최종 프로젝트
- 자바스크립트
- Next 팀 프로젝트
- 파이썬 enumerate
- React Hooks
- useState
- 파이썬 반복문
- 파이썬 replace
- Today
- Total
sohyeon kim
[SW] 세션 기반 인증 & 토큰 기반 인증 본문
💡 세션과 토큰에 대해 알아보자.
리퀘스트를 보낸 유저를 확인하는 방식
💡 세션 : 서버가 저장하는 사이트 방문자들에 대한 기록
- 세션 DB 필요 (유저가 늘수록 커짐)
세션 기반 인증 과정
- 누군가 서버에 첫 리퀘스트를 보내면 서버는 그 방문에 대한 데이터를 세션에 저장(id, ip 주소, 브라우저 종류 등)
- 리스폰스의 Set-Cookie 에 새로 만든 세션의 아이디를 추가
- 클라이언트에게 전달
- 다음에 같은 클라이언트가 리퀘스트를 보내면 항상 쿠키로 세션 아이디가 같이 보내짐
➡️ 방문자가 누군지 확인 가능, 세션 아이디가 저장되어있지 않다면 첫 방문자 - 세션 아이디가 확인된 유저가 로그인을 한다면 user_id 도 세션에 저장 (로그인 되어 있지 않은 유저는 null 저장)
** 구현에 따라 방문자가 첫 리퀘스트를 보냈을 때 클라이언트에 세션 아이디를 보내도 되고,
** 로그인 했을 때 처음 보내도 된다.
❗️ (로그인 시) 한 번 저장된 세션을 영원히 사용할 수 있는건 아니다.
특정 시간이 지나거나 유저가 로그아웃을 하면 서버는 해당 세션이나 로그인 유저를 만료 처리한다.
➡️ 다시 로그인 필요
💡 인증 토큰 : 유저에 대한 정보를 암호화한 문자열
- 서버에 보내 유저가 특정 기능이나 콘텐츠에 접근할 수 있게 해주기 때문에
(Access) 접근 토큰이라고도 부른다. - 세션처럼 매번 저장 및 확인하지 않고, 토큰 자체를 해석해 사용한다.
토큰 기반 인증 과정
- 유저가 클라이언트의 로그인 리퀘스트를 통해 이메일과 비밀번호를 보냈고,
서버는 이 정보가 유효하다는 걸 확인한 상태 - 서버에서 토큰 생성 (유저 아이디와 유효 기간에 비밀키를 더해 암호화)
- 이제 리스폰스 바디에 토큰을 저장해 클라이언트에게 전달 (쿠키도 가능하긴 함)
- 토큰을 돌려받을 땐 Authorization 헤더로 받는다. (쿠키도 가능하긴 함)
- 토큰을 돌려받은 서버는 비밀키를 사용해 다시 해석해 내용을 보고 유저를 특정짓는다.
Authorization: Bearer ... ➡️ 이 Bearer 는 서버에게 인증 정보의 종류를 알려주기 위함으로 헤더 인증 시 필수
❗️ 토큰을 갖고있는 것만으로 만료 시간까지 항상 로그인 상태 유지 가능 (따로 또 저장, 확인 불필요)
로그아웃을 하고 싶다면 클라이언트에서 직접 저장한 토큰을 삭제하면 된다.
💡 Refresh 토큰 : 토큰의 안전 장치
토큰의 만료 기간이 길다면 누군가 토큰을 훔쳤을 때 더 오래 권한을 갖게 할 수 있다.
하지만 짧다면 로그인 인증을 너무 자주 해야 해서 불편하고, 인증을 많이 보내니 위험할 수 있다.
➡️ 이를 위해 Refresh 토큰을 함께 사용하는 방법이 있다.
- Access 토큰이 만료됐을 때, 이메일 비밀번호를 사용하지 않고 토큰을 새로 발급받는데 사용하는 토큰
- 유저가 처음 로그인을 했다면, 서버는 Access, Refresh 두 토큰을 보내준다.
- Access 토큰이 만료되어, 리퀘스트 인증을 할 수 없는 상태라면
클라이언트는 토큰을 새로 발급받을 URL 에 GET 리퀘스트를 보낸다, 이 때 Refresh 토큰을 함께 보낸다. - 서버는 Refresh 토큰이 유효한 걸 확인하고, 새 Access 토큰을 발급해 리스폰스로 클라이언트에게 보낸다.
일반적으로 Refresh 토큰이 Access 토큰보다 만료기간이 더 길다. (e.g. Access 가 10분이라면 Refresh 는 24시간)
Aceess 토큰의 기간이 짧기 때문에 서버로 토큰을 보낼 때,
누군가 이 정보를 가로채도 10분까지만 사용이 가능하니 좀 더 안전해진다.
➡️ Refresh 토큰은 새 토큰을 받을 때만 보내면 되기 때문에 훨씬 적게 보내도 되고 그만큼 위험 부담이 적어진다.
💡 JWT : JSON Web Token, JSON 형식의 데이터를 문자열로 인코딩한 토큰
점을 기준으로 총 세 부분으로 나뉘어진다
🟡 Header : 토큰 자체에 대한 데이터 저장
- 단순히 인코딩된 정보기 때문에 누구나 해석할 수 있으므로 비밀번호 같은 민감한 내용은 넣으면 안된다.
(PayLoad 도 마찬가지)
🟢 PayLoad : 토큰이 실질적으로 저장하려는 정보
- 저장하고 싶은 데이터 종류의 제한 없음
- 최대한 짧게, 짧을수록 좋음
- 공식 이름 최대한 활용 (exp, iat, jti 등)
🔴 Signature : 토큰을 믿을 수 있는지 확인하기 위한 데이터 저장
- Header 와 PayLoad의 인코딩 값, 서버가 가지고 있는 비밀번호인 시크릿 키가 합쳐진 정보
- 이 시그니처가 같다면 유효한 토큰
- 누군가 헤더, 페이로드 내용을 임의로 바꿨거나 다른 키를 사용했다면 시그니처 내용이 다를 것
➡️ 토큰을 훔쳐 유저 행세를 할 순 있지만, 토큰 내용을 변경해 조작할 순 없다.
✴️ 세션 기반 인증 & 토큰 기반 인증
효율성 : 토큰 기반 인증
세션을 사용하면 서버는 항상 로그인 세션 정보를 저장하고, 매 리퀘스트마다 유저와 그 정보를 비교해야한다.
이를 위해선 용량과 시간이 들고, 로그인한 유저가 엄청 많거나 특정 시간에 몰리게 된다면 리퀘스트 처리 속도가 느려질 수 있다.
반면, 토큰은 어딘가 저장한 데이터와 비교하는게 아니라 토큰 자체를 해석하기만 하면 되기때문에 더 효율적이다.
유연성 : 토큰 기반 인증
토큰을 발행하는 방법이 같고, 시크릿 키가 있다면 발행을 한 곳과 확인을 한 곳이 달라도 된다.
예를 들어 같은 유저 데이터베이스를 사용하는 여러 서비스가 있을 때, 같은 방식과 키로 토큰을 발행한다면
어떤 서비스에서 제공한 토큰을 가지고 다른 서비스에서도 인증을 받을 수 있게 된다.
RESTful API : 토큰 기반 인증
세션 정보와 같이 서버가 '상태' 정보(유저의 로그인 여부)를 저장하고 있을 때, stateful 하다고 표현한다.
REST 에 부합하기 위해선 서버가 상태 정보를 저장하지 않는, stateless 한 특성이 있어야 한다.
서버는 클라이언트에서 보내는 정보만으로 충분히 상태를 파악할 수 있어야 하는 것.
이 기준에서 RESTful 한 API 서버를 만들고 있다면 토큰 기반 인증이 더 어울린다.
무효화 : 세션 기반 인증
세션의 장점 중 하나는 서버에서 세션 데이터를 관리하기 때문에 특정 세션을 손쉽게 무효화할 수 있다는 점이다.
하지만 토큰은 따로 서버가 정보를 저장하지 않기 때문에 특정 토큰을 무시하는게 복잡하다. (중복 로그인 방지 불가)
예를 들어 금융 서비스에서 누군가 유저 토큰을 가로챘는데 이걸 바로 무효화할 수 없다면 큰 문제로 이어질 수 있다.
이중 비밀번호나, OTP 등 이를 방지하기 위한 방법들이 있지만, 세션 인증으로 좀 더 쉬운 안전장치를 사용할 수 있다.
e.g. 수상한 유저 강제 로그아웃, 인스타그램에서 로그인된 기기 확인, 넷플릭스에서 로그인된 계정 수 확인
❗️ 세션을 보완하는 느낌으로 JWT 를 사용하지만 사이트가 커진다면 안전성 문제로 다시 세션을 사용해야 할 수 있다.
🔗 https://youtu.be/tosLBcAX1vk?si=CTuIlUOWUQc5Cerr
'Software' 카테고리의 다른 글
[SW] 웹 최적화, 프론트 성능 개선에 대해 (6) | 2024.09.06 |
---|---|
[SW] 쿠키 & 웹 스토리지, 로컬 스토리지, 세션 스토리지 (1) | 2024.09.05 |
[SW]REST API : URI & HTTP 요청 메서드 GET, POST.. (0) | 2024.02.19 |
[SW] HTTP 상태 코드 정리 (0) | 2024.02.16 |
[SW] Library & Framework 라이브러리와 프레임워크 (0) | 2024.01.02 |