프론트엔드/리액트 | React

리액트 라우터 사용하기 2 ( useParams, useRouteMatch, useHistory, useLocation)

개발자R 2022. 4. 10. 18:26
반응형

useParams, useRouteMatch

import { Fragment, useEffect } from "react";
import { useParams, Route, Link, useRouteMatch } from "react-router-dom";

import Comments from "./../comments/Comments";
import HighlightedQuote from "../quotes/HighlightedQuote";

const QuoteDetail = () => {
  const match = useRouteMatch();
  const params = useParams();

  console.log(match)
  console.log(params)

  const { quoteId } = params;

  return (
    <Fragment>
      <HighlightedQuote text={loadedQuote.text} author={loadedQuote.author} />
      <Route path={match.path} exact>
        <div className="centered">
          <Link className="btn--flat" to={`${match.url}/comments`}>
            Load Comments
          </Link>
        </div>
      </Route>
      <Route path={`${match.path}/comments`}>
        <Comments></Comments>
      </Route>
    </Fragment>
  );
};

export default QuoteDetail;

useParams는 말 그대로 URL 에 담긴 파라미터를 key-value타입으로 가져오는 것이다.

위 코드에서 12번줄 params를 콘솔을 찍어보았을 때 

{
	"quoteId": "-N-D_U5yjkbikU--WPc_"
}

이런식으로 나온다. 

이 페이지에서 url 파라미터는 quoteId 밖에 없기 때문이다.

<Route path="/quotes/:quoteId">
          <QuoteDetail />
</Route>

 

useRouteMatch 를 이용해서 path 값이나 현재 url 값을 알아낼 수 있다.

exact 유무도 알 수 있다.

위 코드에서 11번째 줄 match를 콘솔로 찍으면 아래처럼 찍힌다.

 Nested Route를 쓸 때 path를 하드코딩하지 않아도 되어서 유용하다.

 

useHistory, useLocation

useHistory를 사용해서 직접 url이동을 할 수 있다.

지금까지 이동한 url들이 history에 기록되어있다고 생각하면 된다.

push("경로")를 하면 해당 경로로 이동하고,

replace("경로")를 하면 해당 경로로 이동하는 대신 지금 페이지 경로에 덮어씌워진다. 

A -> B로 가는데 replace를 하면 B에서 뒤로가기를 눌렀을 때에 A로 가지 않고 그 전 페이지로 이동한다는 뜻.

 

pop()을 하면 경로를 하나 빼기 때문에 뒤로 가기가된다.

 

useLocation으로는 pathname, search (쿼리파라미터) 등을 가져올 수 있다.

import { Fragment } from 'react';
import { useHistory, useLocation, useParams } from 'react-router-dom';

import QuoteItem from './QuoteItem';
import classes from './QuoteList.module.css';

const QuoteList = (props) => {
  const history = useHistory()
  const location = useLocation();

  const queryParams = new URLSearchParams(location.search)

  const isSortingAscending = queryParams.get('sort') === 'asc';
  
  const changeSortingHandler = () => {
   //가독성 좋게 push 하는 방법
    history.push({
      pathname: location.pathname,
      search: `?sort=${(isSortingAscending ? 'desc' : 'asc')}`
    })
    // history.push(`${location.pathname}?sort=${(isSortingAscending ? 'desc' : 'asc')}`)
  }

  return (
    <Fragment>
      <div className={classes.sorting}>
        <button onClick={changeSortingHandler}>Sort {isSortingAscending ? 'Descending' : 'Ascending'}</button>
      </div>
      <ul className={classes.list}>
        {sortedQuotes.map((quote) => (
          <QuoteItem
            key={quote.id}
            id={quote.id}
            author={quote.author}
            text={quote.text}
          />
        ))}
      </ul>
    </Fragment>
  );
};

export default QuoteList;
반응형