¿Por qué es necesario fijar [email protected] en el proyecto Nuxt-Auth?
Recientemente actualicé las dependencias de un proyecto Nuxt-auth, pero surgieron un montón de advertencias y la función de inicio de sesión también funcionó mal. Este artículo explica claramente la causa, por qué no se puede actualizar, si es seguro hacerlo ahora y cómo lo resolví finalmente, basándome en mi propia experiencia.
Renderizando...
# Por qué es obligatorio fijar [email protected] en los proyectos Nuxt Recientemente, al actualizar las dependencias de un proyecto Nuxt-auth, aparecieron una gran cantidad de advertencias y el funcionamiento del inicio de sesión se volvió anómalo. Superficialmente, parece un problema de conflicto entre `@sidebase/nuxt-auth` y `next-auth`, pero en realidad es un viejo problema donde las estrategias de exportación de los paquetes Nuxt, Nitro y NextAuth chocan. Este artículo explica la razón, por qué no se puede actualizar, si es seguro hacerlo ahora y cómo lo resolví finalmente, basándome en mi propia experiencia. ## Fenómenos Observados Inicialmente Después de actualizar las dependencias e iniciar el servicio de desarrollo, Nitro genera advertencias continuas durante la fase de empaquetado, similares a: ```text WARN "next-auth/providers/google" is imported by "server/api/auth/[...].ts", but could not be resolved – treating it as an external dependency. WARN "next-auth/providers/credentials" is imported by "server/api/auth/[...].ts", but could not be resolved – treating it as an external dependency. WARN "next-auth/providers/github" is imported by "server/api/auth/[...].ts", but could not be resolved – treating it as an external dependency. WARN "next-auth/jwt" is imported by ".../@sidebase/nuxt-auth/.../nuxtAuthHandler.js", but could not be resolved – treating it as an external dependency. WARN "next-auth/core" is imported by ".../@sidebase/nuxt-auth/.../nuxtAuthHandler.js", but could not be resolved – treating it as an external dependency. ``` Las advertencias parecen decir "si no se puede resolver, considéralo una dependencia externa". Mucha gente las ignora como ruido. Luego, el inicio de sesión deja de funcionar: no hay respuesta con nombre de usuario y contraseña, y las redirecciones de GitHub / Google tampoco funcionan. Intenté dos cosas que "deberían funcionar según lo esperado", pero el resultado fue el mismo: 1. Actualizar `next-auth` a 4.22+, 4.24, o incluso 5. 2. No declarar `next-auth` en el proyecto, esperando que `@sidebase/nuxt-auth` lo traiga consigo. Ambos caminos conducen a advertencias similares y el inicio de sesión sigue fallando. ## Primer Malentendido: nuxt-auth No Incluye next-auth Por Sí Mismo `@sidebase/nuxt-auth` no es un núcleo de autenticación completo, sino una capa de adaptación para Nuxt. La ruta `authjs`, que realmente emite JWT, maneja OAuth y proporciona Google / GitHub / Credenciales, es `next-auth`. Puedes confirmarlo mirando su `package.json`: ```json { "peerDependencies": { "next-auth": "~4.21.1" }, "peerDependenciesMeta": { "next-auth": { "optional": true } } } ``` Hay tres puntos clave: - Es una dependencia **peer**, no una dependencia empaquetada. El código fuente del módulo `import "next-auth/core"`, y en tiempo de ejecución debe buscar este paquete en tu proyecto. - La versión es `~4.21.1`, que solo permite 4.21.x, no `^4`. - También está marcado como **opcional**. Esto se debe a que el módulo tiene un proveedor `local` que puede no conectarse a Auth.js. Si eliges `authjs`, opcional no significa "no es necesario instalarlo". El Quick Start oficial es muy directo: además de npm, debes instalarlo tú mismo, y especifica la versión: ```bash pnpm i [email protected] ``` La documentación también advierte: debido a los cambios disruptivos de NextAuth, **nuxt-auth solo es compatible con versiones anteriores a 4.23.0**, y se recomienda fijar `4.21.1`. Por lo tanto, "usar la versión incluida con el módulo" casi siempre fallará en proyectos pnpm. pnpm es estrictamente aislado: si no incluyes `next-auth` en tus propias `dependencies`, no estará en el directorio `node_modules` raíz. Cuando Nitro intente resolver `next-auth/providers/google`, no lo encontrará y solo podrá marcarlo como externo; luego, cuando Node intente `import` en tiempo de ejecución, el paquete no estará allí y la cadena de inicio de sesión se interrumpirá directamente. npm a veces eleva los paquetes peer a la raíz, haciendo que parezca que "funciona sin declararlo". Cambiar a pnpm / yarn revelará la verdad. Esto no es un error del gestor de paquetes, sino un comportamiento esperado cuando se combinan peer + opcional + aislamiento estricto. ## ¿Qué Significa Realmente Esa Cadena de WARN? Esto no es ESLint, es **Nitro / Vite / Rollup fallando al resolver durante el empaquetado del paquete del servidor**. Dos cadenas de importación intentan buscar subrutas de `next-auth` simultáneamente: - Tu ruta catch-all: `next-auth/providers/google`, `github`, `credentials` - El `NuxtAuthHandler` interno del módulo: `next-auth/core`, `next-auth/jwt` Si la resolución tiene éxito, estos módulos se incluirán en el producto de Nitro. Si falla, el empaquetador dirá "tratar como dependencia externa", lo que significa: no te preocupes durante la construcción, deja que Node lo busque en `node_modules` en tiempo de ejecución. Esto crea una experiencia muy confusa: la construcción "tiene éxito", solo con advertencias amarillas; pero cuando el worker se inicia o intentas iniciar sesión, aparece `Cannot find package 'next-auth'` o `Package subpath './core' is not defined by "exports"`. Las WARN son el síntoma. La causa raíz es: **la subruta o no existe en la versión de `next-auth` instalada actualmente, o está oculta por `exports`.** ## ¿Por Qué Exactamente 4.21.1? El handler de `@sidebase/nuxt-auth` hace referencia directa a puntos de entrada internos de NextAuth que en ese momento aún eran públicos: `next-auth/core` y `next-auth/jwt`. `4.21.1` todavía trata estas subrutas como módulos importables. A partir de **4.23.0**, NextAuth restringió las `exports` de su `package.json`, eliminando rutas internas como `./core` de las exportaciones públicas, preparándose para Auth.js / v5. Cuando Nitro intenta resolverlo de la manera anterior, se produce: ```text Package subpath './core' is not defined by "exports" ``` El propio issue de sidebase lo confirma: [NextAuth >= v4.23.0 Breaking change](https://github.com/sidebase/nuxt-auth/issues/514). El mantenedor admitió más tarde: tuvieron que reescribir el módulo según la nueva arquitectura, y después de eso ya no sería compatible con versiones anteriores a 4.23; sin embargo, esta reescritura en la versión 1.x aún no se ha lanzado como una solución estable. Por lo tanto, la versión 1.x sigue fijando el peer en `~4.21.1`. `next-auth@5` es aún más drástico: la estructura del paquete, las rutas de los proveedores y la API del handler han cambiado. `@sidebase/[email protected]` no puede conectarse. Hay otro detalle fácil de pasar por alto: los proveedores de 4.21.1 son CommonJS. Los proyectos Nuxt suelen ser ESM (`"type": "module"`), por lo que el ejemplo oficial debe escribirse como `.default()`: ```ts import { NuxtAuthHandler } from "#auth" import GithubProvider from "next-auth/providers/github" import CredentialsProvider from "next-auth/providers/credentials" export default NuxtAuthHandler({ secret: process.env.NUXT_AUTH_SECRET, providers: [ // @ts-expect-error Al cargar un proveedor CJS en ESM, se debe usar .default GithubProvider.default({ clientId: process.env.GITHUB_CLIENT_ID, clientSecret: process.env.GITHUB_CLIENT_SECRET, }), // @ts-expect-error CredentialsProvider.default({ name: "Credentials", credentials: { email: { label: "Email", type: "text" }, password: { label: "Password", type: "password" }, }, async authorize(credentials) { // Realiza tu propia validación aquí, devuelve el usuario o null return null }, }), ], session: { strategy: "jwt" }, pages: { signIn: "/login", }, }) ``` Esto no es una peculiaridad del proyecto, sino la interoperabilidad al importar proveedores CJS en el servidor ESM. Una vez que la versión prioriza ESM, `.default` a menudo es `undefined`, el proveedor no se registra en absoluto, y el inicio de sesión falla silenciosamente de otra manera. La configuración de Nuxt correspondiente solo necesita declarar el uso de Auth.js: ```ts export default defineNuxtConfig({ modules: ["@sidebase/nuxt-auth"], auth: { originEnvKey: "NUXT_AUTH_BASE_URL", provider: { type: "authjs", trustHost: false, addDefaultCallbackUrl: true, }, }, }) ``` Se recomienda mantener `trustHost: false`. En entornos de producción, configura `NUXT_AUTH_BASE_URL` con la URL completa, por ejemplo `https://example.com/api/auth`, no solo la raíz del dominio. ## Dos Operaciones Erróneas, ¿Por Qué Ambas Fallan? **No declarar `next-auth`.** pnpm no elevará un peer opcional a las dependencias raíz de tu aplicación. Tu `server/api/auth/[...].ts` y el `nuxtAuthHandler.js` interno fallarán simultáneamente al resolverse. Esto es el mismo tipo de problema que en los issues de sidebase [#748](https://github.com/sidebase/nuxt-auth/issues/748) y [#877](https://github.com/sidebase/nuxt-auth/issues/877). **Cambiar a 4.22+ / 4.24 / 5.** El paquete se instala, pero `exports` ya no exporta `./core`. Nitro también falla al resolver, y en tiempo de ejecución se convierte en `ERR_PACKAGE_PATH_NOT_EXPORTED`. El inicio de sesión sigue sin funcionar. El escáner puede detenerse temporalmente, pero la aplicación se rompe. No escribas `^4.21.1` en `package.json`. `^` incluirá 4.22, 4.23, 4.24. Lo correcto es la tilde o la versión exacta: ```json { "dependencies": { "@sidebase/nuxt-auth": "1.3.1", "next-auth": "~4.21.1" } } ``` Después de instalar, verifica la versión real con el gestor de paquetes para evitar que se añada otra versión silenciosamente en el lockfile: ```bash pnpm ls next-auth ``` Deberías ver `[email protected]`. Luego, ejecuta `nuxt prepare` de nuevo / reinicia el desarrollo, y la cadena "treating it as an external dependency" debería desaparecer, permitiendo que la ruta de inicio de sesión se incluya correctamente en Nitro. ## ¿Hay Nuevas Versiones Que Se Puedan Actualizar Juntas? En el momento de escribir este artículo (septiembre de 2026), la situación es la siguiente: | Elemento | Estado | | -------------------------------- | --------------------------------- | | `@sidebase/nuxt-auth` versión estable | `1.3.1` (30-06-2026), es la última | | peer | Sigue siendo `next-auth@~4.21.1` | | sidebase 2.0 | En el roadmap, no en npm | | Oficial `@auth/nuxt` | La documentación de Auth.js sigue marcando Open PR | 1.3.x corrige el propio módulo de refresco, cookies y compatibilidad con Nuxt 4, **no libera** el bloqueo de versión de `next-auth`. Actualizar nuxt-auth de 1.1 a 1.3 no resuelve las WARN de este artículo. Sidebase planeaba cambiar a Auth.js v5 en la versión 2.0, las discusiones relacionadas están en [Roadmap #1028](https://github.com/sidebase/nuxt-auth/issues/1028) y [Migration #673](https://github.com/sidebase/nuxt-auth/issues/673). Han realizado al menos dos rondas de PR de migración, pero se detuvieron debido a la inestabilidad de `@auth/core` / `oauth4webapi`. El mantenedor dijo públicamente: no estaban seguros de la estabilidad de Auth.js en ese momento y no querían lanzar una versión estable con dependencias defectuosas. Más tarde, Auth.js se fusionó con Better Auth. Alguien sugirió que sidebase migrara directamente a él, pero el mantenedor se negó: Auth.js puede tener sesiones JWT sin base de datos, mientras que Better Auth requiere sesiones de base de datos por defecto, no es solo un cambio de nombre de paquete. El encapsulado actual de Better Auth en la comunidad Nuxt también está en sus primeras etapas. Por lo tanto, hoy no hay una actualización síncrona de "solo cambiar el número de versión, sin tocar el código de inicio de sesión del negocio". Salir de 4.21.1 significa esencialmente cambiar el núcleo de autenticación: esperar sidebase 2.0, o migrar tú mismo a `nuxt-auth-utils` / Better Auth y reescribir el handler, `signIn`, y la lectura de sesiones y cookies. Eso es migrar un proyecto, no actualizar una dependencia. ## ¿Es Seguro Fijar en 4.21.1? Esta era mi mayor preocupación antes de decidir "no tocar por ahora". La respuesta debe dividirse, no dejarse llevar por el texto rojo de `npm audit`. Los escáneres casi siempre informarán: - `next-auth < 4.24.5`: [CVE-2023-48309](https://github.com/advisories/GHSA-v64w-49xw-qq89), falsificación de usuario vacío - `next-auth < 4.24.15`: [CVE-2026-73419](https://github.com/advisories/GHSA-x445-f3h2-j279), confusión de proveedor OAuth Ambos parches están en 4.24.x, pero 4.24.x hace que el inicio de sesión de nuxt-auth actual falle. Por lo tanto, la pregunta se convierte en: **¿Estas vulnerabilidades afectan a la ruta Nuxt?** **CVE-2023-48309 es en gran medida inaplicable a NuxtAuth.** Solo afecta al middleware `withAuth` predeterminado de Next.js, el tipo de escritura que solo verifica "si hay sesión". Un atacante podría usar un JWT incompleto para parecer conectado, pero sin correo electrónico ni permisos. El mantenedor de sidebase escribió específicamente sobre esto: no usan el middleware de Next, sino las herramientas de sesión de Nuxt / h3. El mantenedor marcó este problema como no afectando al módulo en [#1001](https://github.com/sidebase/nuxt-auth/issues/1001). En el archivo de bloqueo, a menudo aparecerá `next@13`. Ese es el peer de `[email protected]`, no tu servidor web. Las aplicaciones Nuxt no ejecutarán Next Server Actions, y las vulnerabilidades de SSRF de Next informadas por el escáner generalmente no son el vector de ataque HTTP de este sitio. **CVE-2026-73419 coincide con la versión, pero las condiciones completas de explotación son muy estrictas.** 4.21.1 cae dentro del rango afectado. La descripción oficial requiere cumplir simultáneamente: múltiples proveedores OAuth, **con el usuario ya conectado**, vincular el segundo proveedor al usuario actual, y al menos un proveedor de redirección que pueda pasar sin PKCE. Si solo inicias OAuth en la página de inicio de sesión, no tienes una entrada para "vincular otra cuenta después de iniciar sesión", y no tienes el tipo de `linkAccount` de NextAuth Adapter, el riesgo real es mucho menor de lo que dice el escáner. Este es un riesgo teórico debido a la antigüedad de la biblioteca, no algo que "debe descontinuarse inmediatamente". Mi conclusión para mí mismo es: - **Se puede seguir usando** `@sidebase/[email protected]` + `[email protected]` - Considerar las advertencias de audit como conocidas, evaluadas y temporalmente no corregidas - No actualizar `next-auth` solo para eliminar el texto rojo Lo que realmente debes proteger son los usos, no el número de versión en sí: - Usa una cadena aleatoria suficientemente larga para `NUXT_AUTH_SECRET`; debería fallar si no hay clave al iniciar. - Mantén `trustHost` en `false`, no confíes ciegamente en los encabezados de reenvío de Host. - Configura `NUXT_AUTH_BASE_URL` como una dirección absoluta que incluya `/api/auth`. - El middleware frontal solo se encarga de redirigir a la página de inicio de sesión; la autorización de la interfaz debe volver a verificar la sesión en el servidor y, al menos, confirmar la existencia de campos de identificación del usuario, y las interfaces de administración también deben verificar los roles. - Usa HTTPS en producción; solo así las cookies de sesión pueden funcionar con los prefijos de seguridad de Auth.js. También debes aceptar una limitación estructural: `next-auth` v4 está en modo de mantenimiento. Si en el futuro aparece una nueva vulnerabilidad que afecte al **núcleo de verificación de JWT o de redirección OAuth**, y sidebase sigue fijado en 4.21.1, entonces no será algo que `pnpm update` pueda solucionar, sino que requerirá un cambio de pila. Es más honesto registrar esto en la lista de deuda técnica que fingir que el escáner está en verde. ## El Plan Que Adopté Finalmente El plan es en realidad muy simple, tan simple que va en contra del instinto de "actualizar dependencias". 1. Añade explícitamente `next-auth@~4.21.1` a las `dependencies` de tu propia aplicación, alineándote con el peer de `@sidebase/nuxt-auth`. 2. Cuando uses un gestor de paquetes como pnpm, no asumas que los peers se elevarán automáticamente. 3. En la ruta catch-all, importa los proveedores de la manera oficial, usando `.default()` para la interoperabilidad CJS. 4. No cambies `next-auth` a `^4` o `5`, ni lo elimines. 5. Registra las dos CVE de next-auth del `npm audit` como "ruta Nuxt evaluada, no se puede actualizar con la versión del parche". 6. Espera a sidebase 2.0 o prepárate para realizar una migración de autenticación por separado, sin vincularla a las actualizaciones de dependencias diarias. La verificación es directa: después de reiniciar el desarrollo, Nitro ya no debería tratar `next-auth/core`, `next-auth/jwt`, o `next-auth/providers/*` como externos; el nombre de usuario/contraseña y las redirecciones OAuth deberían completarse; y `pnpm ls next-auth` solo debería mostrar 4.21.1. ## Si Alguna Vez Debo Salir de 4.21.1 No hay una tercera vía de "solo actualizar la versión". Las opciones que me dejo son: 1. **Seguir fijando.** El módulo todavía se mantiene y funciona con Nuxt 4. El precio es permanecer para siempre en NextAuth v4. 2. **Esperar sidebase 2.0.** La versión oficial dijo que migraría a Auth.js v5, pero no hay un cronograma estable al que adherirse, ni una etiqueta de distribución npm utilizable en producción. 3. **Cambiar de pila y reescribir.** La dirección oficial de Nuxt es `nuxt-auth-utils` (sesión de cookie cifrada, OAuth requiere que lo conectes tú mismo); o Better Auth. Ambas requieren reescribir el punto de entrada de inicio de sesión, la forma de la sesión y las redirecciones; las sesiones existentes se perderán. Antes de eso, trataré esta combinación de versiones como una capa congelada de la infraestructura de inicio de sesión: puedo corregir mis propias páginas y lógica de autorización, pero no "organizar" `next-auth`. ## Conclusión La razón por la que esto es complicado es que va en contra de la intuición de la gestión de dependencias: el escáner dice que es antiguo, la documentación dice que lo fijes, la construcción solo advierte pero no falla, y el fallo ocurre al iniciar sesión. Una vez que las tres cosas se separan, todo se aclara: - El **fallo de resolución** proviene del aislamiento de pnpm, además de que NextAuth ya no exporta `./core` a partir de la versión 4.23. - La **imposibilidad de actualizar** se debe a que `@sidebase/[email protected]` todavía depende de esos puntos de entrada internos, y la versión 2.0 aún no se ha entregado. - **Se puede seguir usando** porque la CVE más escaneada afecta al middleware predeterminado de Next.js, no a las herramientas de sesión propias de NuxtAuth; y el nuevo mix-up de OAuth depende de si tienes una ruta de "vincular otra cuenta después de iniciar sesión". Por lo tanto, escribo la solución como una frase que puedo ejecutar: en el proveedor `authjs` de Nuxt, fija `[email protected]` como una dependencia de primera clase, considera las advertencias de audit como deuda conocida, y deja la actualización real para la próxima migración de autenticación.
Comentario
Inicia sesión para ver y publicar comentarios
Ir a iniciar sesión