Replies: 1 comment
-
Remix doesn't provide an easy way to access the route configuration directly. However, if you're using one of the custom adapters, like Express, you can include the routes config from the server build using const build = viteDevServer
? () => viteDevServer.ssrLoadModule("virtual:remix/server-build")
: await import("./build/server/index.js");
const remixHandler = createRequestHandler({
build,
getLoadContext: async () => {
const serverBuild = await build();
return { routes: serverBuild.routes };
},
});
{
root: {
id: 'root',
parentId: undefined,
path: '',
index: undefined,
caseSensitive: undefined,
module: {
Layout: [Getter],
default: [Function: App],
[Symbol(Symbol.toStringTag)]: 'Module'
}
},
'routes/user.$id': {
id: 'routes/user.$id',
parentId: 'routes/user',
path: ':id',
index: undefined,
caseSensitive: undefined,
module: {
loader: [Getter],
action: [Getter],
default: [Function: Component],
[Symbol(Symbol.toStringTag)]: 'Module'
}
},
// ... snip ...
} React Router provides a handy function, Unfortunately, the Remix route config is not in the format that Here's a function that will convert to the correct format. // convert Remix routes to React Router routes
function convertRoutes(routes) {
if (!routes) {
return [];
}
const routeConfigs = Object.values(routes);
function getChildren(parentId) {
return routeConfigs
.filter((route) => route.parentId === parentId)
.map((route) => {
return {
...route,
children: getChildren(route.id),
};
});
}
return [{ ...routes["root"], children: getChildren("root") }];
} So the same config above would look like this: [
{
id: 'root',
parentId: undefined,
path: '',
index: undefined,
caseSensitive: undefined,
module: {
Layout: [Getter],
default: [Function: App],
[Symbol(Symbol.toStringTag)]: 'Module'
},
children: [
{
id: 'routes/_index',
parentId: 'root',
path: undefined,
index: true,
caseSensitive: undefined,
module: [Object],
children: []
},
{
id: 'routes/test',
parentId: 'root',
path: 'test',
index: undefined,
caseSensitive: undefined,
module: [Object],
children: []
},
{
id: 'routes/user',
parentId: 'root',
path: 'user',
index: undefined,
caseSensitive: undefined,
module: [Object],
children: [Array]
}
]
}
] So in getLoadContext: async () => {
const serverBuild = await build();
return { routes: convertRoutes(serverBuild.routes) };
}, So you're probably wondering how this helps you solve your problem. By using You now have access to the import { matchRoutes } from '@remix-run/react'
const { routes } = context // get converted routes
const matches = matchRoutes(rrRoutes, url) // get matches for the url
const match = matches.at(-1) // get leaf match
const { handle } = match?.route.module // get the handle for the matched route
const breadcrumb = handle?.crumb() // you can now access data, call functions, etc. |
Beta Was this translation helpful? Give feedback.
-
I've searched the docs, googled, and asked ChatGPT and I haven't be able to find an answer on this yet. What I'm trying to do is implement a "Favorite Page" feature in my application. I have static page-specific data stored inside the crumb function based on this documentation that I would like to access outside of the route and component that match it. When my user "favorites" a page I would like to display that page information nicely without having to save duplicate static information. I'd prefer to just link the static crumb data to the URL. Is this even possible or am I missing something?
Beta Was this translation helpful? Give feedback.
All reactions