Feat: Genre system with per-genre daily puzzles
This commit is contained in:
@@ -1,78 +1,18 @@
|
||||
import { NextResponse } from 'next/server';
|
||||
import { PrismaClient } from '@prisma/client';
|
||||
import { getTodayISOString } from '@/lib/dateUtils';
|
||||
import { getOrCreateDailyPuzzle } from '@/lib/dailyPuzzle';
|
||||
|
||||
const prisma = new PrismaClient();
|
||||
|
||||
export async function GET() {
|
||||
export async function GET(request: Request) {
|
||||
try {
|
||||
const today = getTodayISOString();
|
||||
const { searchParams } = new URL(request.url);
|
||||
const genreName = searchParams.get('genre');
|
||||
|
||||
let dailyPuzzle = await prisma.dailyPuzzle.findUnique({
|
||||
where: { date: today },
|
||||
include: { song: true },
|
||||
});
|
||||
const puzzle = await getOrCreateDailyPuzzle(genreName);
|
||||
|
||||
console.log(`[Daily Puzzle] Date: ${today}, Found existing: ${!!dailyPuzzle}`);
|
||||
|
||||
if (!dailyPuzzle) {
|
||||
// Get all songs with their usage count
|
||||
const allSongs = await prisma.song.findMany({
|
||||
include: {
|
||||
puzzles: true,
|
||||
},
|
||||
});
|
||||
|
||||
if (allSongs.length === 0) {
|
||||
return NextResponse.json({ error: 'No songs available' }, { status: 404 });
|
||||
}
|
||||
|
||||
// Calculate weights: songs never used get weight 1.0,
|
||||
// songs used once get 0.5, twice 0.33, etc.
|
||||
const weightedSongs = allSongs.map(song => ({
|
||||
song,
|
||||
weight: 1.0 / (song.puzzles.length + 1),
|
||||
}));
|
||||
|
||||
// Calculate total weight
|
||||
const totalWeight = weightedSongs.reduce((sum, item) => sum + item.weight, 0);
|
||||
|
||||
// Pick a random song based on weights
|
||||
let random = Math.random() * totalWeight;
|
||||
let selectedSong = weightedSongs[0].song;
|
||||
|
||||
for (const item of weightedSongs) {
|
||||
random -= item.weight;
|
||||
if (random <= 0) {
|
||||
selectedSong = item.song;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Create the daily puzzle
|
||||
dailyPuzzle = await prisma.dailyPuzzle.create({
|
||||
data: {
|
||||
date: today,
|
||||
songId: selectedSong.id,
|
||||
},
|
||||
include: { song: true },
|
||||
});
|
||||
|
||||
console.log(`[Daily Puzzle] Created new puzzle for ${today} with song: ${selectedSong.title} (ID: ${selectedSong.id})`);
|
||||
if (!puzzle) {
|
||||
return NextResponse.json({ error: 'Failed to get or create puzzle' }, { status: 404 });
|
||||
}
|
||||
|
||||
if (!dailyPuzzle) {
|
||||
return NextResponse.json({ error: 'Failed to create puzzle' }, { status: 500 });
|
||||
}
|
||||
|
||||
return NextResponse.json({
|
||||
id: dailyPuzzle.id,
|
||||
audioUrl: `/uploads/${dailyPuzzle.song.filename}`,
|
||||
songId: dailyPuzzle.songId,
|
||||
title: dailyPuzzle.song.title,
|
||||
artist: dailyPuzzle.song.artist,
|
||||
coverImage: dailyPuzzle.song.coverImage ? `/uploads/covers/${dailyPuzzle.song.coverImage}` : null,
|
||||
});
|
||||
return NextResponse.json(puzzle);
|
||||
|
||||
} catch (error) {
|
||||
console.error('Error fetching daily puzzle:', error);
|
||||
|
||||
Reference in New Issue
Block a user