I’m building a full stack react application. I have the stack operating and pulling information from the backend when I’m calling it from the frontend. I’m using axios on the frontend to hit the endpoints I’ve set up on the backend. I’m having an issue with frontend authentication though. I’m using passport and passport-google-oauth20 to log users in with Google OAuth2.0. I have this working correctly. The problem I’m having: when a user hits a specific URL (controlled by react-router-dom) I have a function called authVerify
run that pings the backend and checks if the user is logged in (by looking at the cookie - not accessible in JS). The function runs correctly and correctly updates the state. I have a state field for authenticated originally set to false, and on a successful 200 response I setState for authenticated to true. But, the protected routes I’ve built aren’t working. If the user is authenticated, they should be able to go to that route. If not, they get redirected to the login page. But, everything just redirects to the login page.
Here is the Router.js code:
import React from 'react';
import axios from 'axios';
import { BrowserRouter, Route, Switch } from 'react-router-dom';
import PrivateRoute from './PrivateRoute';
import Login from './Login';
import SignUp from './SignUp';
import App from './App';
import NotFound from './NotFound';
class Router extends React.Component {
constructor(props) {
super(props);
this.state = {
authenticated: false,
};
}
componentDidMount() {
this.authVerify()
.then((res) => {
if (res.status === 200) {
console.log(this.state);
this.setState({
authenticated: true,
});
console.log(this.state);
}
})
.catch(err => console.log(err));
}
authVerify = () => axios.get('/authVerify')
render() {
return (
<BrowserRouter>
<Switch>
<PrivateRoute path="/" component={App} />
<Route exact path="/pages/signup" component={SignUp} />
<Route exact path="/pages/login" component={Login} />
<PrivateRoute path="/pages/dashboard" authenticated={this.state.authenticated} component={App} />
<Route component={NotFound} />
</Switch>
</BrowserRouter>
);
}
}
export default Router;
And here is the PrivateRoute.js code:
import React from 'react';
import { Route, Redirect, withRouter } from 'react-router-dom';
const PrivateRoute = ({ component: Component, authenticated, ...rest }) => (
<Route
{...rest}
render={props => (authenticated === true ? <Component {...props} /> : <Redirect to="/pages/login" />)}
/>
);
export default withRouter(PrivateRoute);
I have console logged the response from the API and I successfully get a 200 response. I’ve also console logged the state before and after the call to the API and before it’s false
and after it’s true
. But, I’m always redirected to the login page.
I think the issue is that the call to the API is taking too long and the component is mounting before authentication is verified. But, I thought by setting the state in the componentDidMount function would update the component and redirect appropriately. Any help would be appreciated.