'Pass State to Private Nested Routes on React Router v6
So, I have set up my React app routing using React Router v6 with nested Routes.
The problem is that when I access any of my Private routes (defined as follows) I lose the state of the session, losing info such as the query params and the referrer (previous path) and I can't seem to figure route how I can pass this state to my Private route component to the children routes.
This is my routing configuration:
App.js:
import routes from './routes';
const App = () => {
const routing = useRoutes(routes);
return (
<ThemeProvider theme={theme}>
<UserProvider>
<GlobalStyles />
{routing}
</UserProvider>
</ThemeProvider>
);
};
export default App;
Index.js:
import App from './App';
ReactDOM.render((
<BrowserRouter>
<App />
</BrowserRouter>
), document.getElementById('root'));
Routes.js:
The console.log(location) shows the location.state empty
const Private = ({ component: Component, ...rest }) => {
const [state] = React.useContext(UserContext);
const location = useLocation()
const path = location.pathname
console.log(location)
if (state.auth){
console.log('Authenticated');
return <Component {...rest} />
}
else {
console.log('Not Authenticated')
return <Navigate to = {'/login?from=' + path} />
}
};
const routes = [
{
path: 'app',
element: <Private component={DashboardLayout} />,
children: [
{
path: 'account', children: [
{ path: 'integrations', element: <Integrations /> },
]
},
{ path: 'dashboard', element: <Dashboard /> },
{ path: 'audiences', element: <Audiences /> },
{ path: 'creatives', element: <Creatives /> },
{ path: 'copywriting', element: <Copywriting /> },
{ path: 'settings', element: <ProjectSettings /> },
{ path: 'user_settings', element: <UserSettings /> },
{ path: 'fb_interests', element: <FbInterestsExplorer /> },
{ path: '*', element: <NotFound /> },
]
},
{
path: '/',
element: <MainLayout />,
children: [
{ path: 'login', element: <Login /> },
{ path: 'user/activate/:user_id', element: <UserConfirmation /> },
{ path: '/', element: <Navigate to="/app/dashboard" /> },
{ path: '*', element: <NotFound /> }
]
}
];
export default routes;
DashboardLayout.js
const DashboardLayout = () => {
const [isMobileNavOpen, setMobileNavOpen] = useState(false);
return (
<DashboardLayoutRoot>
<DashboardNavbar onMobileNavOpen={() => setMobileNavOpen(true)} />
<DashboardSidebar
onMobileClose={() => setMobileNavOpen(false)}
openMobile={isMobileNavOpen}
/>
<DashboardLayoutWrapper>
<DashboardLayoutContainer>
<DashboardLayoutContent>
<Outlet />
</DashboardLayoutContent>
</DashboardLayoutContainer>
</DashboardLayoutWrapper>
</DashboardLayoutRoot>
);
};
export default DashboardLayout;
Solution 1:[1]
Try this to get the state in v6:
const location = useLocation()
console.log(location)
const state = location.state
console.log(state)
Solution 2:[2]
This happend with me when spreading an object inside history state.
<MenuItem
onClick={() => {
history("/users/form", {
state: { isNew: false, ...row },
})
}}
>
Edit
</MenuItem>
This fixed the issue
<MenuItem
onClick={() => {
history("/users/form", {
state: {
isNew: false,
type: row.type,
email: row.email,
kind: row.kind || "",
role: row.role,
permissions: row.permissions,
},
})
}}
>
Edit
</MenuItem>
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | ouflak |
| Solution 2 | CESCO |
