6
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

【React】react-router-dom v6の導入方法と使い方

Last updated at Posted at 2024-05-04

インストール

npmコマンドを使用してパッケージをインストールします。

npm i -S react-router-dom

npm iは、npm installのエイリアス(別名)で、パッケージをインストールするコマンドです。

-Sオプションは--saveのショートカットで、このオプションをつけることでpackage.jsonに記録できます。package.jsonに記録しておくことで、他の人がnpm installを実行した時に依存パッケージとしてインストールさせることができます。

ルーティングを設定

src/index.jsファイルの<App /><BrowserRouter />でラップします。
<BrowserRouter />は、アプリケーションにルーティング機能を提供するコンポーネントです。

// src/index.js
import React from 'react';
import ReactDOM from 'react-dom/client';
import './index.css';
import App from './App';
import reportWebVitals from './reportWebVitals';
import { BrowserRouter } from 'react-router-dom';

const root = ReactDOM.createRoot(document.getElementById('root'));
root.render(
  <React.StrictMode>
    <BrowserRouter>
      <App />
    </BrowserRouter>
  </React.StrictMode>
);

reportWebVitals();

次に、src/App.jsで各ページのコンポーネント(今回は<Home /><RouteRouterTest />)とRoute, Routesをインポートします。RoutesコンポーネントでラップされたRouteコンポーネントにURLと遷移先コンポーネントを記述します。

// src/App.js
// react-router-dom v6
import './App.css';
import { Route, Routes } from 'react-router-dom';
import Home from './pages/Home';
import RouterTest from './pages/RouterTest';

function App() {
  return (
    <Routes>
      <Route path='/' element={<Home />} />
      <Route path="/router/test" element={<RouterTest />} />
    </Routes>
  );
}

export default App;

v5以前はSwitchコンポーネントにラップされたRouteコンポーネントでURLとコンポーネントの対応を決めていたので、混同しないように気を付けましょう。慣れ親しんだSwitchを使うと下記のエラーが出ます。

ERROR in ./src/App.js 20:12-18
export 'Switch' (imported as 'Switch') was not found in 'react-router-dom'

【参考】

v5の書き方
// src/App.js
// react-router-dom v5
import './App.css';
import { Route, Switch } from 'react-router-dom';
import Home from './pages/Home';
import RouterTest from './pages/RouterTest';

function App() {
  return (
    <Switch>
      <Route path="/" exact component={<Home />} />
      <Route path="/router/test" exact component={<RouterTest />} />
    </Switch>
  );
}

export default App;

Linkコンポーネントでの画面遷移

ルーティングが設定されたURLをLinkコンポーネントのtoに指定すると指定のコンポーネントへのリンクを作成できます。

<Link to="/router/test">RouterTestのページへ</Link>

useNavigateによる画面遷移

useNavigate Hookを利用することで、関数内で画面遷移処理を入れることができます。v5のuseHistoryと似ています。

import React from "react";
import { useNavigate } from "react-router-dom"

const Home = () => {
    const navigate = useNavigate();
    return (
        <div>
            <div onClick={() => {navigate("/router/test")}}>
                RouterTestページへ
            </div>
        </div>
    )
}

export default Home;

v6でuseHistoryを使おうとすると、下記のエラーが出ます。

ERROR in ./src/pages/Home.jsx 29:10-20
export 'useHistory' (imported as 'useHistory') was not found in 'react-router-dom'

【おまけ】~window.location.hrefとの違い~

react-router-domを使う代わりにwindow.location.href="url"を使えば良くない?と思った方へ。私も最初同じことを思いました。しかし、二つの遷移方法には違いがあります。

App.jsに、ボタンと、ボタンが押された回数をステートで表示する機能を持ったヘッダーを追加して実験してみます。

App.js(クリックでオープン)
import { useState } from 'react';
import './App.css';
import { Route, Routes, BrowserRouter } from 'react-router-dom';
import Home from './pages/Home';
import RouterTest1 from './pages/RouterTest1';
import RouterTest2 from './pages/RouterTest2';
import RouterTest3 from './pages/RouterTest3';

function App() {
  const [count, setCount] = useState(0);
  return (
    <BrowserRouter>
      <header className="App-header">
        <div>{count}</div>
        <button onClick={() => setCount((prev) => prev+1)}>
            +ボタン
        </button>
    </header>
      <Routes>
        <Route path='/' element={<Home />} />
        <Route path="/router/test/1" element={<RouterTest1 />} />
        <Route path="/router/test/2" element={<RouterTest2 />} />
        <Route path="/router/test/3" element={<RouterTest3 />} />
      </Routes>
    </BrowserRouter>
  );
}

export default App;
Home.jsx(クリックでオープン)
import React from "react";
import { useNavigate, Link } from "react-router-dom"

const Home = () => {
    const navigate = useNavigate();

    return (
        <div className="App">
            <button onClick={() => {
                window.location.href="/router/test/1"
            }}>
                1ページへ(window.location.hrefを利用)
            </button>
            <button>
                <Link to="/router/test/2"><span>2ページへ(Linkコンポーネントを利用)</span></Link>
            </button>
            <button onClick={() => {
                navigate("/router/test/3");
            }}>
                3ページへ(useNavigateを利用)
            </button>
        </div>
    )
}

export default Home;

window.location.href="url"を使って遷移
image.png

react-router-domを使って遷移(Linkコンポーネント)
image.png

react-router-domを使って遷移(useNavigate)
image.png

window.location.href="url"を使って遷移した場合、ページが再読み込みされることでステートが初期化さています。一方、react-router-domを使うとページを再読み込みすることなく画面遷移を行うためステートが維持されていることが確認できます。

ステートを維持したかったり余計なAPI呼び出しを行いたくなかったりするときはreact-router-domを使い、ログアウト処理などを行って一度ページを再読み込みしたい場合はwindow.location.href="url"を使うのが良いでしょう。

参考文献

6
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
6
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?