feat(阶段3): oj 侧端点铺开(基线提交,未经评审)

由外部 agent (Codex) 在本会话额度中断期间完成。原样提交作为基线,
后续修复单独成 commit,便于区分与回退。

覆盖 oj 侧 65 个端点,新增 9 组路由(account/achievement/ai/classroom/
content/contest/flowchart/problemset/site)与对应 Zod 契约。

已核验:tsc --noEmit 退出码 0;API 可启动;/api/problems 返回真实数据;
judge 与 flowchart worker 均 ready。
未核验:权限边界与数据泄露,评审进行中。

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
xuyueandClaude Opus 5 committed 2026-08-07 01:25:36 -06:00
1 parent ec274419c3
commit 8c00cdc947
52 files changed
+4273 -300

No files matched your search

+51
View File
@@ -0,0 +1,51 @@
import { z } from "zod"
export const achievementRaritySchema = z.enum(["bronze", "silver", "gold", "platinum"])
export const achievementSchema = z.object({
id: z.number().int(),
name: z.string(),
description: z.string(),
icon: z.string(),
rarity: achievementRaritySchema,
hidden: z.boolean(),
metric: z.string().nullable(),
operator: z.enum(["gte", "lte"]).nullable(),
threshold: z.number().int().nullable(),
unlocked: z.boolean(),
unlockTime: z.string().nullable(),
backfilled: z.boolean(),
progress: z.number().nullable(),
unlockRate: z.number(),
})
export const achievementListSchema = z.object({
username: z.string(),
achievements: z.array(achievementSchema),
})
export const pendingAchievementSchema = z.object({
id: z.number().int(),
name: z.string(),
description: z.string(),
icon: z.string(),
rarity: achievementRaritySchema,
})
export const achievementSummarySchema = z.object({
username: z.string(),
total: z.number().int(),
unlocked: z.number().int(),
percent: z.number(),
rarity: z.array(z.object({
rarity: achievementRaritySchema,
label: z.string(),
total: z.number().int(),
unlocked: z.number().int(),
})),
recent: z.array(pendingAchievementSchema),
})
export const markAchievementsReadSchema = z.object({
ids: z.array(z.number().int()),
})