Add diashow and styling
This commit is contained in:
@@ -1,205 +0,0 @@
|
||||
import { useValidatedParams, z, zh } from 'h3-zod';
|
||||
import prisma from '~~/lib/prisma';
|
||||
|
||||
export default defineEventHandler(async (event) => {
|
||||
// TODO: re-enable perms
|
||||
// const user = await requireUserSession(event);
|
||||
//
|
||||
// if (user.user.role !== 'ADMIN') {
|
||||
// throw createError({
|
||||
// status: 403,
|
||||
// statusText: 'Not allowed!'
|
||||
// });
|
||||
// }
|
||||
// const userId = user.user.id;
|
||||
const { huntId } = await useValidatedParams(
|
||||
event,
|
||||
z.object({
|
||||
huntId: zh.numAsString
|
||||
})
|
||||
);
|
||||
|
||||
const _hunt = await prisma.hunt.findUnique({
|
||||
where: {
|
||||
id: huntId
|
||||
// OR: [
|
||||
// {
|
||||
// creatorId: userId
|
||||
// },
|
||||
// {
|
||||
// members: {
|
||||
// some: {
|
||||
// memberId: userId
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// ]
|
||||
},
|
||||
select: {
|
||||
id: true,
|
||||
name: true,
|
||||
start: true,
|
||||
end: true,
|
||||
|
||||
_count: {
|
||||
select: {
|
||||
teams: true,
|
||||
members: true,
|
||||
quests: true
|
||||
}
|
||||
},
|
||||
|
||||
teams: {
|
||||
select: {
|
||||
_count: {
|
||||
select: {
|
||||
members: true,
|
||||
answers: {
|
||||
where: {
|
||||
review: {
|
||||
score: { gt: 0 }
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
id: true,
|
||||
name: true,
|
||||
description: true,
|
||||
answers: {
|
||||
select: {
|
||||
review: {
|
||||
select: {
|
||||
score: true
|
||||
}
|
||||
}
|
||||
},
|
||||
where: {
|
||||
review: {
|
||||
score: { not: null }
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
quests: {
|
||||
select: {
|
||||
id: true,
|
||||
title: true,
|
||||
question: true,
|
||||
textSolution: true,
|
||||
points: true,
|
||||
extraPoints: true,
|
||||
|
||||
answers: {
|
||||
select: {
|
||||
id: true,
|
||||
text: true,
|
||||
review: {
|
||||
select: {
|
||||
score: true
|
||||
}
|
||||
},
|
||||
|
||||
picture: {
|
||||
select: {
|
||||
url: true,
|
||||
createdAt: true,
|
||||
creator: {
|
||||
select: {
|
||||
id: true,
|
||||
name: true
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
team: {
|
||||
select: {
|
||||
id: true,
|
||||
name: true
|
||||
}
|
||||
}
|
||||
},
|
||||
where: {
|
||||
review: {
|
||||
showcase: true
|
||||
}
|
||||
},
|
||||
orderBy: [
|
||||
{
|
||||
review: {
|
||||
rankingValue: { sort: 'asc', nulls: 'last' }
|
||||
}
|
||||
},
|
||||
{
|
||||
review: {
|
||||
score: { sort: 'asc', nulls: 'last' }
|
||||
}
|
||||
},
|
||||
{ createdAt: 'asc' }
|
||||
]
|
||||
}
|
||||
},
|
||||
where: {
|
||||
OR: [
|
||||
{
|
||||
answers: {
|
||||
some: {
|
||||
review: {
|
||||
showcase: true
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
// TODO: showcase solutions to quests
|
||||
// {
|
||||
// textSolution: { not: null }
|
||||
// }
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
if (!_hunt) {
|
||||
throw createError({ status: 404, statusText: 'Not found!' });
|
||||
}
|
||||
|
||||
const { teams, ...hunt } = _hunt;
|
||||
|
||||
const userCount = teams.reduce(
|
||||
(sum, team) => sum + team._count.members + 1,
|
||||
0
|
||||
);
|
||||
|
||||
const leaderboard = teams
|
||||
.map(({ name, id, description, answers, _count }) => ({
|
||||
name,
|
||||
id,
|
||||
description,
|
||||
answers: _count.answers,
|
||||
score: answers.reduce((sum, a) => sum + (a.review?.score || 0), 0)
|
||||
}))
|
||||
.toSorted((a, b) => b.score - a.score);
|
||||
|
||||
const totalScore = leaderboard.reduce((sum, team) => sum + team.score, 0);
|
||||
|
||||
const pictureCount = await prisma.file.count({
|
||||
where: {
|
||||
answer: {
|
||||
quest: {
|
||||
huntId
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
return {
|
||||
userCount,
|
||||
pictureCount,
|
||||
totalScore,
|
||||
leaderboard,
|
||||
...hunt
|
||||
};
|
||||
});
|
||||
Reference in New Issue
Block a user