# Proteção de Rotas

Por
Willyan Marques
Em 
Publicado 2024-02-28

O next oferece a possibilidade da criação de arquivos layout.tsx para configuração de páginas que estão dentro de determinadas rotas/pastas.

Além disso, também podemos criar grupos de rotas capazes de ocultar parte dos endereços de acesso para o usuário. Para isso, basta criarmos uma pasta de rota nomeada entre parênteses. Por exemplo, podemos separar nossas rotas em dois tipos agrupando todas páginas que necessitam de autenticação em uma única rota (auth) e rotas públicas em (public).

Utilizando esses dois recursos juntamente com o NextAuth, podemos criar rotas seguras que agrupam determinadas páginas protegidas por login. Para isso, podemos criar um arquivo layout.tsx como no exemplo abaixo:

src/app/(auth)/(user)/layout.tsx
import { getServerAuthSession } from "~/server/auth";
import { permanentRedirect } from "next/navigation";
import { AuthProvider } from "~/components/authProvider";

export default async function AuthLayout({
  children,
}: {
  children: React.ReactNode,
}) {
  const session = await getServerAuthSession();

  if (session?.user) {
    //permanentRedirect não deixa retornar
    permanentRedirect("/login");
  }

  return (
    <>
      <AuthProvider>{children}</AuthProvider>;
    </>
  );
}

Nesse exemplo, temos um grupo de rotas chamado (user) que agrupa todas páginas relacionadas ao perfil de um usuário qualquer. O componente AuthProvider engloba o children para que as páginas tenham acesso a sessão no client-side. Além disso, o layout pega o session no server-side e define que para acessar a rota, uma sessão precisa existir. Ou seja, o usuário deve estar estar logado senão ele é redirecionado para a página de login.

Dentro do grupo (user), podemos ter uma página para o perfil do usuário (user)/profile/page.tsx.

src/app/(auth)/(user)/profile/page.tsx
import { getServerAuthSession } from "~/server/auth";

export default async function ProfilePage() {
  const session = await getServerAuthSession();
  return (
    <>
      <h1>Página do Usuário</h1>

      <span>Meu Nome: {session?.user.name}</span>
      <span>Meu Email: {session?.user.email}</span>
      <span>Minha Senha: LOL</span>
    </>
  );
}

Também podemos criar uma nova rota para uma página de login login/page.tsx. Nessa página de login, de maneira análoga ao layout, direcionamos o usuário para seu perfil caso ele já esteja logado.

src/app/(public)/login/page.tsx
import { permanentRedirect } from "next/navigation";
import SessionControlButton from "~/components/user/signIn";
import { getServerAuthSession } from "~/server/auth";

export default async function LoginPage() {
  const session = await getServerAuthSession();

  if (session?.user) {
    permanentRedirect(`/profile`);
  }

  return (
    <>
      <h1>Página de Login Foda</h1>
      <SessionControlButton />
    </>
  );
}