RefreshToken을 이용하여 로그인 세션 유지하기

sdsdsrd·2020년 12월 2일
0

졸업프로젝트

목록 보기
15/15

JWT

Spring boot 로 구현한 Back-End에서 JWT를 사용하여 로그인 시 Access Token과 Refresh Token을 response로 보내준다. 보통 유효기간은 Access Token은 1시간, Refresh Token은 2주 정도이다.

최초 로그인 시 서버가 보내준 Access Token을 쿠키에 저장하고, Refresh Token은 더 안전한 곳에 저장한다. 이번 프로젝트에서는 Refresh Token을 localStorage에 저장하였다.

클라이언트는 모든 request 전송 전에 갖고 있는 Acess Token의 유효기간을 체크한다. 현재로부터 30초 이내 만료인 경우 Refresh Token을 꺼내어 다시 서버로 재전송하고, 서버로부터 다시 Access Token과 Refresh Token을 받는다. 새로 받은 토큰들을 다시 저장 후에 새로운 Access Token을 헤더에 담아 원래 보내려던 request를 보낸다.

위에서 Refresh Token도 유효기간이 만료되어 403 Forbidden Error가 난 경우에는 재로그인하도록 한다.


jwt-decode 설치

Access Token의 만료 시점을 체크하여 현재로부터 몇 초 이내 만료인지 구할 수 있도록 jwt-decode를 이용하여 토큰을 해독한다.

npm install jwt-decode

interceptor에서 유효기간 체크

jwt-decode를 이용하여 expiry를 구한 후 현재 시간을 빼 남은 시간을 구한다.

import jwt_decode from 'jwt-decode';

export function setInterceptors(instance) {
  instance.interceptors.request.use(
    async function(config) {
      // Do something before request is sent
      var decoded = jwt_decode(store.state.accessToken);
      let now = new Date();
      let expiry = decoded.exp - Number(now.getTime().toString().substr(0, 10));
      
...

RefreshTokenRequest

expiry가 30 미만인 경우 RefreshTokenRequest를 보내어 새로운 Acceess Token과 Refresh Token을 받는다.
여기서 error가 나는 경우는 Refresh Token도 만료되어 403 Forbidden을 받은 경우로, store의 isLogin을 False로 바꾸어 재로그인시킨다.

if(expiry < 30) {
  try {
    const userData = {
      header: {
        name: 'RefreshTokensRequest',
        userId: getUserFromCookie(),
      },
      payload: {
        userId: getUserFromCookie(),
        refreshToken: store.state.refreshToken,
      },
    };
    const { data } = await getRefreshToken(userData);
    store.state.accessToken = data.payload.accessToken;
    store.state.refreshToken = data.payload.refreshToken;

    saveAuthToCookie(data.payload.accessToken);
    saveRefreshTokenToCookie(data.payload.refreshToken);
  } catch (error) {
    deleteCookie('auth');
    deleteCookie('refresh_token');
    deleteCookie('user');
    deleteCookie('username');
    store.state.userId = '';
    store.getters.isLogin = false;
  }
}
config.headers.Authorization = store.state.accessToken;
return config;

1개의 댓글

comment-user-thumbnail
2021년 3월 25일

선생님 전체코드를 보고싶은데 ㅠㅠ 볼 수 있을가요??ㅠㅠㅠㅠㅠ

답글 달기