Iniciar sesión con UTILIA en Next.js
Añade el botón «Iniciar sesión con UTILIA» a una aplicación Next.js con Auth.js: UTILIA OS actúa como proveedor OpenID Connect y la configuración es mínima.
Actualizado el . 2 min de lectura
Con Auth.js (next-auth v5), UTILIA OS funciona como cualquier proveedor OpenID Connect: le das el emisor y las credenciales, y Auth.js descubre solo las direcciones de autorización, token y claves, hace PKCE y verifica el id_token. Esta guía usa Next.js con App Router.
Antes de empezar
- Activa OAuth en tu aplicación externa, con el tipo Con servidor propio (recomendado), como explica Activar OAuth en tu aplicación.
- Añade como dirección de vuelta
http://localhost:3000/api/auth/callback/utiliapara desarrollo y la de producción con tu dominio, por ejemplohttps://tu-app.com/api/auth/callback/utilia. - Ten a mano el identificador público y la clave secreta.
Instala Auth.js
Bashnpm install next-auth@betaConfigura el proveedor
Crea
auth.tsen la raíz del proyecto:TypeScriptimport NextAuth from "next-auth" export const { handlers, auth, signIn, signOut } = NextAuth({ providers: [ { id: "utilia", name: "UTILIA", type: "oidc", issuer: "https://os.utilia.ai", clientId: process.env.AUTH_UTILIA_ID, clientSecret: process.env.AUTH_UTILIA_SECRET, checks: ["pkce", "state"], }, ], })Con
type: "oidc", Auth.js leehttps://os.utilia.ai/.well-known/openid-configurationy pide por defectoopenid profile email.checksdeja explícito el uso de PKCE, que UTILIA OS exige, y destate.Añade las variables de entorno
En
.env.local:BashAUTH_UTILIA_ID=utilia_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx AUTH_UTILIA_SECRET=tu_clave_secreta AUTH_SECRET=genera_una_con_openssl_rand_base64_32AUTH_SECRETes la clave con la que Auth.js cifra sus sesiones; genérala conopenssl rand -base64 32. La clave secreta de UTILIA OS va solo aquí, nunca en código que llegue al navegador.Crea la ruta de Auth.js
En
app/api/auth/[...nextauth]/route.ts:TypeScriptimport { handlers } from "@/auth" export const { GET, POST } = handlersSi tu proyecto no tiene el alias
@/apuntando a la raíz, importaauth.tscon una ruta relativa.Pon el botón
TSX"use client" import { signIn } from "next-auth/react" export function LoginButton() { return ( <button type="button" onClick={() => signIn("utilia")}> Iniciar sesión con UTILIA </button> ) }Para darle la imagen oficial, usa el estilo de Botones y marca.
Leer la sesión
En un componente de servidor:
import { auth } from "@/auth"
export default async function Page() {
const session = await auth()
if (!session?.user) {
return <p>No has iniciado sesión.</p>
}
return (
<div>
<p>Hola, {session.user.name}</p>
<p>Correo: {session.user.email}</p>
</div>
)
}En un componente de cliente, envuelve la aplicación con SessionProvider y usa useSession:
// app/providers.tsx
"use client"
import { SessionProvider } from "next-auth/react"
export function Providers({ children }: { children: React.ReactNode }) {
return <SessionProvider>{children}</SessionProvider>
}"use client"
import { useSession } from "next-auth/react"
export function UserInfo() {
const { data: session, status } = useSession()
if (status === "loading") return <p>Cargando...</p>
if (!session) return <p>No has iniciado sesión.</p>
return <p>Hola, {session.user?.name}</p>
}session.user trae el nombre, el correo y la foto que llegan en el id_token (name, email y picture).
Cerrar sesión
"use client"
import { signOut } from "next-auth/react"
export function LogoutButton() {
return (
<button type="button" onClick={() => signOut()}>
Cerrar sesión
</button>
)
}signOut() cierra la sesión de tu aplicación. Si además guardas los tokens de UTILIA OS para llamar a sus servidores MCP, revócalos al cerrar sesión, como explica Cierre de sesión desde tu aplicación.
Si algo falla
- La autorización vuelve con un error de redirección: la dirección de vuelta del panel tiene que ser exactamente la de Auth.js,
.../api/auth/callback/utilia. invalid_cliental canjear el código: revisaAUTH_UTILIA_IDyAUTH_UTILIA_SECRET, y que la aplicación sea de tipo Con servidor propio.
Más casos en Problemas frecuentes con OAuth.