fix: 修复学生代码窃取 token、提示词链 XSS 和打分没有上限的问题

- 运行提交代码的 iframe(编辑器预览、随机评分弹窗、/submission/:id、全屏预览)
  加上 sandbox,不给 allow-same-origin,代码读不到 localStorage 里的 token
- 提示词和 AI 回复的 markdown 渲染时转义原始 HTML,链接只放行 http(s)/mailto;
  ChainModal 也改用这个渲染函数
- 打分限定 1-5 分(超出返回 422),不能给自己的提交打分

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
xuyueandClaude Opus 5.5 committed 2026-10-26 21:33:26 +08:00
1 parent 4014aaabbf
commit 73788c4595
8 files changed
+78 -34

No files matched your search

+3 -2
View File
@@ -530,9 +530,10 @@ router.post("/:id/view", (c) => {
router.put("/:id/score", async (c) => {
const user = requireUser(c)
const id = uuidParam(c, "id")
const { score } = await body(c, z.object({ score: z.number().int() }))
const { score } = await body(c, z.object({ score: z.number().int().max(5) }))
if (score <= 0) throw new HttpError(400, "分数不能为零")
orNotFound(get(`SELECT 1 FROM submission_submission WHERE id = $id`, { id }))
const sub = orNotFound(get<{ user_id: number }>(`SELECT user_id FROM submission_submission WHERE id = $id`, { id }))
if (sub.user_id === user.id) throw new HttpError(400, "不能给自己的提交打分")
const exists = get(`SELECT 1 FROM submission_rating WHERE user_id = $user_id AND submission_id = $id`, {
user_id: user.id,