2022. 9. 4. 23:23ㆍFront-end/React
이번에 백엔드 개발자와 협업한 프로젝트에서 JWT 방식 로그인을 사용했는데, 간단하게 정리해볼까 한다.
JWT 토큰 방식 로그인의 순서는 다음과 같다.
- 클라이언트에서 서버에 로그인 요청을 보낸다.
- 요청 데이터에 문제가 없다면 서버는 새로운 토큰을 발급한다.
- 발급한 토큰을 응답 헤더에 담아 클라이언트로 보낸다.
- 클라이언트는 응답 헤더에서 토큰을 꺼내 웹 스토리지에 저장한다.
이후 사용자 인증이 필요한 요청 시 요청 헤더에 저장한 토큰을 담아서 요청하면 된다.
다음은 코드와 함께 JWT 인증 방식에 대해 알아보자.
로그인 요청
const handleLogin = async (data) => {
return await axios.post("http://서버URL/users/logins", {
email: data.email,
password: data.password,
});
};
로그인 요청을 받은 서버는 토큰을 발급해 응답 헤더에 담아 클라이언트로 보낸다.
웹 스토리지에 토큰 저장
localStorage.setItem("accessToken", data.headers["authorization"]);
localStorage.setItem("refreshToken", data.headers["refresh-token"]);
navigate("/");
클라이언트는 응답 헤더에 있는 토큰을 웹 스토리지에 저장하고 메인 페이지로 이동한다.
그리고 요청할 때 토큰을 서버로 보내는 부분은 사용자 인증이 필요한 요청에 사용할 axios 객체를 만들고 interceptors를 사용했다. axios 인터셉터는 요청이나 응답을 가로채 원하는 작업을 수행할 수 있게 해 준다.
// 사용자 인증 axios 객체 생성
export const auth = axios.create({
baseURL: process.env.REACT_APP_SERVER,
});
// 웹 스토리지에 저장된 토큰을 서버로 전송
auth.interceptors.request.use((config) => {
config.headers["authorization"] = localStorage.getItem("accessToken");
config.headers["refresh-token"] = localStorage.getItem("refreshToken");
return config;
});
여기서 refresh token은 access token이 만료됐을 때 access token을 새로 발급해주기 위한 토큰이다. 클라이언트는 토큰의 만료 여부를 알 수 없다.
그래서 요청 헤더에 토큰을 담아 서버로 보냈을 때 서버가 토큰의 만료 여부를 확인하고 refresh 토큰이 유효하다면 서버는 새로운 access 토큰을 발급해 클라이언트로 보내준다.
그럼 클라이언트는 응답 헤더에 access 토큰이 있는 걸 확인하고 기존 토큰이 만료됐다는 사실을 알게 된다. 그다음 클라이언트는 기존 토큰을 삭제하고 리프레시된 토큰을 다시 저장하는 것이다.
그렇다면 클라이언트는 어떻게 매번 응답 헤더에 리프레시된 토큰이 있는지 확인할까?
이 또한 axios의 interceptors를 이용하면 간단하게 구현할 수 있다.
instance.interceptors.response.use((response) => {
// 응답 헤더에 토큰이 있으면 true
if (response.headers["authorization"]) {
// 만료된 access 토큰 삭제
localStorage.removeItem("accessToken");
// 새로운 access 토큰 저장
localStorage.setItem("accessToken", response.headers["authorization"]);
} else if (response.data.error === "INVALID_TOKEN") { // refresh 토큰 만료
localStorage.removeItem("accessToken"); // access 토큰 삭제
localStorage.removeItem("refreshToken"); // refresh 토큰 삭제
alert("토큰이 만료되었습니다. 다시 로그인해주세요.");
}
return response;
});
두 번째 조건에 해당하는 구문은 주석으로 표기한 바와 같이 리프레시 토큰이 만료됐을 때 실행되는 구문이다.
참고로 토큰 유효기간은 access 토큰은 탈취될 가능성이 높으므로 보통 30분에서 2시간 정도로, refresh 토큰은 아예 유효기간을 두지 않거나 한 달에서 3개월까지 두는 곳도 있다고 한다.
JSON 웹 토큰 - 위키백과, 우리 모두의 백과사전
위키백과, 우리 모두의 백과사전. JSON 웹 토큰상태인터넷 표준최초 출판일2010년 12월 28일 (2010-12-28)마지막 버전RFC 75192015년 5월조직IETF약어JWT JSON 웹 토큰(JSON Web Token, JWT, "jot”[1])은 선택적 서명
ko.wikipedia.org
'Front-end > React' 카테고리의 다른 글
[React] 리액트 앱에서 렌더링 최적화하기 (0) | 2022.10.30 |
---|---|
[React] 리액트에서 CSR을 최적화하는 원리 (0) | 2022.10.03 |
[React] CRA를 이용한 프로젝트 생성과 TypeScript 적용하기 (0) | 2022.09.15 |
[React] 서버 데이터를 다루기 좋은 React Query 기본 사용법 (0) | 2022.09.09 |
[React] 리액트 기본 특징 간단 정리 (0) | 2022.08.23 |