Ilustración que muestra el logo de Next.js junto a iconos de autenticación y seguridad representando NextAuth en el App Router.

La autenticación de usuarios es uno de los aspectos fundamentales en el desarrollo de aplicaciones web. En Next.js, contamos con diversas formas de implementar la autenticación, pero una de las librerías más sencillas y potentes para lograrlo es NextAuth.js.

En este artículo, aprenderás cómo configurar de manera rápida un sistema de login/logout, con proveedores de autenticación como Google, GitHub, e incluso la opción de credenciales personalizadas (email y contraseña). ¡Empecemos!

¿Qué es NextAuth.js?

NextAuth.js es una librería de autenticación para Next.js que te permite:

  • Conectarte a proveedores de terceros (OAuth) como Google, GitHub, Twitter y más.
  • Manejar sesiones y tokens de manera sencilla.
  • Proteger rutas (páginas) y componentes.
  • Evitar la configuración manual de cada flujo de autenticación, ahorrando tiempo y errores.

Requisitos Previos

Antes de empezar, verifica que cumples lo siguiente:

  • Tienes instalado Node.js (versión 14 o superior).
  • Cuentas con un proyecto Next.js reciente (usando create-next-app o similar).
  • Tienes acceso a crear credenciales en la consola de desarrolladores de Google o GitHub (o el proveedor OAuth que elijas).

Instalación y Configuración Inicial

Dentro de tu proyecto Next.js, abre la terminal y ejecuta:

npm install next-auth
# o
yarn add next-auth

Luego, crea un archivo .env.local en la raíz para poner tus variables de entorno. Por ejemplo:

GOOGLE_CLIENT_ID=tuGoogleId
GOOGLE_CLIENT_SECRET=tuGoogleSecret
NEXTAUTH_SECRET=unValorSecretoGenerado
  • NEXTAUTH_SECRET se usa para firmar y encriptar los tokens de sesión.
  • GOOGLE_CLIENT_ID y GOOGLE_CLIENT_SECRET los obtienes de la Consola de Google Cloud.

Creación de la Ruta API de NextAuth

NextAuth funciona a través de una API Route en tu proyecto. Crea la carpeta y archivo correspondiente, por ejemplo:

/app/api/auth/[...nextauth]/route.js

Estructura de route.js

import NextAuth from "next-auth"
import GoogleProvider from "next-auth/providers/google"

const handler = NextAuth({
  providers: [
    GoogleProvider({
      clientId: process.env.GOOGLE_CLIENT_ID,
      clientSecret: process.env.GOOGLE_CLIENT_SECRET,
    }),
  ],
  secret: process.env.NEXTAUTH_SECRET,
  // Puedes agregar callbacks, páginas personalizadas, etc.
})

export { handler as GET, handler as POST }

  • Importas NextAuth y defines tus proveedores (en este ejemplo, Google).
  • Exportas handler tanto como GET y POST para manejar solicitudes HTTP hacia /api/auth/[...nextauth].

Con esto, NextAuth gestionará las rutas /api/auth/signin, /api/auth/signout, /api/auth/callback/google, etc., automáticamente.

Utiliza Proveedores (OAuth y/o Credenciales)

Además de Google, puedes usar GitHubProvider, FacebookProvider, TwitterProvider, etc., siempre que obtengas sus Client IDs y Secrets. Por ejemplo:

import GitHubProvider from "next-auth/providers/github"

const handler = NextAuth({
  providers: [
    GoogleProvider(...),
    GitHubProvider({
      clientId: process.env.GITHUB_ID,
      clientSecret: process.env.GITHUB_SECRET,
    }),
  ],
  ...
})

Uso de Credenciales Personalizadas

Si quieres autenticar con usuario/contraseña propios, añade:

import CredentialsProvider from "next-auth/providers/credentials";

const handler = NextAuth({
  providers: [
    CredentialsProvider({
      name: "Credenciales",
      credentials: {
        email: { label: "Email", type: "text" },
        password: { label: "Contraseña", type: "password" },
      },
      async authorize(credentials, req) {
        // Lógica para verificar en tu BD, por ejemplo:
        const user = await findUserByEmail(credentials.email)
        if (user && verifyPassword(credentials.password, user.hash)) {
          return user // objeto { id, name, email... }
        }
        return null
      }
    }),
  ],
  ...
})

Autenticación en App Router: Server y Client Components

En el App Router, las páginas o layouts se pueden implementar como Client Components o Server Components.

  • Server Components: Usan getServerSession para obtener la sesión directamente en el servidor (ideal para manejar lógica sensible).
  • Client Components: Usan useSession para leer la sesión en el cliente.

Obtener Sesión en un Server Component

Ejemplo: app/dashboard/page.jsx (server component por defecto si no pones 'use client' al inicio).

import { getServerSession } from "next-auth"
import { authOptions } from "@/app/api/auth/[...nextauth]/route"

export default async function DashboardPage() {
  const session = await getServerSession(authOptions)

  if (!session) {
    return <p>No tienes acceso a esta página.</p>
  }

  return (
    <div>
      <h1>Bienvenido, {session.user.name}</h1>
    </div>
  )
}
  • Importas getServerSession y la configuración authOptions (que debes exportar desde tu route.js).
  • Obtienes la sesión en el servidor y, si no existe, muestras un mensaje o rediriges a otra página.

Usar Sesión en un Client Component

Si prefieres manejar la sesión en tiempo real (por ejemplo, para mostrar un botón “Login/Logout”), crea un componente cliente:

"use client"
import { signIn, signOut, useSession } from "next-auth/react"

export default function AuthStatus() {
  const { data: session, status } = useSession()

  if (status === "loading") return <p>Cargando...</p>
  if (!session) {
    return <button onClick={() => signIn()}>Iniciar Sesión</button>
  }
  return (
    <>
      <p>Bienvenido, {session.user.name}</p>
      <button onClick={() => signOut()}>Cerrar Sesión</button>
    </>
  )
}

Luego, incluye <AuthStatus /> en un layout o en cualquier otra parte de tu interfaz.

Tip: Para que useSession funcione en el App Router, agrega el SessionProvider en tu layout Client:

"use client"
import { SessionProvider } from "next-auth/react"

export default function RootLayout({ children }) {
  return (
    <html>
      <body>
        <SessionProvider>{children}</SessionProvider>
      </body>
    </html>
  )
}

Así podrás usar useSession en todos los componentes hijos de tu layout.

Restricción de Rutas con Middleware (Opcional)

Otra forma de proteger rutas completas es usando Middleware en Next.js:

Crea un archivo middleware.js en la raíz del proyecto:

import { getToken } from "next-auth/jwt"
import { NextResponse } from "next/server"

export async function middleware(req) {
  const token = await getToken({ req, secret: process.env.NEXTAUTH_SECRET })
  // Si no hay token y la ruta inicia con /dashboard, redirige al login
  if (!token && req.nextUrl.pathname.startsWith("/dashboard")) {
    return NextResponse.redirect(new URL("/api/auth/signin", req.url))
  }
  return NextResponse.next()
}

export const config = {
  matcher: ["/dashboard/:path*"],
}

Este middleware se ejecutará antes de cada request a las rutas definidas en matcher.

getToken verifica si existe sesión; si no, redirige a /api/auth/signin.

¡Listo! Has configurado NextAuth con el App Router de Next.js para manejar la autenticación de usuarios de forma sencilla y escalable. En resumen:

  • app/api/auth/[...nextauth]/route.js define el endpoint de autenticación usando NextAuth.
  • Utiliza getServerSession en Server Components y useSession en Client Components para gestionar sesiones.
  • (Opcional) Configura Middleware para restringir rutas a usuarios autenticados.
  • Añade más proveedores (OAuth, credenciales, etc.) según tus necesidades.

La autenticación es un pilar clave en casi cualquier aplicación web, y NextAuth simplifica muchísimo ese proceso en Next.js. ¡Ahora puedes centrarte en otras funcionalidades sin preocuparte por la complejidad del login/logout!

¿Tienes dudas o comentarios? ¡Déjalas en la sección de comentarios y con gusto te ayudaremos en la Comunidad Capo Digital!

Leave a Reply

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *

Instagram