reactjs - Το NextJS getServerSession(authOptions) επιστρέφει null μετά τη δήλωση των NEXTAUTH_URL και NEXTAUTH_SECRET
Προσπαθώ να κάνω ένα OAuth με τον πάροχο Google να δουλέψει με την web εφαρμογή μου Next.js 13. Αυτή τη στιγμή έχω ένα σφάλμα όπου το getServerSession(authOptions) επιστρέφει null. Έχω κοιτάξει άλλες λύσεις (όπως η συμπερίληψη ενός NEXTAUTH_URL και NEXTAUTH_SECRET στο αρχείο .env. Επίσης δοκίμασα το NEXTAUTH_URL_INTERNAL) και προσπάθησα να τις εφαρμόσω, αλλά συνεχίζω να λαμβάνω null.
Η ανακατεύθυνση στη σελίδα εισόδου της Google λειτουργεί χωρίς προβλήματα, όμως στην ανακατεύθυνση στη σελίδα '/dashboard' κάτι πάει στραβά. Καθώς έχω μια έλεγχο για να δω αν υπάρχει χρήστης/συνεδρία, συνεχίζω να λαμβάνω το σφάλμα 404 δεν βρέθηκε.
Το περιβάλλον μου:
NEXTAUTH_SECRET=randomletters
NEXTAUTH_URL=http://localhost:3000
(πίνακας εργαλείων)/πίνακας εργαλείων/σελίδα.tsx:
import { FC } from "react"
import ApiDashboard from "@/components/ApiDashboard"
import RequestApiKey from "@/components/RequestApiKey"
// import { authOptions } from "@/lib/auth"
import { db } from "@/lib/db"
import { getServerSession } from "next-auth"
import type { Metadata } from "next"
import { notFound } from "next/navigation"
import { authOptions } from "@/pages/api/auth/[...nextauth]"
export const metadata: Metadata = {
title: "Similarity API | Dashboard",
description: "Free and open-source text smilarity API",
}
const page = async () => {
const user = await getServerSession(authOptions) //<-- this is null
if (!user) return notFound() //<-- returns 404 because of this
const apiKey = await db.apiKey.findFirst({
where: { userId: user.user.id, enabled: true },
})
return (
<div className="mx-auto mt-16 max-w-7xl">
{user ? <ApiDashboard /> : <RequestApiKey />}
</div>
)
}
export default page
Μπάρα πλοήγησης :
import { getServerSession } from "next-auth/next"
import Link from "next/link"
import { FC } from "react"
import { buttonVariants } from "@/ui/Button"
import SignInButton from "@/components/ui/SignInButton"
import SignOutButton from "@/components/ui/SignOutButton"
import ThemeToggle from "./ThemeToggle"
import { authOptions } from "@/pages/api/auth/[...nextauth]"
const Navbar = async () => {
const session = await getServerSession(authOptions) //<-- null as well
return ( some stuff )
[...nextauth].ts:
import NextAuth from "next-auth"
import { db } from "@/lib/db"
import { PrismaAdapter } from "@next-auth/prisma-adapter"
import { NextAuthOptions } from "next-auth"
import GoogleProvider from "next-auth/providers/google"
function getGoogleCredentials(): { clientId: string; clientSecret: string } {
const clientId = process.env.GOOGLE_CLIENT_ID
const clientSecret = process.env.GOOGLE_CLIENT_SECRET
if (!clientId || clientId.length === 0) {
throw new Error("Missing GOOGLE_CLIENT_ID")
}
if (!clientSecret || clientSecret.length === 0) {
throw new Error("Missing GOOGLE_CLIENT_SECRET")
}
return { clientId, clientSecret }
}
export const authOptions: NextAuthOptions = {
adapter: PrismaAdapter(db),
session: {
strategy: "jwt",
},
pages: {
signIn: "/login",
},
providers: [
GoogleProvider({
clientId: getGoogleCredentials().clientId,
clientSecret: getGoogleCredentials().clientSecret,
}),
],
callbacks: {
async session({ token, session }) {
if (token) {
session.user.id = token.id
session.user.name = token.name
session.user.email = token.email
session.user.image = token.picture
}
return session
},
async jwt({ token, user }) {
const dbUser = await db.user.findFirst({
where: {
email: token.email,
},
})
if (!dbUser) {
token.id = user!.id
return token
}
return {
id: dbUser.id,
name: dbUser.name,
email: dbUser.email,
picture: dbUser.image,
}
},
async redirect() {
return "/dashboard"
},
},
}
export default NextAuth(authOptions)
Αν κάποιος έχει βρει μια λύση, παρακαλώ ενημερώστε με. Ευχαριστώ
Απάντηση #1
Στα server components του Nextjs 13, τα cookies δεν περνούν στις API διαδρομές από προεπιλογή. Η λύση που έκανα ήταν όταν στέλνεις το αίτημα να μπορείς να περάσεις τα headers μαζί με το αίτημα όπως παρακάτω. Αυτή η υλοποίηση δούλεψε για μένα.
import { headers } from "next/headers";
const res = await fetch(ENDPOINT, {
method: "GET",
cache: "no-cache",
headers: headers(),
});
