feat(统计): 统计接口补上每人每道题的每一次提交、流程图每人最好的一次,流程图也能一次查几道题

- 新增 GET /submissions/statistics/grid:范围内每个学生的每次提交(只含普通学生,最多 5000 条),
  没选班级时附带各班花名册人数,统计页按「人 × 题」画方块串、按班级汇总
- /flowcharts/statistics 题号可以一次填几道,多返回 people(每人分数最高的那张)

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
xuyueandClaude Opus 5.5 committed 2026-09-29 18:28:27 +08:00
1 parent 99c158498c
commit f09da88ff7
8 files changed
+288 -1492

No files matched your search

+33
View File
@@ -386,6 +386,38 @@ export const submissionStatisticsItemsSchema = z.object({
truncated: z.boolean(),
})
/**
* 统计页的方块串(GET /submissions/statistics/grid):范围内每个学生的每一次提交,
* 前端按「人 × 题」排成方块串,并据此算每道题做完几人。计数口径(正确率、做完、没交)
* 仍以 submissionStatisticsSchema 为准,这里只给「每一次交了什么结果」。
*
* 只含普通学生(老师试题留下的提交不混进来),最多 5000 条最近的,超了 `truncated`。
* `classSizes` 只在没传用户名(从题目页进来、按班级汇总)时给:各班花名册人数。
*/
export const submissionStatisticsGridSchema = z.object({
/** 传了题号就按传的顺序;没传就是范围内出现过的题,按第一次有人交的时间排 */
problems: z.array(z.object({ problemDisplayId: z.string(), title: z.string() })),
rows: z.array(
z.object({
username: z.string(),
/** 剥掉 `ks<班级号>` 前缀后的那段,同 unacceptedStudentSchema.realName */
realName: z.string(),
className: z.string().nullable(),
/** 从早到晚 */
submissions: z.array(
z.object({
id: z.string(),
problemDisplayId: z.string(),
result: judgeStatusSchema,
createTime: z.string(),
}),
),
}),
),
classSizes: z.record(z.string(), z.number().int()),
truncated: z.boolean(),
})
export const submissionStatisticsSchema = z.object({
submissionCount: z.number().int(),
acceptedCount: z.number().int(),
@@ -528,6 +560,7 @@ export type SubmissionStatistics = z.infer<typeof submissionStatisticsSchema>
export type TodaySubmissionStatistics = z.infer<typeof todaySubmissionStatisticsSchema>
export type SubmissionStatisticsUser = z.infer<typeof submissionStatisticsUserSchema>
export type SubmissionStatisticsItems = z.infer<typeof submissionStatisticsItemsSchema>
export type SubmissionStatisticsGrid = z.infer<typeof submissionStatisticsGridSchema>
export type UnacceptedStudent = z.infer<typeof unacceptedStudentSchema>
export type AttemptedStudent = z.infer<typeof attemptedStudentSchema>