diff --git a/backend/src/contests/contests/contests.service.ts b/backend/src/contests/contests/contests.service.ts index 091079a..7c3ea6b 100644 --- a/backend/src/contests/contests/contests.service.ts +++ b/backend/src/contests/contests/contests.service.ts @@ -273,22 +273,23 @@ export class ContestsService { // 解析 contestTenants JSON 字符串为数组,并计算评审统计数据 const parsedList = await Promise.all( filteredList.map(async (contest) => { - // 计算总作品数(已提交的作品) + // 计算总作品数(已提交或评审中的作品) const totalWorksCount = await this.prisma.contestWork.count({ where: { contestId: contest.id, - status: 'submitted', + status: { in: ['submitted', 'reviewing'] }, isLatest: true, + validState: 1, }, }); - // 计算已完成评审的作品数(所有评委都评分的作品) - // 简化逻辑:统计有评分记录的作品数 + // 计算已完成评审的作品数(有评分记录的作品) const reviewedCount = await this.prisma.contestWork.count({ where: { contestId: contest.id, - status: 'submitted', + status: { in: ['submitted', 'reviewing'] }, isLatest: true, + validState: 1, scores: { some: { validState: 1, @@ -302,6 +303,11 @@ export class ContestsService { contestTenants: this.parseContestTenants(contest.contestTenants), totalWorksCount, reviewedCount, + // 覆盖 _count.works 为正确的统计数据(只统计 isLatest=true 且 validState=1 的作品) + _count: { + ...contest._count, + works: totalWorksCount, + }, }; }), ); diff --git a/backend/src/contests/results/results.service.ts b/backend/src/contests/results/results.service.ts index 67abf37..1b4491a 100644 --- a/backend/src/contests/results/results.service.ts +++ b/backend/src/contests/results/results.service.ts @@ -537,6 +537,15 @@ export class ResultsService { }, }, }, + scores: { + where: { validState: 1 }, + select: { + id: true, + totalScore: true, + judgeName: true, + scoreTime: true, + }, + }, }, orderBy: [ { finalScore: 'desc' }, @@ -547,6 +556,25 @@ export class ResultsService { this.prisma.contestWork.count({ where }), ]); + // 计算每个作品的评委平均分(用于显示) + const enrichedWorks = works.map((work) => { + let judgeScore: number | null = work.finalScore + ? Number(work.finalScore) + : null; + // 如果没有最终得分但有评分记录,则计算平均分作为评委评分 + if (judgeScore === null && work.scores && work.scores.length > 0) { + const totalScores = work.scores.reduce( + (sum, s) => sum + Number(s.totalScore), + 0, + ); + judgeScore = Number((totalScores / work.scores.length).toFixed(2)); + } + return { + ...work, + judgeScore, // 评委评分(平均分) + }; + }); + return { contest: { id: contest.id, @@ -554,7 +582,7 @@ export class ResultsService { resultState: contest.resultState, resultPublishTime: contest.resultPublishTime, }, - list: works, + list: enrichedWorks, total, page, pageSize, diff --git a/frontend/src/views/contests/components/WorkDetailModal.vue b/frontend/src/views/contests/components/WorkDetailModal.vue index 08e72c2..37db6ca 100644 --- a/frontend/src/views/contests/components/WorkDetailModal.vue +++ b/frontend/src/views/contests/components/WorkDetailModal.vue @@ -98,8 +98,8 @@