문의 시, 사용하시는 개발환경과 디벨로퍼스 앱ID를 알려주세요.
인텔리제이에서 oauth와 jwt를 사용해서 카카오 로그인을 구현하는데 로그아웃을 할 때 카카오 계정과 함께 로그아웃 페이지가 뜨지 않고 바로 로그아웃이 됩니다. 해결하고 싶은데 이유가 뭔지를 모르겠습니다.
이전 오류에서는 KOE207가 발생했지만 파라미터를 수정하지 않고 다른 부분을 수정하니 KOE207오류가 발생하지 않고 토큰이 사라지며 로그아웃만 됩니다.
코드들
- CustomLogoutHanlder.java
package com.example.app.config.auth.logoutHandler;
import com.example.app.config.auth.PrincipalDetails;
import com.example.app.config.auth.jwt.JwtProperties;
import com.example.app.config.auth.jwt.JwtTokenProvider;
import groovyjarjarpicocli.CommandLine;
import jakarta.servlet.http.Cookie;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import jakarta.servlet.http.HttpSession;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.http.*;
import org.springframework.http.client.HttpComponentsClientHttpRequestFactory;
import org.springframework.security.core.Authentication;
import org.springframework.security.web.authentication.logout.LogoutHandler;
import org.springframework.stereotype.Component;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.web.client.HttpClientErrorException;
import org.springframework.web.client.RestTemplate;
import javax.swing.*;
import java.util.Arrays;
@Component
public class CustomLogoutHandler implements LogoutHandler {
@Autowired
private JwtTokenProvider jwtTokenProvider;
//client-id 추가
@Value("${kakao.rest-api}")
private String KAKAO_CLIENT_ID;
@Override
public void logout(HttpServletRequest request, HttpServletResponse response, Authentication auth) {
//Authentication 객체에 접근
Authentication authentication = null;
String token = Arrays.stream(request.getCookies())
.filter(cookie->cookie.getName().equals(JwtProperties.COOKIE_NAME)).findFirst()
.map(cookie -> cookie.getValue())
.orElse(null);
if(token!=null) {
authentication = jwtTokenProvider.getAuthentication(token);
}
System.out.println("CustomLogoutHandler's logout()..");
System.out.println("Authentication.......... : " + authentication);
if (authentication != null && authentication.getPrincipal() instanceof PrincipalDetails) {
HttpSession session = request.getSession(false);
if (session != null)
session.invalidate();
}
//JWT 토큰 삭제
response.addCookie(createExpiredCookie());
//kakao Logout
assert authentication != null;
PrincipalDetails principalDetails = (PrincipalDetails) authentication.getPrincipal();
System.out.println("principalDetails!!!!!!!!!!"+principalDetails);
String accessToken = principalDetails.getAccessToken();
String snsType = principalDetails.getUserDto().getSnsType();
System.out.println("SNSTYPE : "+snsType + ", ACCESSTOKEN : " + accessToken);
String url = "https://kapi.kakao.com/v1/user/logout";
// String url = "https://kauth.kakao.com/oauth/logout";
HttpHeaders headers = new HttpHeaders();
headers.add("Authorization", "Bearer "+accessToken);
MultiValueMap<String,String> params = new LinkedMultiValueMap<>();
HttpEntity<MultiValueMap<String,String>> entity = new HttpEntity(params,headers);
RestTemplate rt = new RestTemplate();
try {
ResponseEntity<String> resp = rt.exchange(url, HttpMethod.POST, entity, String.class);
if(resp.getStatusCode() == HttpStatus.OK){
System.out.println("Successfully logout from kakao");
}else{
System.out.println("Failed to logout from kakao. Status code : "+resp.getStatusCode());
}
}catch (HttpClientErrorException ex){
System.out.println("Failed to logout from kakao. Error : "+ex.getMessage());
}catch (Exception ex){
System.out.println("An error occurred while logout from kakao. Error : "+ ex.getMessage());
}
}
private Cookie createExpiredCookie(){
Cookie cookie = new Cookie(JwtProperties.COOKIE_NAME, null);
cookie.setMaxAge(0);
cookie.setPath("/");
return cookie;
}
}
- CustomLogoutSuccessHandler.java
package com.example.app.config.auth.logoutHandler;
import com.example.app.config.auth.PrincipalDetails;
import jakarta.servlet.ServletException;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.PropertySource;
import org.springframework.security.core.Authentication;
import org.springframework.security.web.authentication.logout.LogoutSuccessHandler;
import org.springframework.stereotype.Component;
import java.io.IOException;
import java.net.URLEncoder;
@Component
//@PropertySource("classpath:application-SECRET-KEY.properties")
public class CustomLogoutSuccessHandler implements LogoutSuccessHandler {
@Value("${kakao.rest-api}")
private String KAKAO_CLIENT_ID;
@Value("${spring.security.oauth2.client.kakao.logout.redirect.uri}")
// private String KAKAO_LOGOUT_REDIRECT_URI="http://localhost:8080/th/member/login";
private String KAKAO_LOGOUT_REDIRECT_URI;
@Override
public void onLogoutSuccess(HttpServletRequest request, HttpServletResponse response, Authentication authentication) throws IOException, ServletException {
if(authentication != null) {
PrincipalDetails principalDetails = (PrincipalDetails) authentication.getPrincipal();
String snsType = principalDetails.getUserDto().getSnsType();
if (snsType != null && "kakao".equals(snsType)) {
response.sendRedirect("https://kauth.kakao.com/oauth/logout?client_id=" + KAKAO_CLIENT_ID + "&logout_redirect_uri=" + KAKAO_LOGOUT_REDIRECT_URI);
return;
}
}
System.out.println("CustomLogoutSuccessHandler's onLogoutSuccess()");
response.sendRedirect("/");
}
}
이게 현재 로그아웃 관련 코드들입니다.