Next.js Discord

Discord Forum

next 14 prevent infinite redirects in layout

Answered
stiltkl posted this in #help-forum
Open in Discord
Hello, I'm creating a chess.com clone - I am attempting to redirect the user if they are currently in a game and they are trying to access any page that is not the 'game page'. Intuitively I thought to do this in a server layout component, so that I can query the serverside game's manager and check if the player is in a game and redirect them if they are. My conditions works, and the user is in fact in a game, they are redirected. However, because they are redirected to a page that is nested within the layout with the redirect condition in, they are redirected again and a redirect cycle begins.

How would I go about ensuring that the user is only redirected for this reason once. My initial thought was to do something like if(path !== "/play") redirect("/play") (/play is the page with the game interface on) but I have been having trouble accessing the 'current path' from within the server side layout component.

Thanks in advance for any help 🙂
Answered by joulev
in that case
app/
  layout.tsx <- actual layout here
  (not-play)/
    layout.tsx <- redirect here
  play/
    page.tsx
View full answer

10 Replies

This is my (dynamic)/layout.tsx file that attempts to redirect the user if they are in a game.

import { ReactNode } from "react";
import SessionProvider from "~/app/_components/providers/session.provider";
import { TRPCProvider } from "~/app/_components/providers/trpc.provider";
import { getServerSession } from "~/lib/lucia/util.lucia";
import { GameMaster } from "~/lib/game/GameMaster";
import { redirect } from "next/navigation";

export default async function Layout({ children }: { children: ReactNode }) {
  const { session, user } = await getServerSession();

  if (user && GameMaster.instance().getByPlayer(user.id) !== null)
    redirect("/play");

  return (
    <SessionProvider session={session} user={user}>
      <TRPCProvider>
        <div>{children}</div>
      </TRPCProvider>
    </SessionProvider>
  );
}
But then say I accessed some page (dynamic)/play/join for example, and I was in fact in a game, and hence would ideally redirect to (dynamic)/play , if my (dynamic) layout did no longer have the redirect in it, and instead some other layout did, would my page still redirect?
you cannot redirect from a layout to itself so you have to reorganise your files
you can redirect from the layout or from the page or from the middleware etc.
@joulev you can redirect from the layout or from the page or from the middleware etc.
Which layout are you referring to when you say ‘the layout here’ sorry? Ideally I’d just have my whole app covered such that if a user enters the site but they are in a game, the only page they can access is the page /play
Answer
Ahhhh I see. Thanks that is actually really smart, I’ll try implementing that structure next time I’m at my pc.
Thank you for the help! 👏