认证方案选型
公开教程 · 无需登录

认证方案选型

本课采用服务端会话(server-side session)。浏览器 Cookie 中仅保存随机会话标识,用户、角色与班级信息保存在服务端。登出即删除对应会话记录,会话立即失效。

1服务端会话与 JWT

服务端会话 Cookie(本课采用) 浏览器 Cookie 仅持有随机会话标识 服务端会话表 user · role · class 状态在服务端 登出 = 删除会话行,立刻失效 主要风险:CSRF → 同源 + SameSite 角色与班级每次从数据库读取 JWT(本课不采用) JWT(三段结构) role 写在载荷里 服务端只验签 不查会话表 状态在客户端,载荷默认可见 登出 ≠ 立即失效(须额外维护吊销清单) 主要风险:XSS 读走 localStorage 变更角色须待令牌过期后方才生效
两种登录态的本质差异在于「状态存放于何处」,它决定了登出语义、角色变更的生效时机以及需要重点防范的风险类型。

Cookie 设置 HttpOnly 属性并限定本站作用域。需要重点防范的是跨站请求伪造(CSRF),而非将令牌存放于 localStorage 所引入的风险。

2登录成功必须换发会话标识

若登录成功后沿用浏览器中已有的会话标识,攻击者可预先将该标识植入受害者浏览器,即会话固定攻击。身份校验通过后必须签发新的会话标识,原标识立即作废。

攻击者 受害者浏览器 服务端 ① 攻击者正常登录,取得会话标识 A ② 诱导受害者携带标识 A 访问 ③ 受害者携带标识 A 提交登录 ④ 校验通过,签发新标识 B 原标识 A 立即作废 ⑤ Set-Cookie:标识 B ⑥ 攻击者持原标识 A 请求 → 401
会话固定(Session Fixation)的防御要点:登录成功必须换发新的会话标识,攻击者预置的旧标识随之失效。

3登录模块如何向下游传递身份

登录接口本身不要求请求方已持有会话。它校验用户名与口令哈希,通过后丢弃浏览器携带的旧会话标识,在 sessions 表写入新记录,再通过 Set-Cookie 将新标识下发给浏览器。Cookie 中不保存角色,也不保存班级。

第一次:POST /api/login 用户名 + 口令 只在这一次出现 比对口令哈希 失败时三种原因对外一致 写入新的 sessions 记录 原标识作废 Set-Cookie 仅含随机会话标识 此后每次请求:携带 Cookie 的 /api 认证模块查会话 过期或不存在 → 401 再读 users 表 角色与班级以该行为准 交给材料或上传模块 它们不再解析 Cookie
口令仅在登录这一次请求中出现。后续模块所见的是认证模块已解析完成的用户对象,而非浏览器再次声明的身份。

教师接口额外增加角色校验

上传请求在认证通过之后,仍须校验角色是否为教师。学生请求将被拒绝并返回 403,此时文件尚未落盘、数据表尚未插入。角色取自前述 users 查询。页面上不渲染上传按钮,仅意味着少了一条入口,无法阻止调用方直接请求接口。