본문 바로가기

프로젝트/KimsBoard

라우터 설계를 위한 기초 설정


  //아래 description들은 라우터설계를 위한 사전작업.
  //description: 메인 화면 :'/' - Main  // 메인화면의 경우 경로는 '/'로 설정된다. 컴포넌트의 이름은 Main이 된다.//
  //description:  인증과 관련된 회원가입과 로그인 페이지 : '/auth' - Authentication  //
  //description: 검색화면 : '/search/:searchWord' - Search //
  // description: 유저 페이지: '/user/:userEmail' - User //
  // description: 게시물 상세보기 : '/board/:boardNumber' - BoardDetail//(여기서 BoardDetail은 컴포넌트 이름임)
  // description: 게시물 작성하기 : '/board/write' - BoardWrite // (여기서 BoardWrite는 컴포넌트 이름임)
  // description: 게시물 수정하기: '/board/update/:boardNumber'- BoardUpdate// (boardNumber=어떤 게시물인지. boardNumber는 컴포넌트 이름)

위와 같이 설계를 하고 이를 코드로 옮기면 아래와 같다.

여기서 주의 할  것이 만약 경로를 http://localhost:3000/board/update 와 같이 작성해 주면 어디로 갈까? 업데이트 화면으로 가지 않는다 Detail로 간다. path='update/:boardNumber' 로 갈려면 어찌됐든 간에 update다음에 어떠한 아무 것이라도 와야 한다. 그냥 update만 오면 그것은 :boardNumber와 매칭된다.

 

===========================================================================

 

내가 예전에 고민했던 것 중에 하나가 각기 다른 모든 페이지에 공통된 헤더(Header)와 Footer를 어떻게 적용하나 였다. 당시에 나는 어떻게 해선가 조잡하게 이 문제를 해결했었는데 여기서 Outlet이라는 컴포넌트를 사용해서 아주 깔쌈하게 해결해 주고 있다 굿굿. 적용하자!!!

 

======================================================================

여기서 흥미롭게도 내가 필요한 상황이 우연찮게 주워지는데 바로 인증화면 같은 경우는 Footer가 존재 하지 않는것이다. 이렇게 특정화면에서는 공통적으로 적용되는 요소(여기서는 Footer)를 빼버릴려면 어떻게 하면 될까? 결론부터 말하면 react-router-dom라이브러리에 있는 useLocation() 훅을 사용하는 것이다. 말그대로 위치를 사용하는 것인데 위치와 관련된 변수인 pathname을 사용할 수 있게 해준다.

다시 layouts폴더 안의 Container폴더안의 index파일안에 가서 아래처럼 모형을 갖추어 준다.

 

코드를 보면 알겠지만 auth화면이 아닐 경우에만 Footer컴포넌트가 사용되게 끔 꾀를 부린것을 볼수 있다.

 

======================================================================

아래 그림을 보면(App.tsx) path에 대한 이름을 모두 리터럴 값으로 지정해 놓았는데 리터럴 path값은 개발할 때 많이 쓰이게 됩니다. 따라서 오타를 내기 쉬운데 그것을 방지하기 위해 상수값으로 아예 지정해 버리는 것입니다. constants폴더에 index.ts파일을 만들어 줍니다.

상수값 경로(path)를 적용해 주지 않음
constants폴더에 위와 같이 상수를 지정해줌

이후 이를 App.tsx에 적용하면 아래와 같음. 기본적으로 각각의 PATH는 const이기 때문에 가능한 것이다.

 

=============================================================================

중간에 파일명을 constants로 해서 문제가 생겼다. 왜 constants로 하면 안되나? 대화방에 질문한 끝에 오류의 원인을 보편적으로 해결할 수 있는 방법을 찾았다. 컨트롤 누르고 문제의 constants에 마우스를 올리면 아래와 같은 오류문구가 뜬다.

좀더 정확한 원인은 constants가 노드 모듈이고 타입스크립트는 노드 모듈을 우선시 하기 때문에 constants라는 이름으로 폴더를 생성하면 오류가 나는 것이다.

 

중요한 것은 변기 뚫듯이 끝까지 에러의 원인을 알고 해결하려 하는 자세이다.

 

=============================================================================

Outlet과 useLocation의 쓰임

import { Outlet, useLocation } from 'react-router-dom'
 

react-router-dom에는 Outlet과 useLocation이라는 훅이 있다. Outlet의 쓰임은 다음과 같다.

Outlet은 부모 컴포넌트에 쓰여 자식을 랜더링 해주기 위해서 사용한다. 즉 자식 컴포너트를 보여줄지를 결정하는 것이다.

 

useLocation같은 경우는 아래와 같이 프로젝트를 구성할 때 쓰였다.

useLocation()의 속성인 pathname을 가져와 그것이 특정 이름의 경로(path)와 다를때와 Footer컴포넌트를 랜더링하는 식이다.  공식문서에는 아래와 같은 설명으로 나온다.  (참고. https://reactrouter.com/en/main/hooks/use-location  )

useLocation

Type declaration

This hook returns the current location object. This can be useful if you'd like to perform some side effect whenever the current location changes.

import * as React from 'react';
import { useLocation } from 'react-router-dom';

function App() {
  let location = useLocation();

  React.useEffect(() => {
    // Google Analytics
    ga('send', 'pageview');
  }, [location]);

  return (
    // ...
  );
}

Properties

location.hash

The hash of the current URL.

location.key

The unique key of this location.

location.pathname

The path of the current URL.