In older react versions i was able to use this code to redirect if user is logged in:
history.push('/login?redirect=shipping')
Now in v6 i am using the useNavigate functions instead of history.push but i dont know how to check if user is logged in with navigate, please let me know if you need more of my code to answer, currently this is my navigate code:
let navigateCart = useNavigate()
// some code here
navigateCart('/login?redirect=shipping') // the mistake is inside the parenthesis here but i dont know what it is!
This is not working it is taking me to .../login/shipping instead of .../shipping
This is my router config:
<BrowserRouter>
<Container><Routes>
<Route path='/' element={< HomeScreen />} exact />
<Route path='/login' element={< LoginScreen />} />
<Route path='/profile' element={< ProfileScreen />} />
<Route path='/shipping' element={< ShippingScreen />} />
</Routes></Container>
</BrowserRouter>
Login Screen Function :
function LoginScreen() {
let navigateLog = useNavigate()
let location = useLocation()
const [email, setEmail] = useState('')
const [password, setPassword] = useState('')
const dispatch = useDispatch()
const redirect = location.search ? location.search.split('=')[1] : '/'
const userLogin = useSelector(state => state.userLogin)
const { error, loading, userInfo } = userLogin
useEffect(() => {
if (userInfo) {
navigateLog(redirect)
}
}, [navigateLog, userInfo, redirect])
const submitHandler = (e) => {
e.preventDefault()
dispatch(login(email, password))
}
CodePudding user response:
Issue
The redirect target path is "shipping"
instead of "/shipping"
. In react-router-dom@6
there are relative paths and absolute paths. The difference is simple, absolute paths start with a leading "/"
character while relative paths do not. navigate("shipping")
will append "shipping"
to the end of the current pathname
and navigate there.
Solution
Either prepend the leading "/"
when navigating:
navigate(`/${navigateLog}`, { replace: true });
Or include it when you initially navigate:
navigateCart('/login?redirect=/shipping');
You'll likely also want to use the useSearchParams
hook to access the redirect
query parameter instead of relying on it to be at a specific string position.
function LoginScreen() {
const navigateLog = useNavigate();
const [searchParams] = useSearchParams();
...
const redirect = searchParams.get("redirect") || '/';
...
useEffect(() => {
if (userInfo) {
navigateLog(redirect, { redirect: true });
}
}, [navigateLog, userInfo, redirect])
...
Note that in issuing the imperative redirect that I've included an options object to the navigate
function that specifies replace: true
, this is to issue a REPLACE action instead of a PUSH action.
CodePudding user response:
Change this line navigateLog(redirect)
inside that useEffect
in LoginScreen
to this one:
navigateLog(`/${redirect}`);
In your case it's redirecting to /login/shipping
instead of /shipping
, cause it's like you are calling navigateLog("shipping")
since redirect
is equal to "shipping"
, so it's used as a relative path. Which means it takes into account your current url, which is in your case /login
.
Here is a working CodeSandbox of a simplified version of your code as well.