I've been having a hard time trying to redirect to the PrivateRoute that I have for homepage after a user is authenticated via Firebase auth combining it with Redux actions and reducers. Right now if I history push from the dispatch action it is too early for auth to activate the PrivateRoute and if I redirect from componentDidMount it doesn't redirect to '/' which is homepage. Please let me know the best approach to do this. helpp!
In my Auth.js
import React, { useEffect, useState } from "react";
import { auth } from "./fbConfig";
export const AuthContext = React.createContext();
export const AuthProvider = ({ children }) => {
const [currentUser, setCurrentUser] = useState(null);
const [pending, setPending] = useState(true);
useEffect(() => {
auth.onAuthStateChanged((user) => {
setCurrentUser(user)
setPending(false)
});
}, []);
return (
<AuthContext.Provider
value={{
currentUser
}}
>
{children}
</AuthContext.Provider>
);
};
In my login.js
class Login extends React.Component {
state = {
email: '',
password: ''
}
handleChange = (e) => {
this.setState({
[e.target.id]: e.target.value
})
}
handleSubmit = (e) => {
e.preventDefault();
console.log(this.state);
this.props.signIn(this.state);
}
componentDidUpdate(prevProps) {
if (this.props.auth.isEmpty != prevProps.auth.isEmpty) {
// CODE NOT WORKING
console.log("hey");
this.props.history.push('/');
}
}
render() {
...
}
}
const mapStateToProps = (state) => {
return {
authError: state.authError,
auth: state.firebase.auth
}
}
const mapDispatchToProps = (dispatch, props) => {
return {
signIn: (creds) => dispatch(signIn(creds, props))
}
}
const enhance = compose(
withRouter,
withStyles(useStyles),
connect(mapStateToProps, mapDispatchToProps),
);
export default enhance(Login);
In my authActions.js
export const signIn = (credentials, props) => {
return (dispatch, getState, {getFirebase}) => {
const firebase = getFirebase();
firebase.auth().signInWithEmailAndPassword(
credentials.email,
credentials.password
).then(() => {
dispatch({ type: 'LOGIN_SUCCESS' });
// this.props.history.push('/');
}).catch((err) => {
dispatch({ type: 'LOGIN_ERROR', err });
});
}
}
PivateRoute.js
import React, { useContext } from "react";
import { Route, Redirect } from "react-router-dom";
import { AuthContext } from "./Auth";
const PrivateRoute = ({ component: RouteComponent, ...rest }) => {
const {currentUser} = useContext(AuthContext);
console.log(currentUser);
return (
<Route
{...rest}
render={routeProps =>
!!currentUser ? (
<RouteComponent {...routeProps} />
) : (
<Redirect to={"/login"} />
)
}
/>
);
};
export default PrivateRoute
App.js
const App = () => {
return (
<AuthProvider>
<Router>
<div>
<Switch>
<Route exact path='/login' component={Login} />
<Route exact path='/signup' component={SignUp} />
<PrivateRoute exact path="/" component={Homepage} />
</Switch>
</div>
</Router>
</AuthProvider>
);
}