UNPKG

@mikandev/next-discord-auth

Version:
66 lines (65 loc) 2.94 kB
import { NextRequest, NextResponse } from "next/server"; import { headers } from "next/headers"; import { cookies } from "next/headers"; import { redirect } from "next/navigation"; import { getGlobalConfig } from "./index"; import { RefreshAccessToken } from "./lib/oauth"; import jwt from "jsonwebtoken"; export const getSession = async () => { const config = getGlobalConfig(); const cookieStore = await cookies(); const token = cookieStore.get("AUTH_SESSION")?.value; if (!token) return null; try { const session = jwt.verify(token, config.jwtSecret); if (session.expires) { const expiresAt = new Date(session.expires); if (expiresAt < new Date()) { cookieStore.delete("AUTH_SESSION"); return null; } else { const timeUntilExpiration = expiresAt.getTime() - Date.now(); if (timeUntilExpiration < 5 * 60 * 1000) { // less than 5 minutes const refreshedSession = await RefreshAccessToken(config, session.refreshToken || ""); if (refreshedSession) { session.accessToken = refreshedSession.accessToken; session.refreshToken = refreshedSession.refreshToken; session.expires = new Date(Date.now() + refreshedSession.expiresIn * 1000).toISOString(); const newToken = jwt.sign(session, config.jwtSecret); cookieStore.set("AUTH_SESSION", newToken, { sameSite: "lax", httpOnly: true, secure: true }); } } return session; } } return null; } catch (error) { console.error("Invalid token:", error); return null; } }; export const signIn = async (redirectTo) => { const config = getGlobalConfig(); const session = await getSession(); const cookieStore = await cookies(); const headersList = await headers(); const redirectUri = redirectTo ?? headersList.get("Referer") ?? "/"; await cookieStore.set("REDIRECT_AFTER", redirectUri, { sameSite: "lax", httpOnly: true, secure: true }); if (session) { return NextResponse.json({ message: "Already signed in" }, { status: 200 }); } const signInURL = `https://discord.com/api/oauth2/authorize?client_id=${config.clientId}&redirect_uri=${encodeURIComponent(config.redirectUri)}&response_type=code&scope=${config.scopes.join(" ")}`; return redirect(signInURL); }; export const signOut = async () => { const cookieStore = await cookies(); const token = cookieStore.get("AUTH_SESSION")?.value; if (!token) { return NextResponse.json({ message: "Not signed in" }, { status: 401 }); } cookieStore.delete("AUTH_SESSION"); return NextResponse.json({ message: "Signed out successfully" }, { status: 200 }); };