전에 올렸던 로그인 정보 글에서는, 토큰을 먼저 발급한 뒤 해당 토큰으로 서버에 다시 내 정보를 요청하는 방식으로 로그인을 구현했다.
이 방식은 더 빠르다는 장점이 있지만, 리다이렉션을 바로 시켜주기 때문에 헤더에 접근할 수 없어 리프레시 토큰으로 유저 정보를 다시 불러오고, 액세스 토큰도 재발급해야 하는 번거로움이 있다.
처음 시도했을 땐 나름 만족했지만, 볼수록 뭔가 어색하고 사용자 정보를 요청할 때 어려움이 생겨, 임시 토큰을 먼저 발급하고 이를 이용해 정식 토큰을 재발급받는 방식으로 리팩토링하기로 했다.
현재 코드

현재 코드에서는 엑세스 토큰과 리프레시 토큰을 모두 발급해주고 있다.
그러나 앞서 언급했듯이, 바로 리다이렉션이 이루어지기 때문에 헤더에는 접근할 수 없고 쿠키에만 접근할 수 있다.
그런 이유로 클라이언트가 엑세스 토큰을 저장하지 못해 엑세스 토큰도 다시 발급해줘야 하는 번거로움이 있다.
리팩토링

이렇게 임시 코드를 발급하게 되면 클라이언트는 임시로 발급된 1분짜리 엑세스 토큰으로 서버에 유저의 정보를 요청하면 된다.
또한 1분짜리 엑세스 토큰을 발급하고 발급한 토큰으로 정식 토큰을 재발급 받기 때문에 보안이 더 강화되었다.
(유효기간이 1분이라 엑세스 토큰이 탈취되어도 큰 문제가 없기 때문에 보안이 강화된 것이다)
더보기
/**
* 응답이 이미 커밋되었는지 확인
*/
private boolean isResponseCommitted(HttpServletResponse response) {
if (response.isCommitted()) {
log.info("응답이 이미 커밋되었습니다.");
return true;
}
return false;
}
/**
* 리다이렉트 url 생성
*/
private static String getRedirectUrl(String tempAccessToken) {
return UriComponentsBuilder
.fromUriString(REDIRECT_URI)
.queryParam("tempToken", tempAccessToken)
.build()
.toUriString();
}
/**
* 임시 액세스 토큰 생성
*/
private String generateTempAccessToken(ThisCodingAuthentication authentication) {
return tokenFactory.createTempAccessToken(authentication.getUser());
}
/**
* 리다이렉트 수행
*/
private void performRedirect(HttpServletRequest request, HttpServletResponse response, String redirectUrl) throws IOException {
this.clearAuthenticationAttributes(request, response);
this.getRedirectStrategy().sendRedirect(request, response, redirectUrl);
}
/**
* 인증 성공 후 불필요한 인증 관련 데이터를 정리.
*/
private void clearAuthenticationAttributes(HttpServletRequest request, HttpServletResponse response) {
super.clearAuthenticationAttributes(request);
servletUtils.removeCookie(request, response, "oauth2_auth_request");
}
/**
* Authentication 객체를 ThisCodingAuthentication으로 변환.
* - OAuth2 인증 객체인 경우 ThisCodingAuthentication으로 반환.
* - ThisCodingAuthentication 타입이 아닐 경우 예외 발생
*/
private ThisCodingAuthentication parseToThisCodingAuthentication(Authentication authentication) {
if (authentication instanceof OAuth2AuthenticationToken oAuthToken) {
if (oAuthToken.getPrincipal() instanceof ThisCodingAuthentication thisCodingAuth) {
return thisCodingAuth;
}
}
throw new InvalidAuthenticationException(ErrorCode.INVALID_AUTHENTICATION);
}
'개발' 카테고리의 다른 글
| Redis 캐싱 직렬화 실패 해결 과정 (LocalDateTime 대응) (2) | 2025.05.06 |
|---|---|
| 대형 Document 분리와 비지니스 로직 개선 중 발생한 성능이슈 : [MongoDB 성능 리팩토링] (1) | 2025.04.29 |
| ec2 환경에서 도커 스크립트 작성 (0) | 2025.03.21 |
| OAuth2.0 로그인 정보 (1) | 2025.03.20 |
| EC2 젠킨스 빌드 멈춤 상황 해결과정에서 깨달은 CI/CD툴 선택 (0) | 2025.03.12 |