세션 인증 (Session Authentication)

Session-based authentication is a stateful authentication mechanism where the user's session state is stored on the server.

— OWASP 인증 표준 아키텍처 개요

토큰 인증(JWT)이 유행하자 퇴물 취급을 받았으나, 정작 JWT의 로그아웃 불가 및 토큰 탈취 이슈에 데인 시니어들이 '역시 구관이 명관'이라며 다시 조용히 복귀시키는 정통의 명작. 결국 서버 측 세션 저장소로 Redis를 무조건 깔고 가야 해서 백엔드 유지보수 서버 목록에 인프라 하나가 추가된다.(...)

1. 개요

사용자의 로그인 자격 증명이 성공하면 서버가 그 유저의 고유한 세션(Session) 정보를 서버 측 저장소에 안전하게 기록하고, 클라이언트에게는 이 세션을 가리키는 고유 열쇠인 세션 ID(Session ID)만을 발급해 주는 전통적인 상태 유지(Stateful) 인증 방식. 클라이언트는 발급받은 세션 ID를 주로 쿠키에 담아 보관하며, 요청을 보낼 때마다 이 열쇠를 서버에 제출해 안전하게 신원 보증을 받는다.

2. Stateful 인증의 완벽한 보안 통제력

세션 인증의 최대 장점은 바로 '서버가 모든 통제권을 쥐고 있다'는 점이다. 사용자가 로그아웃을 하거나, 관리자가 특정 악성 유저의 세션을 강제로 파괴(Invalidate)하고자 할 때, 서버는 자기가 쥐고 있는 세션 저장소에서 해당 세션 정보만 날려버리면 끝이다.1 클라이언트가 훔친 세션 ID로 아무리 문을 두드려도 서버 저장소에 열쇠가 존재하지 않으므로 즉시 접근이 차단된다. 이는 클라이언트에 정보와 만료 통제권이 분산되는 토큰(JWT) 기반 인증 방식에 비해 압도적인 보안 및 통제 유연성을 보장한다.

3. 스케일아웃과 세션 불일치(Session Inconsistency) 재앙

하지만 세션 인증은 서버를 수평 확장(Scale-out)하는 순간 진정한 지옥의 문이 열린다. 유저가 1번 서버에서 로그인하여 세션이 생성되었는데, 다음 요청이 로드 밸런서에 의해 2번 서버로 전달되면, 2번 서버에는 해당 세션 정보가 없으므로 유저는 뜬금없이 로그인 창으로 튕겨 나간다. 이를 '세션 불일치' 문제라 한다. 이를 해결하기 위해 사용자의 요청을 최초 로그인한 서버로만 계속 보내주는 Sticky Session, 서버끼리 세션 데이터를 동기화하는 Session Clustering 등의 기법을 동원하지만, 이는 아키텍처 복잡도를 극대화한다. 현대 백엔드에서는 이를 극복하고자 세션을 개별 웹 서버 메모리가 아닌, Redis 같은 초고속 외부 캐시/인 메모리 데이터베이스에 공유 세션 저장소(Shared Session Storage)로 이식하여 평화를 되찾는 경우가 대부분이다.

4. 관련 밈 및 드립

4.1. 새로고침을 했더니 로그아웃이 됐어요

세션 저장 장치가 꼬이거나, 서버가 무중단 배포를 진행하며 메모리를 리셋하는 순간 유저들이 집단으로 겪는 현상. 로컬 메모리에 세션을 담는 멍청한 설정을 해 두면, 코드를 수정하고 서버를 빌드할 때마다 개발자 자신을 포함한 모든 동시 접속 유저들의 세션이 사정없이 날아간다. 퇴근 전 테스트 도중 이 현상을 겪고 등골이 오싹해져 황급히 Redis 서버의 상태를 체크하는 백엔드 개발자들의 모습이 흔히 목격된다.

4.2. JWT는 만병통치약이 아니다

세션 아키텍처의 스케일아웃 단점을 해결하겠다고 앞뒤 안 가리고 JWT(JSON Web Token)를 무작정 도입했다가 피를 흘리는 개발자들의 하소연. 토큰 탈취나 강제 로그아웃 구현의 한계 때문에 결국 블랙리스트를 저장할 초고속 세션 저장소를 DB에 다시 구축하게 되고, '이럴 거면 그냥 처음부터 세션 인증 쓸걸 그랬다'라며 제자리로 돌아오는 순회 밈이다.(...)

5. 여담

  • 세션 ID의 난수 정합성: 세션 ID는 해커가 대충 때려 맞추거나 예측할 수 없도록 암호학적으로 안전한 난수 생성기(CSPRNG)를 통해 극도로 무작위적이고 긴 문자열로 생성되어야 한다. 만약 개발자가 세션 ID를 단순히 Auto Increment ID(1, 2, 3...) 같은 규칙으로 발행했다가는 해커가 주소창 숫자만 올려가며 타인 계정으로 프리패스하는 대참사가 터진다.
  • 세션 하이재킹(Session Hijacking): 세션 인증의 아킬레스건은 클라이언트가 들고 있는 세션 ID 자체를 훔쳐오는 세션 하이재킹 공격이다. 해커가 피해자의 브라우저에서 쿠키 속 세션 ID만 복사해서 자기 브라우저에 이식하면 아무런 패스워드 입력 없이 완전한 본인으로 로그인할 수 있다. 이를 막기 위해 HTTPS 적용과 함께 Secure, HttpOnly 속성을 쿠키에 입혀 사전에 락을 걸어야 한다.
  • 세션 타임아웃의 미학: 무한히 살아있는 세션은 보안상 재앙이므로 보통 30분 내외의 세션 유효시간(Session Timeout)을 부여한다. 이때 유저가 웹서핑을 계속 클릭할 때마다 서버가 유효 시간을 자동으로 30분씩 갱신해 주어 로그인이 풀리지 않게 돕는 스마트한 유지 기법이 '슬라이딩 윈도우 익스파이어(Sliding Window Expiry)'다.

6. 관련 문서

각주

  1. 세션 정보에는 유저 식별자뿐만 아니라 가벼운 장바구니 상태, 권한 목록 등 서버 측에서 자주 꺼내 보아야 하는 다양한 유저 임시 상태들을 안전하게 마음껏 적재해 둘 수 있다.