diff --git a/app/(dashboard)/settings/page.tsx b/app/(dashboard)/settings/page.tsx index 96c05dd..43a1b8d 100644 --- a/app/(dashboard)/settings/page.tsx +++ b/app/(dashboard)/settings/page.tsx @@ -24,8 +24,10 @@ export default function SettingsPage() { {/* Settings Navigation Sidebar */}
+ // @ts-ignore setParams({ ...params, settings_tab: v }) } /> @@ -34,6 +36,7 @@ export default function SettingsPage() { {/* Main Content Area */}
} ) { try { - const session = await requireAuth(); + const session = await auth.api.getSession({ headers: await headers() }); - // For demo purposes, just return success - // In production, you'd revoke the specific session + if (!session) { + return NextResponse.json( + { error: "Unauthorized", success: false }, + { status: 401 } + ); + } + const currentToken = session.session.token; + const { sessionId } = await params; + const sessionToRevoke = await prisma.session.findUnique({ + where: { id: sessionId }, + }); + + // Prevent revoking current session + if (sessionToRevoke?.token === currentToken) { + return NextResponse.json( + { error: "Cannot revoke current session" }, + { status: 400 } + ); + } + + await prisma.session.delete({ + where: { + id: sessionId, + userId: session.user.id, + }, + }); return NextResponse.json({ message: "Session revoked successfully" }); } catch (error) { console.error("Session revoke error:", error); return NextResponse.json( { error: "Failed to revoke session" }, - { status: 500 }, + { status: 500 } ); } } diff --git a/app/api/settings/sessions/route.ts b/app/api/settings/sessions/route.ts index 6d5fddf..0a1a956 100644 --- a/app/api/settings/sessions/route.ts +++ b/app/api/settings/sessions/route.ts @@ -2,6 +2,8 @@ import { NextRequest, NextResponse } from "next/server"; import { requireAuth } from "@/lib/auth-utils"; import { prisma } from "@/lib/prisma"; import { UAParser } from "ua-parser-js"; +import { auth } from "@/lib/auth"; +import { headers } from "next/headers"; // Helper function to parse user agent and get device info function parseUserAgent(userAgent: string) { @@ -59,10 +61,15 @@ function getTimeAgo(date: Date) { export async function GET(request: NextRequest) { try { - const session = await requireAuth(); + const session = await auth.api.getSession({ headers: await headers() }); - // Get current session token from cookie - const currentToken = request.cookies.get("session")?.value; + if (!session) { + return NextResponse.json( + { error: "Unauthorized", success: false }, + { status: 401 } + ); + } + const currentToken = session.session.token; // Fetch all sessions for the user const sessions = await prisma.session.findMany({ @@ -96,8 +103,15 @@ export async function GET(request: NextRequest) { export async function DELETE(request: NextRequest) { try { - const session = await requireAuth(); - const currentToken = request.cookies.get("session")?.value; + const session = await auth.api.getSession({ headers: await headers() }); + + if (!session) { + return NextResponse.json( + { error: "Unauthorized", success: false }, + { status: 401 } + ); + } + const currentToken = session.session.token; const { searchParams } = new URL(request.url); const sessionId = searchParams.get("sessionId"); diff --git a/components/settings/settings-content.tsx b/components/settings/settings-content.tsx index 9225201..80a0420 100644 --- a/components/settings/settings-content.tsx +++ b/components/settings/settings-content.tsx @@ -56,15 +56,14 @@ import { useDisable2FA, useRevokeSession, useRevokeAllSessions, - useSettingsBilling, - useUpdateSettingsBilling, useSettingsRepositories, useDisconnectRepository, useDisconnectAllRepositories, } from "@/hooks"; +import { useTheme } from "next-themes"; interface SettingsContentProps { - activeSection: string; + activeSection: SettingsTab; hasChanges: boolean; setHasChanges: (hasChanges: boolean) => void; } @@ -74,6 +73,7 @@ export function SettingsContent({ hasChanges, setHasChanges, }: SettingsContentProps) { + const { setTheme } = useTheme(); // Real data hooks const { data: profile, isLoading: profileLoading } = useSettingsProfile(); const { data: notifications } = useSettingsNotifications(); @@ -93,8 +93,6 @@ export function SettingsContent({ const disable2FA = useDisable2FA(); const revokeSession = useRevokeSession(); const revokeAllSessions = useRevokeAllSessions(); - const { data: billing } = useSettingsBilling(); - const updateBilling = useUpdateSettingsBilling(); const disconnectRepository = useDisconnectRepository(); const disconnectAllRepositories = useDisconnectAllRepositories(); @@ -257,7 +255,8 @@ export function SettingsContent({ bio: profile.bio || "", location: profile.location || "", website: profile.website || "", - githubUrl: profile.githubUrl || "", + githubUrl: + profile?.githubUrl || `https://github.com/${profile.username}` || "", showEmail: profile.showEmail || false, showLocation: profile.showLocation !== false, }); @@ -324,7 +323,8 @@ export function SettingsContent({ bio: profile.bio || "", location: profile.location || "", website: profile.website || "", - githubUrl: profile.githubUrl || "", + githubUrl: + profile?.githubUrl || `https://github.com/${profile.username}` || "", showEmail: profile.showEmail || false, showLocation: profile.showLocation !== false, }); @@ -358,6 +358,7 @@ export function SettingsContent({ useEffect(() => { if (appearanceSettings) { setAppearanceData(appearanceSettings); + setTheme(appearanceSettings?.theme); } }, [appearanceSettings]); @@ -386,7 +387,7 @@ export function SettingsContent({ Profile Information - +
@@ -410,7 +411,7 @@ export function SettingsContent({ setProfileData({ ...profileData, name: e.target.value }); setHasChanges(true); }} - className="mt-1" + className="mt-1 border-border!" />
@@ -420,7 +421,7 @@ export function SettingsContent({ type="email" value={profile?.email || ""} disabled - className="mt-1" + className="mt-1 border-border!" />

Email cannot be changed from profile settings @@ -437,7 +438,7 @@ export function SettingsContent({ setProfileData({ ...profileData, bio: e.target.value }); setHasChanges(true); }} - className="mt-1" + className="mt-1 border-border!" rows={3} />

@@ -455,7 +456,7 @@ export function SettingsContent({ }); setHasChanges(true); }} - className="mt-1" + className="mt-1 border-border!" />
@@ -467,7 +468,7 @@ export function SettingsContent({ setProfileData({ ...profileData, website: e.target.value }); setHasChanges(true); }} - className="mt-1" + className="mt-1 border-border!" />
@@ -481,7 +482,7 @@ export function SettingsContent({ setProfileData({ ...profileData, githubUrl: e.target.value }); setHasChanges(true); }} - className="mt-1" + className="mt-1 border-border!" /> @@ -759,13 +760,7 @@ export function SettingsContent({

{session.device}

{session.location} •{" "} - {session.current - ? "Active now" - : `${Math.floor( - (Date.now() - - new Date(session.lastActive).getTime()) / - (1000 * 60 * 60) - )} hours ago`} + {session.current ? "Active now" : session.lastActive}

{session.current ? ( @@ -810,7 +805,7 @@ export function SettingsContent({ Email Notifications -
+

Review completed

@@ -831,7 +826,7 @@ export function SettingsContent({ }} />

-
+

Review failed

@@ -849,7 +844,7 @@ export function SettingsContent({ }} />

-
+

New repository added

@@ -867,7 +862,7 @@ export function SettingsContent({ }} />

-
+

Weekly summary

@@ -893,7 +888,7 @@ export function SettingsContent({ In-App Notifications -

+

AI insights available

@@ -911,7 +906,7 @@ export function SettingsContent({ }} />

-
+

Team mentions

@@ -973,7 +968,7 @@ export function SettingsContent({