현재 프론트엔드 애플리케이션은 백엔드에 http 요청을 보냈을 때 403이 리턴되면 로그인 페이지로 리디렉트 해야합니다.
또 로그인한 후 백엔드 서비스로 부터 받은 토큰을 어딘가에 저장해 놓고
요청을 보낼 때마다 헤더에 Bearer 토큰을 지정해줘야합니다.
그래서 첫번쨰로 로그인 페이지와 리디렉션 로직을 구현해야합니다.
그러기위해서 리액트-라우터-돔 라이브러리가 필요합니다.
2021.12.14 - React-router-dom 라이브러리가 필요한 이유
React-router-dom 라이브러리가 필요한 이유
React-router-dom 라이브러리가 필요한이유 이 라이브러리가 왜 필요한지 설명전에 우리에게 익숙한 형식의 웹 애플리케이션을 살펴 보겠습니다. 우리에게 익숙한 형식의 라우팅은 다음과 같습니다
uno-kim.tistory.com
애플리케이션이 존재하는 경로로 들어간 후 react-router-dom을 설치해주도록 합시다.
npm install react-router-dom
설치가 완료되었다.
로그인 컴포넌트
라우팅의 테스팅을 위해 기능이 없는 Login.js 를 작성해봅시다.
import React from "react";
class Login extends React.Component{
constructor(props){
super(props);
}
render(){
return <p>로그인 페이지</p>;
}
}
export default Login;
이제 이 컴포넌트로 라우팅할 수 있는 src/AppRoute.js 를 작성합니다.
import React from "react";
import "../css/index.css";
import App from "./App.js";
import Login from "./Login";
import {BrowserRouter as Router,Switch, Route} from "react-router-dom";
import Box from "@material-ui/core/Box";
import Typography from "@material-ui/core/Typography";
function Copyright(){
return(
<Typography variant="body2" color = "textSecondary" align="center">
{"Copuright @"}
unoKim, {new Date().getFullYear()}
</Typography>
);
}
class AppRouter extends React.Component{
render(){
return(
<div>
<Router>
<div>
<switch>
<Login/>
<Route/>
<Route path="/">
<App/>
</Route>
</switch>
</div>
<Box mt={5}>
<Copyright/>
</Box>
</Router>
</div>
);
}
}
기존에는 ReactDOM에 APP컴포넌트를 넘겨줬지만 하지만 이제는 경로에 따라 실행되는 컴포넌트가 다르므로,
그 정보를 갖고 있는 AppRouter를 가장 먼저 렌더링 해야합니다.
Index.js로 가서 맨 처음 렌더링 되는 컴포넌트가 AppRouter 컴포넌트가 되도록 수정해 줍니다.
import React from "react";
import ReactDOM from "react-dom";
import "./css/index.css";
import AppRouter from "./js/AppRouter";
import reportWebVitals from "./js/reportWebVitals";
ReactDOM.render(
<React.StrictMode>
<AppRouter/>
</React.StrictMode>,
document.getElementById("root")
);
reportWebVitals();
기존의 App.js였고 <App/> 을 위처럼 바꾸어주었습니다.
이제 프론트엔드 서버를 재시작한 후 로컬3000번 로그인페이지로 들어가봅니다.
이때 한번은 오류가 발생할수있습니다.
이유는 설치할때 버전 선언을 안해주어서 ,,,ㅠㅠ
로그인 페이지라는 문가 뜬다면 라우팅이 제대로 동작하는 것을 확인해 줄수 있습니다.
접근 거부 시 로그인 페이지로 라우팅 하기
만약 접근 거부를 받는 경우 /login 으로 라우팅하는 코드는 어디에 작성해야할까요?
우리는 누구에게 API콜을 했을때 접근 거부를 받을까요??
바로 localhost:8080/todo 입니다.
또 Http메서드의 종류(GET/POST/PUT/DELETE)에 상관없이 로그인하지 않은 경우
로그인 페이지로 리디렉트 해야합니다.
따라서 우리는 리디렉트하는 로직을 ApiService의 어딘가에 추가해야 한다는 것을 알 수 가 있습니다.
ApiService의 Call 메서드는 결국 fetch 메서드를 부릅니다. fetch메서드를 이용하면 APU콜을 한 후
,then을 이용해 그 결과를 받아 올 수 있습니다. 그런데 만약 에러 response가 리턴된다면
우리는 자바스크립트에서 Promise에서 catch 매서드를 사용해 에러를 받아볼수있다고 했고,
따라서 이 catch매서드안에서 상태코드를 분석해
403인 경우 login 페이지로 리디렉트 할수 있다.
즉!!!!! 한마디로 403일때 로그인으로 보내준다. 이렇게 생각하시면 될것같습니다.
지금로그인이 안되어있는 상태에서 글을 계속 남기려하면 위와같은 콘솔이 뜹니다.
쉽게얘기해서 403상태고 Access Denied일떄 로그인화면으로 보낸다는 것을
구현해주면됩니다.
import { API_BASE_URL } from "../api-config";
export function call(api, method, request) {
let options = {
headers: new Headers({
"Content-Type": "application/json",
}),
url: API_BASE_URL + api,
method: method,
};
if (request) {
// GET method
options.body = JSON.stringify(request);
}
return fetch(options.url, options)
.then((response) =>
response.json().then((json) => {
if (!response.ok) {
// response.ok가 true이면 정상적인 리스폰스를 받은것, 아니면 에러 리스폰스를 받은것.
return Promise.reject(json);
}
return json;
})
)
.catch((error) => {
// 추가된 부분
console.log(error.status);
if (error.status === 403) {
window.location.href = "/login"; // redirect
}
return Promise.reject(error);
});
}
조금 길어보이실수있지만 기본 코드의 밑에 .catch 를 넣어주어 오류가 나올시
로그를 콘솔에 나타내고, 그게 403이면, 로그인화면으로 이동시켜라 라는 의미입니다.
이제 로그인이 되지않았는데 todo를 한다던가 뭔가 이상한걸 시도하려하면
오류가 발생하고, 그것을 트리거로 하여금 로그인페이지로 이동하는 로직을 구현했습니다.
다음 포스팅으로는 로그인 페이지를 구현하도록 해보겠습니다.
'Spring boot 프로젝트 기록 > 2. 프론트엔드 개발' 카테고리의 다른 글
액세스 토큰 저장 (0) | 2021.12.15 |
---|---|
로그인 페이지 (0) | 2021.12.15 |
서비스통합(백엔드와 프론트엔드 통합하기) (0) | 2021.12.01 |
Todo 수정 (0) | 2021.12.01 |
Todo 기능(추가, 삭제) (0) | 2021.12.01 |
댓글