From c6555f1b0a3fd6033be19682434f7d6ccdb761b7 Mon Sep 17 00:00:00 2001 From: evelina <91142355+135ze@users.noreply.github.com> Date: Sat, 21 Sep 2024 17:51:00 -0400 Subject: [PATCH] add unstyled teacher profile page with gauth info and x/10 absences --- app/api/users/[id]/route.ts | 40 ++++++++++++++++++ app/api/users/email/[email]/route.ts | 56 +++++++++++++++++++++++++ app/api/users/route.ts | 9 ++++ src/pages/profile.tsx | 63 ++++++++++++++++++++++++++++ 4 files changed, 168 insertions(+) create mode 100644 app/api/users/[id]/route.ts create mode 100644 app/api/users/email/[email]/route.ts create mode 100644 app/api/users/route.ts create mode 100644 src/pages/profile.tsx diff --git a/app/api/users/[id]/route.ts b/app/api/users/[id]/route.ts new file mode 100644 index 0000000..013c3b5 --- /dev/null +++ b/app/api/users/[id]/route.ts @@ -0,0 +1,40 @@ +import { PrismaClient } from '@prisma/client'; +import { NextRequest, NextResponse } from 'next/server'; + +const prisma = new PrismaClient(); + +export async function GET(req: NextRequest, params) { + // GETABSENCES + const { searchParams } = new URL(req.url); + const encodedAbsences = searchParams.get('getAbsences'); + let getAbsences = false; + if (encodedAbsences) { + getAbsences = Boolean(decodeURIComponent(encodedAbsences)); + } + + // ID + if (!params || !params.params || !params.params.id) { + return new NextResponse('Invalid id provided', { status: 400 }); + } + + const id = params.params.id; + + if (Number.isNaN(id)) { + return new NextResponse('ID not a number', { status: 400 }); + } + + try { + const user = await prisma.user.findUnique({ + where: { id }, + include: { absences: getAbsences }, + }); + + if (!user) { + return new NextResponse('User not found', { status: 400 }); + } else { + return new NextResponse(JSON.stringify(user), { status: 200 }); + } + } catch (error) { + return new NextResponse('Internal server error', { status: 500 }); + } +} diff --git a/app/api/users/email/[email]/route.ts b/app/api/users/email/[email]/route.ts new file mode 100644 index 0000000..4ed4738 --- /dev/null +++ b/app/api/users/email/[email]/route.ts @@ -0,0 +1,56 @@ +import { PrismaClient } from '@prisma/client'; +import { NextRequest, NextResponse } from 'next/server'; + +const prisma = new PrismaClient(); + +export async function GET(req: NextRequest, params) { + // GETABSENCES + const { searchParams } = new URL(req.url); + const encodedAbsences = searchParams.get('getAbsences'); + let getAbsences = false; + if (encodedAbsences) { + getAbsences = Boolean(decodeURIComponent(encodedAbsences)); + } + + // EMAIL + if (!params || !params.params || !params.params.email) { + return new NextResponse('Invalid email provided', { status: 400 }); + } + + // TODO: rename realEmail to email to be used in the findUnique later + const realEmail = params.params.email; + + try { + // TODO: remove once emails are set up + // fake stuff begins + // find random email in db for now + const useFake = true; + const fakeEmailReq = await prisma.user.findFirst({ + select: { + email: true, + }, + }); + let email; + if (!fakeEmailReq) { + return new NextResponse('DEV ERROR: local db not seeded!', { + status: 400, + }); + } else { + email = useFake ? fakeEmailReq.email : realEmail; + } + // fake stuff ends + + const user = await prisma.user.findUnique({ + where: { email }, + include: { absences: getAbsences }, + }); + + if (!user) { + return new NextResponse('User not found', { status: 400 }); + } else { + return new NextResponse(JSON.stringify(user), { status: 200 }); + } + } catch (error) { + return new NextResponse('Internal server error', { status: 500 }); + } +} diff --git a/app/api/users/route.ts b/app/api/users/route.ts new file mode 100644 index 0000000..34d2055 --- /dev/null +++ b/app/api/users/route.ts @@ -0,0 +1,9 @@ +import { PrismaClient } from '@prisma/client'; +import { NextResponse } from 'next/server'; + +const prisma = new PrismaClient(); + +export async function GET() { + const users = await prisma.user.findMany(); + return NextResponse.json(users); +} diff --git a/src/pages/profile.tsx b/src/pages/profile.tsx new file mode 100644 index 0000000..b2b4ad6 --- /dev/null +++ b/src/pages/profile.tsx @@ -0,0 +1,63 @@ +import { useSession } from 'next-auth/react'; +import { useEffect, useState } from 'react'; +import { SignOutButton } from '../components/SignOutButton'; + +export default function AnotherPage() { + const { data: session, status } = useSession(); + const [numAbsences, setNumAbsences] = useState(null); + const [usedAbsences, setUsedAbsences] = useState(null); + + useEffect(() => { + const fetchUserInfoByEmail = async () => { + if (!session || !session.user || !session.user.email) return; + + const email = session.user.email; + const apiUrl = `/api/users/email/${email}?getAbsences=true`; + + try { + const response = await fetch(apiUrl); + if (!response.ok) { + throw new Error(response.statusText); + } + const data = await response.json(); + setNumAbsences(data['numOfAbsences']); + setUsedAbsences(data['absences'].length); + } catch (error) { + console.error('Error fetching data:', error); + } + }; + + fetchUserInfoByEmail(); + }, [session]); + + return ( +
+

Profile

+
+ {status === 'loading' ? ( +

Loading...

+ ) : session && session.user ? ( +
+

Personal Information

+

Name: {session.user.name}

+

Email: {session.user.email}

+

Image:

+ {session.user.image && ( + User Image + )} + +
+

Metrics

+

+ Absences: {usedAbsences} / {numAbsences}{' '} +

+
+
+ ) : ( +

Error: Signed out

+ )} +
+ +
+ ); +}