74 lines
2.8 KiB
TypeScript
74 lines
2.8 KiB
TypeScript
import { getUserIdFromSession } from '../../../utils/auth';
|
|
import { OBSTACLE_CLEAR_COST } from '../../../utils/village';
|
|
|
|
export default defineEventHandler(async (event) => {
|
|
// 1. Get objectId from params
|
|
const objectId = parseInt(event.context.params?.id || '', 10);
|
|
if (isNaN(objectId)) {
|
|
throw createError({ statusCode: 400, statusMessage: 'Invalid object ID.' });
|
|
}
|
|
|
|
const userId = await getUserIdFromSession(event);
|
|
|
|
// 2. Find village + objects
|
|
const village = await prisma.village.findUnique({
|
|
where: { userId },
|
|
include: { objects: true }
|
|
});
|
|
|
|
if (!village) {
|
|
// This case is unlikely if user has ever fetched their village, but is a good safeguard.
|
|
throw createError({ statusCode: 404, statusMessage: 'Village not found.' });
|
|
}
|
|
|
|
// 3. Find the object
|
|
const objectToDelete = village.objects.find(o => o.id === objectId);
|
|
|
|
// 4. If not found -> 404
|
|
if (!objectToDelete) {
|
|
throw createError({ statusCode: 404, statusMessage: 'Object not found.' });
|
|
}
|
|
|
|
// 5. If OBSTACLE
|
|
if (objectToDelete.type === 'OBSTACLE') {
|
|
const cost = OBSTACLE_CLEAR_COST[objectToDelete.obstacleMetadata || 'DEFAULT'] ?? OBSTACLE_CLEAR_COST.DEFAULT;
|
|
|
|
try {
|
|
// Atomically check coins, deduct, and delete
|
|
await prisma.$transaction([
|
|
prisma.user.update({
|
|
where: { id: userId, coins: { gte: cost } },
|
|
data: { coins: { decrement: cost } },
|
|
}),
|
|
prisma.villageObject.delete({ where: { id: objectId } }),
|
|
]);
|
|
} catch (e) {
|
|
// The transaction fails if the user update fails due to insufficient coins
|
|
throw createError({ statusCode: 402, statusMessage: 'Insufficient coins to clear obstacle.' });
|
|
}
|
|
|
|
// 6. If HOUSE
|
|
} else if (objectToDelete.type === 'HOUSE') {
|
|
const houseCount = village.objects.filter(o => o.type === 'HOUSE').length;
|
|
const fieldCount = village.objects.filter(o => o.type === 'FIELD').length;
|
|
|
|
// Check if removing this house violates the worker rule
|
|
if (fieldCount > (houseCount - 1)) {
|
|
throw createError({
|
|
statusCode: 400,
|
|
statusMessage: `Cannot remove house. You have ${fieldCount} fields and need at least ${fieldCount} workers.`
|
|
});
|
|
}
|
|
|
|
// Delete the house (no cost)
|
|
await prisma.villageObject.delete({ where: { id: objectId } });
|
|
|
|
// 7. Otherwise (FIELD, ROAD, FENCE)
|
|
} else {
|
|
// Delete the object (no cost)
|
|
await prisma.villageObject.delete({ where: { id: objectId } });
|
|
}
|
|
|
|
// 8. Return success message
|
|
return { message: "Object removed successfully" };
|
|
}); |