네이버 소셜 로그인

hyo·2023년 5월 8일
0
post-thumbnail

네이버 소셜 로그인

시작하며

우유부단 프로젝트 리팩토링중에 네이버 소셜로그인을 구현하였다.
그전엔 카카오 / 구글만 소셜 로그인을 구현한 상태였었고,
방식이 조금 달랐다.

OAuth2.0의 방식은

이런 방식으로 진행이된다.

하지만 카카오 / 구글 소셜로그인을 구현할 때에는
약간 다르게 하였다.

카카오 / 구글 소셜 로그인 구현 방식

1. 카카오/구글 버튼을 만든다.
2. 버튼을 누르면 백엔드로 HTTP요청.
3. 백엔드는 인증서버(인가코드 주는 서버)로 요청하고 리다이렉트 URL을 프론트에 응답으로 넘겨줌.
4. 프론트에선 리다이렉트URL 페이지로 이동한 뒤 주소창에 code=''뒷부분인 인가코드를 받아서 다시 백엔드로 params에 넣어 전달.
5. 백엔드는 인가코드로 인증서버에 보내 엑세스토큰 요청.
6. 백엔드는 엑세스토큰을 받아 리소스서버에 유저정보를 요청.
7. 유저정보를 받은 백엔드는 프론트엔드로 유저정보 전달!

즉, 위처럼 카카오/구글 로그인 방식은 인가코드 요청까지 백엔드에서 이루어졌었다.


하지만 정석?적인 방식을 한번 해보고 싶어서 네이버소셜로그인의 인가코드 요청은 프론트에서 진행하고 싶어서 네이버 소셜 로그인에 대해 학습을 해보았다.

네이버 소셜로그인은 다른 소셜 로그인과 조금 다른이 있다고 한다.
인가코드 요청을 보낼때 파라미터로 state 라는 보안을 신경쓴 값을 보내야한다.

우선 네이버 Developers에 들어간다.
네이버 디벨로퍼 바로가기

위 링크로 들어가면 아래와 같은 화면이 나온다.

오픈 API 이용 신청 클릭!
애플리케이션 이름 등록!

제공 정보 선택(나중에 추가 삭제 가능)

환경추가 -> PC웹 선택

서비스 URL은 현재 개발 사이트인
http://localhost:3000 입력

Callback URL은 인가코드를 받을 redirect URL 이다.

나는 http://localhost:3000/auth/redirect 이런식으로 적어줬다.

그리고 등록!

등록하면 Client ID / Client Secret 이 발급된다.

ID와 Secret은 .env 파일에 저장 시켜둔다.


개발가이드를 보면 인가코드 요청은 이렇게 하라고 되어있다.

이제 네이버 로그인 버튼을 구현한 코드로 가보자.

//components/Auth
const Auth = () => {
  const naverState = Math.random(); // 고유한 state값
  const ClientID = process.env.NEXT_PUBLIC_CLIENT_ID;
  const RedirectUrl = process.env.NEXT_PUBLIC_REDIRECT_URL;
  
  return (
    <div>
      <NaverLogin onClick={() => {
         window.location.href = `https://nid.naver.com/oauth2.0/authorize?response_type=code&client_id=${ClientID}&state=${naverState}&redirect_uri=${RedirectUrl}`
      }}>
        <NaverSvg />
      </NaverLogin>
    </div>
  )

}

분명 GET/POST 요청으로 보내야 한다고 되어있어서 처음에는
axios.get(https://nid.naver~~~) 이런식으로 요청을 계속 보내보았지만 CORS 에러만 자꾸 떳다.
그래서 온갖 구글링을 하며 해결해보려 하였지만 실패하였고,
네이버디벨로퍼에 주소를 잘못적었나 싶어 확인도 몇번이고 해보았지만 실패하였다...
POSTMAN에 해봤지만 문제 없었다.
그러다 내가 요청을 보내는 params를 다 알맞게 넣은상태의 URL을 클릭하여 들어가보니

위처럼 원하던 로그인 동의 화면이 뜨는걸 확인할 수 있었다.

동의하기를 누르면 redirectURL로 이동이 되고 주소창엔 파라미터로
code(인가코드), state(고유상태값)이 같이 전달된다.

// pages/auth/naverredirect
import { useRouter } from 'next/router';
import Image from 'next/image';
import axios, { AxiosError, AxiosResponse } from 'axios';
import LocalStorage from '../../../constants/localstorage';
import { useEffect } from 'react';
import { NaverRedirectContainer } from './style';
import LoadingSpinner from '../../../assets/loadingspinner.gif';

const naverredirect = () => {
  const router = useRouter();
  const api = process.env.NEXT_PUBLIC_SERVER_URL;
  const nowUrl = router.query; // 주소창에 URL빼고 뒷부분을 꺼내올 수 있다.	

  console.log('nowUrl : ', nowUrl);

  useEffect(() => {
    axios
      .get(`${api}/naver/callback`, { // 백엔드로 인가코드, state 보내는 요청
        params: nowUrl, // params : {code: !asdada, state: 0.123123}
      })
      .then((res: AxiosResponse) => {
        const naver_access: any = res.headers.authorization?.split(' ')[1];
        const naver_refresh: any = res.headers.refreshtoken;
        LocalStorage.setItem('accesstoken', naver_access);
        router.push('/mypage'); // 백엔드에서의 작업이 다끝나고 완료됐다는 응답이 왔을때 프론트에서의 페이지 전환은 /mypage 로~
      })
      .catch((err: AxiosError) => {
        console.log('err : ', err.message);
      });
  }, [nowUrl]);

  return (
    <NaverRedirectContainer>
      <Image src={LoadingSpinner} alt="gif" /> // 인가코드를 받을동안 로딩창처럼 구현하기위해 로딩스피너 이용!
    </NaverRedirectContainer>
  );
};

export default naverredirect;

이렇게 네이버 소셜 로그인을 완성해 보았다.!!!!!!

profile
개발 재밌다

0개의 댓글