83 lines
2.2 KiB
TypeScript
83 lines
2.2 KiB
TypeScript
import { getUserIdFromSession } from '../../../utils/auth';
|
|
|
|
interface CompletionResponse {
|
|
message: string;
|
|
reward: {
|
|
coins: number;
|
|
};
|
|
updatedCoins: number;
|
|
}
|
|
|
|
/**
|
|
* Creates a Date object for the start of a given day in UTC.
|
|
* This is duplicated here as per the instruction not to create new shared utilities.
|
|
*/
|
|
function getStartOfDay(date: Date): Date {
|
|
const startOfDay = new Date(date);
|
|
startOfDay.setUTCHours(0, 0, 0, 0);
|
|
return startOfDay;
|
|
}
|
|
|
|
export default defineEventHandler(async (event): Promise<CompletionResponse> => {
|
|
const userId = await getUserIdFromSession(event);
|
|
const habitId = parseInt(event.context.params?.id || '', 10);
|
|
|
|
if (isNaN(habitId)) {
|
|
throw createError({ statusCode: 400, statusMessage: 'Invalid habit ID.' });
|
|
}
|
|
|
|
const habit = await prisma.habit.findFirst({
|
|
where: { id: habitId, userId },
|
|
});
|
|
|
|
if (!habit) {
|
|
throw createError({ statusCode: 404, statusMessage: 'Habit not found.' });
|
|
}
|
|
|
|
const today = new Date();
|
|
const dayOfWeek = today.getDay(); // 0 (Sunday) to 6 (Saturday)
|
|
if (!(habit.daysOfWeek as number[]).includes(dayOfWeek)) {
|
|
throw createError({ statusCode: 400, statusMessage: 'Habit is not active today.' });
|
|
}
|
|
|
|
// Normalize date to the beginning of the day for consistent checks
|
|
const startOfToday = getStartOfDay(new Date()); // Correctly get a Date object
|
|
|
|
const existingCompletion = await prisma.habitCompletion.findFirst({
|
|
where: {
|
|
habitId: habitId,
|
|
date: startOfToday, // Use precise equality check
|
|
},
|
|
});
|
|
|
|
if (existingCompletion) {
|
|
throw createError({ statusCode: 409, statusMessage: 'Habit already completed today.' });
|
|
}
|
|
|
|
const rewardCoins = 3;
|
|
const [, updatedUser] = await prisma.$transaction([
|
|
prisma.habitCompletion.create({
|
|
data: {
|
|
habitId: habitId,
|
|
date: startOfToday, // Save the normalized date
|
|
},
|
|
}),
|
|
prisma.user.update({
|
|
where: { id: userId },
|
|
data: {
|
|
coins: {
|
|
increment: rewardCoins,
|
|
},
|
|
},
|
|
}),
|
|
]);
|
|
|
|
return {
|
|
message: 'Habit completed successfully!',
|
|
reward: {
|
|
coins: rewardCoins,
|
|
},
|
|
updatedCoins: updatedUser.coins,
|
|
};
|
|
});
|