- Implement user registration and login with NextAuth v5 (email/password, JWT) - Add authentication modal in UI with login/register tabs - Create user profile screen showing game statistics and history - Integrate Prisma 7 ORM with SQLite database for data persistence - Store game results (mode, path, clicks, time) in database - Auto-save completed games only when user is authenticated - Separate business logic into reusable hooks (useSoloGame, useMultiGame) - Organize UI into composable screen components (HomeScreen, SoloScreen, ProfileScreen, etc) - Add session persistence across F5 refresh for solo and multiplayer - Style auth modal, account button, and profile stats dashboard
59 lines
1.4 KiB
TypeScript
59 lines
1.4 KiB
TypeScript
import { NextRequest, NextResponse } from "next/server";
|
|
import { auth } from "../../../auth";
|
|
import { prisma } from "../../../lib/prisma";
|
|
|
|
// POST /api/games — sauvegarder une partie
|
|
export async function POST(req: NextRequest) {
|
|
const session = await auth();
|
|
if (!session?.user?.id) {
|
|
return NextResponse.json({ error: "Non connecté" }, { status: 401 });
|
|
}
|
|
|
|
const { mode, startArticle, targetArticle, path, clicks, timeSeconds, won } =
|
|
await req.json() as {
|
|
mode: string;
|
|
startArticle: string;
|
|
targetArticle: string;
|
|
path: string[];
|
|
clicks: number;
|
|
timeSeconds: number;
|
|
won: boolean;
|
|
};
|
|
|
|
const game = await prisma.game.create({
|
|
data: {
|
|
userId: session.user.id,
|
|
mode,
|
|
startArticle,
|
|
targetArticle,
|
|
path: JSON.stringify(path),
|
|
clicks,
|
|
timeSeconds,
|
|
won,
|
|
},
|
|
});
|
|
|
|
return NextResponse.json({ id: game.id });
|
|
}
|
|
|
|
// GET /api/games — historique de l'utilisateur connecté
|
|
export async function GET() {
|
|
const session = await auth();
|
|
if (!session?.user?.id) {
|
|
return NextResponse.json({ error: "Non connecté" }, { status: 401 });
|
|
}
|
|
|
|
const games = await prisma.game.findMany({
|
|
where: { userId: session.user.id },
|
|
orderBy: { playedAt: "desc" },
|
|
take: 50,
|
|
});
|
|
|
|
return NextResponse.json(
|
|
games.map((g) => ({
|
|
...g,
|
|
path: JSON.parse(g.path) as string[],
|
|
}))
|
|
);
|
|
}
|