today_is

[ spring 프로젝트 ] 네이버 로그인 api (2) 본문

project

[ spring 프로젝트 ] 네이버 로그인 api (2)

ye_rang 2024. 3. 23. 16:55

 

오늘은 슬픈(?) 소식이 있다

 

[ Hash 로 처리 ]
public MemberDTO login(MemberDTO dto) {
	dto.setUserpw(hashComponent.getHash(dto.getUserpw()));
	return mr.login(dto);
}


[ BcryptPasswordEncoder 로 처리 ]
public MemberDTO login(MemberDTO dto) {
	dto.setUserpw(bCryptPasswordEncoder.encode(dto.getUserpw()));
	return mr.login(dto);
}

 

네이버 로그인 api 를 지정하기 전에는

member 의 비밀번호를 HashComponent 로 처리했었는데

 

api 를 적용한 이후로는  spring-security 를 이용해서 

 BCryptPasswordEncoder 로 처리했었다.

 

 

 

 

 security 를 사용했던 이유는 비밀번호를 기존에 해왔던 Hash 와 다르게 설정해보고 싶은 것도 있었지만, 

interceptor 까지 같이 설정해두면 좋을 것 같다고 생각했기 때문이다.

 

 

내가 구현한 jsp 페이지

 

 

중요한건, 내가 구현한 페이지는 member와 myPage 에 국한되어있는데

 

다른 조원들이 작성한 페이지도 있고 

아직 구성원간 모든 구현이 완료되지 않았기 때문에

 

interceptor 를 지정하는 것이 어려웠다.

 

 

 

일단은 내가 구현한 페이지만 security-context 에 설정 해두었는데,

이것마저도 명확히 정의내리지 않아서,

PostMapping 할때마다

<input type="hidden" name="${_csrf.parameterName }" value="${_csrf.token }"> 해주는것이 헷갈리기 시작했다

 

 

 

interceptor는 기획과 동시에 사전에 미리 계획해두고

기능 구현이 끝날때 적용하는것이 가장 바람직한 것 같다.

 

 

 

팀원들간에 논의를 해본 결과,

당장은 interceptor 를 적용하는게 어렵다고 생각되며,

지금 이 상태에 머물러있는것보다는

다른 기능 구현에 초점을 맞추는게 좋을 것 같다는 조언을 듣게 되었다.

 

 

내가 슬프다고 표현한 이유는 

평소에는  Export 항상 해뒀는데 이번엔 까먹었기 때문이다.

다시 원래대로 되돌리는게 난항일 것으로 예상되어

상.당.히 마음이 답답했다

 

 

근데 갑자기 뇌가 번뜩이더니,  30분만에  해결완료했다

나 진짜 미친거 아니야? 

 

 

 

나도 은연중에 처음으로 되돌려야할 수 도 있겠다라는 생각을 했던 탓인지,

무엇을 바꿔야하는지 눈에 착착 보여서 정말 다행이다

 

 


 

드디어, 로그인 api 마무리 !!

 

해결하지 못했던 session 을 처리했다

 

 

( 해결 전 ) 로그인을 해도 header 에 c:if 가 처리안되어있음

 

 

 

해결한 후

 

 

 

문제점 

header 에 c:if로 세션 객체 login 이 있으면,

로그아웃 / 마이페이지 가 뜨고

 

login 이 없으면

로그인 / 회원가입이 뜨게 했는데

 

네이버로 로그인을 해도 세션 객체가 없는 것처럼 떴다.

 

 

 

해결점

네이버로 로그인한 상태로 회원가입 페이지를 가면,

네이버에서 받아온 정보가 뜨는 것으로 보아

세션에 login 이라는 이름으로 네이버를 통해 로그인된 계정의 정보를 저장해주면 될 것 같았다.

 

 

 

추가된 코드

: session.setAttribute("login", dtoById);       // 사용자 정보를 세션에 저장

@Controller
public class LoginController {
	
	@Autowired private NaverLogin naverLogin;
	@Autowired private MemberService memberService;


	
	@GetMapping("/oauth2_intergrated")
	public ModelAndView oauth2_intergrated(String code, String state, HttpSession session) throws IOException, InterruptedException, ExecutionException {
	    ModelAndView mav = new ModelAndView("oauth2");
	    
	    OauthLogin oauthLogin = null;
	    String provider = (String) session.getAttribute("provider");
	    
	    switch(provider) {
	        case "NAVER":    oauthLogin = naverLogin;    break;
	    }
	    // 2) 로그인 정보로 액세스 토큰을 받아온다
	    String accessToken = oauthLogin.getAccessToken(session, code, state);
	    System.out.println("accessToken : " + accessToken);
	    
	    // 3) 액세스 토큰을 이용하여 사용자의 프로필 정보를 받아온다
	    String apiResult = oauthLogin.getUserProfile(accessToken);
	    System.out.println("apiResult : " + apiResult);
	    
	    // 4) ObjectMapper 를 이용하여 자바 객체 타입으로 변환한다
	    OauthUserDTO oauthUser = oauthLogin.getOauthUser(apiResult);
	    oauthUser.setProvider(provider);
	    session.setAttribute("oauthUser", oauthUser); // 사용자 정보를 세션에 저장
	    
	    // 5) 인증 정보를 이용하여 DB에서 먼저 조회한다
	    MemberDTO dtoById = memberService.getMemberById(oauthUser);
	    MemberDTO dtoByEmail = memberService.getMemberByEmail(oauthUser);
	    
	    // 6) DB조회 여부에 따라, 회원가입, 기존 계정 연동, 로그인으로 분기하여 진행한다
	    if(dtoById == null) {       // 연동된 계정이 없음
	        // 이메일이 일치하는 계정이 있음 -> 계정 연동 제안
	        // 이메일이 일치하는 계정도 없음 -> 회원가입
	        mav.addObject("location", dtoByEmail != null ? "/updateId" : "/member/joinBasicMember");
	    } else {                    // 연동된 계정 정보가 있음 -> 사용자 세션 설정
	        session.setAttribute("login", dtoById); // 사용자 정보를 세션에 저장
	        mav.addObject("location", "/"); // 메인 페이지로 리다이렉트
	    }
	    return mav;
	}

 

 

이제 기능 구현은 슬슬 끝이 보인다

 

고생했다

 

마지막까지 힘내자 !!