skip to Main Content

I’m having some difficulty with react routing and having trouble comprehending composed routes. I’ve attempted some code, but unfortunately, it’s not functioning as expected. The "/" path works perfectly fine, however, when I attempt to access "/child", it doesn’t seem to work. I believe there might be an issue with the wrapper route <Route element={<Wrapper/>} />.

import React from 'react';
import ReactDOM from 'react-dom/client';
import { BrowserRouter, Routes, Route } from 'react-router-dom'

function Home() {
  return <h1>its home</h1>
}

function Child() {
  return <h1>its child</h1>
}

function Wrapper() {
  return( 
    <div>
      <h1>trial</h1>
      <Route path="/child" element={<Child />} />
    </div>
  )
}

function App() {
  return (
    <BrowserRouter>
      <Routes>
        <Route path="/home" element={<Home />} />
        <Route element={<Wrapper />} />
      </Routes>
    </BrowserRouter>
  )
}

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

2

Answers


  1. The Problem

    • You have defined your /child path in the wrong place
    • You have placed it inside your Wrapper component

    Simple Solution

    • This solution just fixes the immediate problem
    • The paths should be defined within the <BrowserRouter> <Routes>
    • See the two commented lines from your example on where to make the changes
    import React from 'react';
    import ReactDOM from 'react-dom/client';
    import {BrowserRouter, Routes, Route} from 'react-router-dom'
    
    
    function Home(){
        return <h1>its home</h1>
    }
    
    function Child(){
        return <h1>its child</h1>
    }
    
    function Wrapper(){
        return( 
        <div>
         <h1>trial</h1>
         <Child/> // Use Child component here
        </div>
        )
    }
    
    function App(){
        return (
            <BrowserRouter>
                <Routes>
                    <Route path= "/home" element={<Home/>} />
                    <Route path= "/child" element={<Wrapper/>}  /> //Path here
                </Routes>
            </BrowserRouter>
        )
    }
    
    

    Further Reading

    • As you say you are still a beginner I’d recommend react router tutorial. It will really help your understanding of the router
    • In particular see the Nested Routes section. I believe this is what you are trying to acheive with the "wrapper"?

    Further Solution

    • Live version of solution codesandbox
    • This solution will make more sense once you have read through the tutorial above.
    • Use react-router Outlet in your wrapper so you can then use the Wrapper across multiple components
    import React from "react";
    import ReactDOM from "react-dom/client";
    import { createBrowserRouter, RouterProvider, Outlet } from "react-router-dom";
    
    function Home() {
      return <h1>Home</h1>;
    }
    
    function Child() {
      return <h2>its child</h2>;
    }
    
    function Wrapper() {
      return (
        <div>
          <h1>Wrapper</h1>
          <Outlet />
        </div>
      );
    }
    
    const router = createBrowserRouter([
      {
        path: "/home",
        element: <Home />
      },
      {
        path: "/",
        element: <Wrapper />,
        children: [
          {
            path: "child",
            element: <Child />
          }
        ]
      }
    ]);
    
    ReactDOM.createRoot(document.getElementById("root")).render(
      <React.StrictMode>
        <RouterProvider router={router} />
      </React.StrictMode>
    );
    
    Login or Signup to reply.
  2. It’s unclear what exactly you are meaning when you say "composed routes", but React-Router basically has two types of routes.

    • Nested Routes: Route components directly rendering other (e.g nested) Route components.

      const FooLayout = () => {
        return (
          ...
          <Outlet />
          ...
        );
      };
      
      <Route path="foo" element={<FooLayout />}>
        <Route index element={<Foo />} />         // <-- rendered into Outlet
        <Route path="bar" element={<FooBar />} /> // <-- rendered into Outlet
      </Route>
      
    • Descendent Routes: Routed components rendering another set of Routes and Route components.

      const FooWrapper = () => {
        return (
          ...
          <Routes>
            <Route path="/" element={<Foo />} />       // <-- descendent route
            <Route path="/bar" element={<FooBar />} /> // <-- descendent route
          </Routes>
          ...
        );
      };
      
      <Route path="foo/*" element={<FooWrapper />} /> // <-- renders descendents
      

    Armed with this knowledge now you have a couple basic ways to render the Child component on the "/child" path where it’s accessible/renderable.

    function Wrapper() {
      return( 
        <div>
          <h1>trial</h1>
          <Routes>
            <Route path="/child" element={<Child />} />
          </Routes>
        </div>
      );
    }
    
    function App() {
      return (
        <BrowserRouter>
          <Routes>
            <Route path="/home" element={<Home />} />
            <Route path="/*" element={<Wrapper />} />
          </Routes>
        </BrowserRouter>
      );
    }
    

    or

    function Wrapper() {
      return( 
        <div>
          <h1>trial</h1>
          <Outlet />
        </div>
      );
    }
    
    function App() {
      return (
        <BrowserRouter>
          <Routes>
            <Route path="/home" element={<Home />} />
            <Route element={<Wrapper />}>
              <Route path="/child" element={<Child />} />
            </Route>
          </Routes>
        </BrowserRouter>
      );
    }
    

    For more details see Layout Routes and Outlets, and Splats.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search