과거 프로그래밍 자료들/프로젝트

프로젝트 수정 8 - node.js로만 구성된 프로젝트에 리액트 추가(클라이언트 항목 : 인증하기)

평부 2022. 5. 16. 23:32

* 현재 진행상황

- 프로젝트에 CRUD만 만든 상황

- fetch로 로그인 했으나 auth로 로그인 및 react로 로그인 화면을 만드는 것이 중요하다고 판단

- node.js 화면단을 ejs로 만들었으나 react에서 js로 만들 예정

- 참고 강의 : 따라하면서 배우는 노드, 리액트(로그인 부분)

 

* 프론트부분에서 인증이 필요한 부분

- 로그인 시 로그인 페이지/회원가입 페이지로 이동 못하게 하기 -> 가려고 하면 기본페이지(LandingPage)로 이동할 것

 

[인증 부분 만들기 - client 부분]

1. hoc/auth.js에서 인증 부분 만들기

2. hoc/auth.js에서 console.log(response)로 확인한 부분들로 조건문 만들기

3. _actions/_reducer에서 auth와 관련된 부분 만들기

4. App.js에서 hoc를 통해 auth 적용시키기

5. 구글 크롬에서 확인하기

 

* HOC 

* 출처 : (https://ko.reactjs.org/docs/higher-order-components.html)

 

1. hoc/auth.js에서 인증 부분 만들기

import React, { useEffect } from "react";
import axios from "axios";
import { useDispatch } from "react-redux";
import { auth } from "../_actions/user_action";


export default function (SpecificComponent, option, adminRoute = null) {
  //backned의 그 사람의 현재 상태 확인
  //api/user/auth로 정보 보내기
  function AuthentificationCheck(props) {
    const dispatch = useDispatch();
    const navigate = useNavigate();

    useEffect(() => {
      dispatch(auth()).then((response) => {
        console.log(response);
        }
      });
    }, []);

    return <SpecificComponent />;
  }

  return <AuthentificationCheck />;
}

 

 

2. hoc/auth.js에서 console.log(response)로 확인한 부분들로 조건문 만들기

  isAdmin isAuth
로그인 하기 전 false true
로그인 후 false true
로그아웃 후 null(빈칸) false

 

  LandingPage("/") LoginPage("/login") RegisterPage("/register")
isAdmin true false false
isAuth null true false

 

hoc/auth.js

 

import React, { useEffect } from "react";
import axios from "axios";
import { useDispatch } from "react-redux";
import { auth } from "../_actions/user_action";
import { useNavigate } from "react-router-dom";

export default function (SpecificComponent, option, adminRoute = null) {
  //backned의 그 사람의 현재 상태 확인
  //api/user/auth로 정보 보내기

  //null : 아무나 출입 가능
  //option이 true : 로그인 한 사람만 출입 가능
  //option이 false : 로그인한 유저는 출입 불가능

  function AuthentificationCheck(props) {
    const dispatch = useDispatch();
    const navigate = useNavigate();

    useEffect(() => {
      dispatch(auth()).then((response) => {
        console.log(response);
        //로그인 하지 않은 상태
        if (!response.payload.isAuth) {
          if (option === true) {
            //로그인으로 이동 시
            navigate("/login"); //로그인페이지로 가게 함
          }
        } else {
          //response.payload.isAuth = true
          //로그인한 상태(로그인페이지, 회원가입 페이지 이동하지 않아야 함)
          if (adminRoute && !response.payload.isAdmin) {
            //option이 true일 때
            navigate("/");
          } else {
            //option이 false일 때
            //false상태
            navigate("/");
          }
        }
      });
    }, []);

    return <SpecificComponent />;
  }

  return <AuthentificationCheck />;
}

 

 

3. _actions/_reducer에서 auth와 관련된 부분 만들기

 

_actions

 

//types
export const LOGIN_USER = "login_user";
export const REGISTER_USER = "register_user";
export const AUTH_USER = "auth_user";


//user_action
import axios from "axios";
import { LOGIN_USER, REGISTER_USER, AUTH_USER } from "./types";

export function loginUser(dataToSubmit) {
  const request = axios
    .post("/api/user/login", dataToSubmit)
    .then((response) => response.data);

  return {
    type: LOGIN_USER,
    payload: request,
  };
}

export function registerUser(dataToSubmit) {
  const request = axios
    .post("/api/user/register", dataToSubmit)
    .then((response) => response.data);

  return {
    type: REGISTER_USER,
    payload: request,
  };
}

export function auth() {
  //get 메소드는 body 부분 : dataToSubmit 필요 없음
  const request = axios.get("/api/user/auth").then((response) => response.data);

  return {
    type: AUTH_USER,
    payload: request,
  };
}

 

 

_reducer

 

//user_reducer.js
import { LOGIN_USER, REGISTER_USER, AUTH_USER } from "../_actions/types";

// eslint-disable-next-line import/no-anonymous-default-export
export default function (state = {}, action) {
  switch (action.type) {
    case LOGIN_USER:
      return { ...state, loginSuccess: action.payload };
    case REGISTER_USER:
      return { ...state, register: action.payload };
    case AUTH_USER:
      return { ...state, userData: action.payload };
      break;
    default:
      return state;
  }
}

 

 

 

4. App.js에서 hoc를 통해 auth 적용시키기

 

import { BrowserRouter, Routes, Route } from "react-router-dom";
import LandingPage from "./components/views/Landing/LandingPage";
import LoginPage from "./components/views/Login/LoginPage";
import RegisterPage from "./components/views/Register/RegisterPage";
import Auth from "./hoc/auth";

function App() {
  return (
    <BrowserRouter>
      <Routes>
        <Route path="/" element={Auth(LandingPage, null)} />
        <Route path="/login" element={Auth(LoginPage, false)} />
        <Route path="/register" element={Auth(RegisterPage, false)} />
      </Routes>
    </BrowserRouter>
  );
}
export default App;

 

 

5. 구글 크롬에서 확인하기

- 로그인 시 로그인페이지와 회원가입 페이지로 가는 대신 랜딩페이지("/")로 이동함