Skip to content

[Fix] Access Token 만료 상태에서 로그아웃하면 Refresh Token이 남는 문제 #229

Open

Description

@seoyeon83

📄 Description

관리자 로그아웃(POST /api/v1/auth/admin/logout)과 사용자 로그아웃(POST /api/v1/auth/user/logout)은 Access Token에서 꺼낸 계정 id로 refresh_token 행을 지우고, Refresh Token 쿠키는 읽지 않는다(AuthService.adminLogout, AuthService.userLogout). 2026-05-18 AuthService 통합 리팩터링부터 이렇게 동작한다.

그래서 Access Token(15분)이 만료된 채 로그아웃을 요청하면 JwtAuthenticationFilter가 401 EXPIRED_TOKEN으로 요청을 끝낸다. 이때 DB의 Refresh Token 행도 지워지지 않고, 브라우저의 Refresh Token 쿠키도 만료되지 않는다.

사용자 프론트엔드는 로그아웃 API가 실패해도 로컬의 Access Token을 지워 화면에서는 로그아웃된 것처럼 보인다. 하지만 Refresh Token 쿠키는 최대 7일 남아 있어서, 같은 브라우저에서 토큰 갱신이 일어나면 다시 로그인된 상태가 된다. 공용 PC에서 문제가 될 수 있다.

로그아웃 경로는 인증이 필요한 경로라서(SecurityConfig), 백엔드에서 쿠키를 읽도록 바꾸는 것만으로는 해결되지 않는다. 만료된 Authorization 헤더가 붙어 있으면 필터가 먼저 401을 주기 때문이다. 아래 방법 중 하나를 정해서 고친다.

  • 방법 A: 로그아웃 경로를 공개 경로로 바꾸고, Refresh Token 쿠키로 계정을 찾아 행을 지운다. 쿠키가 없거나 맞지 않아도 쿠키를 만료시키고 200을 준다. 프론트엔드는 로그아웃 요청에 Authorization 헤더를 붙이지 않는다(토큰 갱신 요청과 같은 방식).
  • 방법 B: 지금 방식을 유지하고, 프론트엔드가 로그아웃이 401로 실패하면 토큰을 갱신한 뒤 다시 로그아웃을 요청한다. 백엔드 수정은 없다.

노션 기능 명세서의 관리자 로그아웃 의사결정 이력(2026-04-15)은 "로그아웃 요청 시 Refresh Token을 명시적으로 검증"이었고, 방법 A가 이 결정에 가깝다.

✅ TO-DO

  • 방법 A, B 중 하나를 정한다 (프론트엔드 담당과 협의)
  • (방법 A) 관리자·사용자 로그아웃을 Refresh Token 쿠키 기준으로 변경하고 공개 경로로 옮긴다
  • (방법 A) Access Token이 만료된 상태에서 로그아웃해도 행이 지워지고 쿠키가 만료되는지 테스트 추가
  • (방법 A) 프론트엔드에 로그아웃 요청에서 Authorization 헤더를 빼 달라고 요청한다
  • backend-docs의 AUTH-03, AUTH-06 기능 명세서·테스트 명세서를 바뀐 동작에 맞게 고친다

⚙️ etc

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Labels

auth인증 (관리자 로그인, 사용자 OAuth, 토큰)🐛 FIX[Fix] 버그 수정

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions