I'm trying to use the onEnter of Router from react-router-dom to validate if a user is authenticate. I'm keeping the authentication in the login reducer.
Initial State:
const initialState = {
logged: false,
userName: null
}
In my App.js I have my Router
import React from 'react';
import {
BrowserRouter as Router,
Switch,
Route,
Link
} from "react-router-dom";
import { useSelector } from "react-redux";
import Home from './Home';
import Login from './Login';
function App() {
const login = useSelector((state) => state.login);
const requireAuth = (nextState, replace, next) => {
console.log(login)
if(!login.logged) {
replace({
pathname: "/login",
state: {nextPathname: nextState.location.pathname}
});
}
next();
}
return (
<Router>
<Switch>
<Route exact path="/" component={Home} onEnter={requireAuth} />
<Route exact path="/login" component={Login} />
</Switch>
</Router>
)
}
export default App;
It is not redirecting to the /login. Actually, it is not calling the requireAuth function because the browser does not show the log that I have inside the function. What am I missing in the Router settings?
By the way, is it an appropriate way to check if a user is authenticate before navigating to a page?
Thanks
Updated code using PrivateRoute. Error: Error: Maximum update depth exceeded.
import React from 'react';
import {
BrowserRouter as Router,
Switch,
Route,
Redirect
} from "react-router-dom";
import { useSelector } from "react-redux";
import Home from './Home';
import Login from './Login';
function App() {
const PrivateRoute = ({ children, ...rest }) => {
const login = useSelector((state) => state.login);
console.log(login);
return (
<Route
{...rest}
render={({ location }) =>
login.logged ? (
children
) : (
<Redirect
to={{
pathname: "/login",
state: { from: location }
}}
/>
)
}
/>
);
}
return (
<Router>
<Switch>
<PrivateRoute path="/">
<Home />
</PrivateRoute>
<Route path="/login">
<Login />
</Route>
</Switch>
</Router>
)
}
export default App;