Thomas Soos
Thomas Soos

Reputation: 189

How to set children to a route that's rendered at "/" in Remix?

I'm trying to migrate a React Router app to Remix. Here's a basic example of how my React Router app works: https://codesandbox.io/s/brave-chandrasekhar-fx0f7f

As you can see, I have a MainComponent which is rendered at "/" and it has an Outlet component from react-router-dom to render different headers based on the path.

By default, my MainHeader component renders there because its path is set to the same as its parent, so it also renders at "/".

But when I navigate to a dynamic route I'm rendering the AnotherHeader component instead of MainHeader.

I'm setting how the routing works in App.tsx with the createBrowserRouter function, where setting children to a component rendered at "/" is perfectly valid.

However, when I try to migrate this app to Remix I have no idea how to do that.

I created the following routes:

I'm rendering it at the same "/" route as my main MainComponent which works great in react-router-dom but apparently index routes cannot have child routes in Remix.

I've created a Remix version of the same app, where you can hopefully see the differences, which lies in the fact that the MainHeader component doesn't render since I haven't created a route for it yet. Also when AnotherHeader renders, it doesn't render within the MainComponent but as a separate component.

So the question is How can I create a route for my MainHeader component in Remix so that it works the same way as in my React Router app?

Upvotes: 2

Views: 2743

Answers (1)

Drew Reese
Drew Reese

Reputation: 203348

The react-router-dom version of your code, it's the more idiomatic convention to specify the index prop for the nested route you want to be rendered when the path exactly the parent route than it is to specify a path prop with the same path value.

Example:

const router = createBrowserRouter([
  {
    path: "/",
    element: <MainComponent />,
    children: [
      {
        index: true, // <-- match with parent route path
        element: <MainHeader />
      },
      {
        path: "/:id",
        element: <AnotherHeader />
      }
    ]
  }
]);

or

<Route path="/" element={<MainComponent />}>
  <Route index element={<MainHeader />} />
  <Route path=":id" element={<AnotherHeader />} />
</Route>

All routing is assumed to be from "root", e.g. "/" in most/common cases. The MainComponent is the root-level component being rendered as a layout route.

Defining Routes

Based on the docs I believe the following is the file/directory structure to convert the react-router-dom code to a Remix version:

app
+-- root.tsx      // <-- file that renders MainComponent, e.g. UI + Outlet
+-- routes
    +-- index.tsx // <-- file that renders MainHeader
    +-- $id.tsx   // <-- file that renders AnotherHeader

https://codesandbox.io/p/sandbox/quirky-leftpad-s1xqfn?file=%2Fapp%2Froot.tsx%3A6%2C10

main root page page id 1 page id 2

Upvotes: 2

Related Questions