[Week2] Google Login
👻 Google Login
1. 구글 API 등록
구글 API 등록 링크 접속 후, 프로젝트 생성
그 후에 API 및 서비스로 이동 후, OAuth 동의 화면 선택!
프로젝트 이름 옆에 위치한, 앱 수정
버튼 클릭
범위 추가 또는 삭제
버튼을 클릭해서 필요한 정보를 불러오기 위해 범위 설정(!!중요한 부분!!)
페이지 하단의 저장 후 계속
버튼 클릭 후, 마지막 페이지에서 대시보드로 돌아가기
버튼 클릭하면 OAuth 동의 화면 설정 완료 🙂
그러면 이제 사용자 인증 정보 설정하러 고고!
사용자 인증 정보 만들기
버튼 클릭후, OAuth 클라이언트 ID 클릭
애플리케이션 유형은 웹 애플리케이션 선택! (프로젝트 유형에 맞게 선택하면 될 듯)
승인된 리디렉션 URI는 우리 프로젝트의 api에 맞게끔 주소 설정
나중에 배포하게 되면, 이 곳에 배포링크 추가해줘야 배포 후에도 구글 소셜 로그인 사용이 가능
만들기
버튼을 클릭하면, 클라이언트 ID와 클라이언트 보안 비밀번호가 발급되는데 잘 보관해두고, 유출되지 않게 조심!!
그리고 클라이언트 ID는 .env 파일이나 별도의 파일에 잘 복붙해놓기
2. client 설정
홈페이지에서 구글 로그인
버튼을 누르면, 아래 코드가 실행됨
React에서 .env 환경 변수 설정시,
환경 변수 앞에 꼭 REACT_APP 붙여줘야함!!!
const handleGoogle = () => {
const GOOGLE_LOGIN_URL = `https://accounts.google.com/o/oauth2/v2/auth?client_id=${process.env.REACT_APP_GOOGLE_CLIENT_ID}&redirect_uri=${process.env.REACT_APP_GOOGLE_REDIRECT_URI}&response_type=code&scope=https://www.googleapis.com/auth/userinfo.email https://www.googleapis.com/auth/userinfo.profile`;
window.location.assign(GOOGLE_LOGIN_URL);
};
우리 프로젝트에서는 구글 로그인시, 구글 이메일 정보와 구글 닉네임 정보가 필요했기에
아래 주소에서 scope 설정시 2개의 정보를 요청해야 했음
scope 부분만 별도로 기록을 해보자면,
1개 이상의 scope이 필요할시에는 api 주소 사이에 띄어쓰기를 해주면 잘 작동함
(이거 완전 꿀팁!)
scope=https://www.googleapis.com/auth/userinfo.email https://www.googleapis.com/auth/userinfo.profile`;
그리고 사용할 수 있는 scope 설정은 위의 API 설정에서
범위 추가 또는 삭제
를 통해 범위를 추가해줘야 추가해준 범위에 한해서 scope 설정이 가능 😎
Router.js 파일에 아래와 같이 라우트 추가
<Route path="/google/signin" element={<Google />} />
Google.js 파일 설정은 아래와 같이 😎
import { useState, useEffect } from 'react';
import axios from 'axios';
import { useDispatch } from 'react-redux';
import { socialSignIn, setSocialUser } from '../../redux/user/userSlice';
import { useNavigate } from 'react-router-dom';
const Google = () => {
const dispatch = useDispatch();
const navigate = useNavigate();
const [token, setToken] = useState();
const getGoogleCode = () => {
const googleCode = new URL(window.location.href).searchParams.get('code');
if (googleCode) {
getToken(googleCode);
}
};
const getToken = async (code) => {
try {
const data = await axios.post('/google/signin', {
code,
});
setToken(data.data.access_token);
} catch (e) {
console.log(e);
}
};
const getUserInfo = async (token) => {
try {
const data = await axios.get(`/google/user?accessToken=${token}`);
if (data) {
const { email, name, user_type: who } = data.data.giverInfo;
dispatch(socialSignIn());
dispatch(setSocialUser({ email, name, who }));
localStorage.setItem('token', token);
navigate('/');
}
} catch (e) {
console.log(e);
}
};
useEffect(() => getGoogleCode(), []);
useEffect(() => getUserInfo(token), [token]);
return (
<>
<div></div>
</>
);
};
export default Google;
3. server 설정
router 파일에 아래 내용 추가
router.post('/google/signin', user.googleLogin.getToken);
router.get('/google/user?', user.googleLogin.getUser);
googleLogin.js 파일 설정은 아래와 같이 😎
'use strict';
const axios = require('axios');
const jwt = require('jsonwebtoken');
const { giver } = require('../../models');
module.exports = {
getToken: async (req, res) => {
const code = req.body.code;
const url = `https://oauth2.googleapis.com/token?code=${code}&client_id=${process.env.GOOGLE_CLIENT_ID}&client_secret=${process.env.GOOGLE_CLIENT_SECRET}&redirect_uri=${process.env.GOOGLE_REDIRECT_URI}&grant_type=${process.env.GOOGLE_GRANT_TYPE}`;
try {
const token = await axios.post(url, {
headers: { 'content-type': 'application/x-www-form-urlencoded' },
});
const data = token.data;
res.send(data);
} catch (e) {
console.log(e);
}
},
getUser: async (req, res) => {
const token = req.query.accessToken;
const googleAPI = `https://www.googleapis.com/oauth2/v2/userinfo?access_token=${token}`;
try {
const googleUser = await axios.get(googleAPI, {
headers: {
authorization: `Bearer ${token}`,
},
});
const user = googleUser.data;
const giverFound = await giver.findOne({ where: { email: user.email } });
if (giverFound) {
const giverInfo = giverFound.dataValues;
delete giverInfo.password;
const accessToken = jwt.sign(giverInfo, process.env.ACCESS_SECRET);
res.send({ accessToken, giverInfo });
} else {
const newGiver = await giver.create({
email: user.email,
name: user.name === '' ? '' : user.name,
user_type: 1,
});
const { id, email, name, user_type } = newGiver.dataValues;
const giverInfo = { id, email, name, user_type };
const accessToken = jwt.sign(giverInfo, process.env.ACCESS_SECRET);
res.send({ accessToken, giverInfo });
}
} catch (e) {
console.log(e);
}
},
};
Author And Source
이 문제에 관하여([Week2] Google Login), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://velog.io/@tiatiahwang/Week2-google-login저자 귀속: 원작자 정보가 원작자 URL에 포함되어 있으며 저작권은 원작자 소유입니다.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)