Middleware redirection is rendering the correct page but not changing browser url
Unanswered
GuitarNerd posted this in #help-forum
Hi everyone,
This issue seems to resurface with me I don't know why, possibly due to updating Next.js.
Below you will find my middleware.
In one of those cases I have 2 redirects:
- User logs in. Code sends it to the dashboard.
- Middleware realises user was not approved by the admin: redirect to a page informing user their account is awaiting approval.
And here are the relevant parts in my server actions:
This issue seems to resurface with me I don't know why, possibly due to updating Next.js.
Below you will find my middleware.
In one of those cases I have 2 redirects:
- User logs in. Code sends it to the dashboard.
- Middleware realises user was not approved by the admin: redirect to a page informing user their account is awaiting approval.
And here are the relevant parts in my server actions:
"use server"
import { revalidatePath, revalidateTag } from "next/cache"
import { cookies } from "next/headers"
import { IUser, IUserAuth } from "@/types/global"
import { USER } from "@/api"
import { extractResponseData, userCookieData } from "./helpers"
export const setUser = (user: IUser | null, token: string) => {
if (user) {
cookies().set(
"user",
JSON.stringify({
token,
user: userCookieData(user),
})
)
} else {
cookies().delete("user")
}
}
export const getUser = async () => {
"use server"
const user = cookies().get("user")
if (!user) {
try {
const response = await fetch(USER.url, {
method: "GET",
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${cookies().get("token")}`,
},
})
if (response.ok) {
const { data } = await extractResponseData(response)
setUser((data as IUserAuth).user as IUser, (data as IUserAuth).access_token)
}
} catch (err) {
console.log(err)
}
}
return cookies().get("user")
}
21 Replies
bump
I don't see any issue there. could you try
return NextResponse.redirect(new URL("/path", req.url))
and see it the url change?Thank you for your answer and taking the time!
I did that. I added 307 after reading the documentation just as a potential last resort, it didn't help.
I'm wondering if the rewrites in next.config.js could be affecting that ?
I did that. I added 307 after reading the documentation just as a potential last resort, it didn't help.
I'm wondering if the rewrites in next.config.js could be affecting that ?
async rewrites() {
return [
{
source: '/signup/:path*',
destination: '/auth/signup/:path*',
},
{
source: '/login',
destination: '/auth/login',
},
{
source: '/created',
destination: '/auth/created',
},
{
source: '/forgot-password/:path*',
destination: '/auth/forgot-password/:path*',
},
{
source: '/waiting',
destination: '/auth/waiting',
},
{
source: '/verification/:path*',
destination: '/auth/verification/:path*',
},
]
},
oh yeah it will affect
rewrite won't change the url
Currently when I'm redirecting I'm using the URL in source. Should I use the one in destination ?
That would be a little odd because it's working on some URLs and not on others
That would be a little odd because it's working on some URLs and not on others
I'll give it a shot when I'm back from the dentist. Thanks!
yes use the one in destination should do it
Didn't work. For a temporary workaround i'm doing a setTimeout on the frontend where i'm using router.push but i'll look into it again in another sprint
for example,
/auth/login
is the real path of /login
right?Yes
I'm thinking that perhaps the router.push is happening before the server action has completed setting my cookies and that is causing my frontend router and my server router to have a delay. Which is why the frontend is rendering correctly but the browser url isn't changing.
This is further supported by the fact that:
- When I refresh the browser url is updated correctly(so it seems there is a delay)
- setTimeout is fixing it.
- When I refresh the browser url is updated correctly(so it seems there is a delay)
- setTimeout is fixing it.
oh where do you use
router.push
? do you use router.push
on all the page and does all the page not changine the url?I am using router.push in my AuthContext which calls a server action. I didn't originally include them as I thought the issue is isolated to the middleware. Adding them below
the settimeout is a workaround that lets me bypass the issue but obviously i'd like to get rid of it
"use server"
import { revalidatePath, revalidateTag } from "next/cache"
import { cookies } from "next/headers"
import { IUser, IUserAuth } from "@/types/global"
import { USER } from "@/api"
import { extractResponseData, userCookieData } from "./helpers"
export const setUser = (user: IUser | null, token: string) => {
if (user) {
cookies().set(
"user",
JSON.stringify({
token,
user: userCookieData(user),
})
)
} else {
cookies().delete("user")
}
}
export const getUser = async () => {
"use server"
const user = cookies().get("user")
if (!user) {
try {
const response = await fetch(USER.url, {
method: "GET",
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${cookies().get("token")}`,
},
})
if (response.ok) {
const { data } = await extractResponseData(response)
setUser((data as IUserAuth).user as IUser, (data as IUserAuth).access_token)
}
} catch (err) {
console.log(err)
}
}
return cookies().get("user")
}
Server Actions
could you do a test on a page without context and
router.push
and see if the url change correctly?@Ray yes it does
ok so should be something wrong on client side. what is the url you use on
router.push
? the source one or the destination one on the rewrites?