Skip to content

v1.5.0-preview

Choose a tag to compare

@ZemuZzz ZemuZzz released this 05 May 19:41
· 6 commits to main since this release

🏷️ v1.5.0 - 用户名牌子系统

继 v1.4.0 工单系统之后,这次推出身份与荣誉层面的两个核心功能。

✨ 新功能

🏷️ 用户名牌子(参照洛谷设计)

每位用户都可以拥有一个显示在用户名右侧的小牌子(tag)。

两种获取途径:

  • 拥有任意管理权限(is_admin/manage_problem/manage_problem_tag/manage_user)的用户自动获得 tag 权限
  • 超管可在 /admin/user-tags 后台授予普通用户 tag 权限

特性:

  • 文字长度上限 12 字符
  • 颜色与用户名颜色档自动一致
  • 用户可在 /edit 自定义文字 + 切换展示开关
  • 管理员默认显示「管理员」,普通被授权者初始为空(需自己填)
  • 管理员身份取消后保留 tag 且仍可修改(类似"老干部"称号)
  • 完整审计:记录授权超管 + 时间戳

超级管理员特权:

  • 可禁用任意非超管用户的 tag 权限
  • 不能禁用自己,也不能禁用其他超管
  • 禁用后用户在 /edit 看不到 tag 相关 UI

🛡️ 作弊者标签

与荣誉 tag 是两个完全独立的系统:荣誉 tag 是用户自愿展示的徽章,作弊者标签是被强加的惩罚。

触发条件:用户至少有一条 judge_state_admin_action.action_type='cheated' 记录。

视觉效果:

  • 用户名变为棕色 + 删除线
  • 强制显示棕色「作弊者」标签
  • 覆盖一切其他视觉(原有的颜色和荣誉 tag 都被压住)

核心边界:

  • 管理员豁免:管理员被标记 cheated 时无任何视觉变化(管理员的紫色 + tag 不受影响)
  • 荣誉 tag 数据保留:即使被标 cheater,用户的荣誉 tag 设置不会被删除——他在 /edit 仍可继续设置(显示黄色警告"当前荣誉 tag 被作弊者身份覆盖"),作弊状态被撤销后立即恢复

🖼️ 排行榜头像

/ranklist 双 Tab(Rating + Hit) 用户名一栏左侧显示 24×24 gravatar 头像,提升识别度。

🔧 Bug 修复

admin-cache 漏掉 super admin

根因:_username_cache.js 只查 user_privilege 表里的 manage_problem 等细分权限,忽略了 user.is_admin=1。导致 super admin 没有被授予细分权限时被误识别为普通用户(灰色 tier)。

修复:用 raw SQL SELECT id FROM user WHERE is_admin = 1 补齐(typeorm boolean 处理在 mariadb 上有怪毛病,用 raw SQL 绕过)。

🛠 技术细节

  • 新增 1 张数据表 user_tag(完全独立,不修改 SYZOJ 核心 schema)
  • 缓存刷新顺序:user-tag-cache 启动延迟 8 秒,确保 admin-cache 先就绪
  • admin fallback 逻辑:adminUserIds 里且数据库中"完全没有显式记录"的用户 → "管理员";数据库里有记录的尊重数据库(支持 admin 主动隐藏自己的 tag)
  • 缓存生命周期:admin-cache、cheater-cache、user-tag-cache 都以 60 秒为周期自动刷新
  • Vue 组件通过 window.__SYZOJ_USER_TAGSwindow.__SYZOJ_CHEATER_USER_IDS 接收数据,与 EJS 模板 syzoj.utils.renderUsername() 行为一致

📊 工程统计

  • 新增数据表: 1 张(user_tag)
  • 新增 model 文件: 1 个
  • 新增 module 文件: 2 个(_user_tag.js + _user_tag_loader.js)
  • 新增/修改模板: 5 个
  • 修复 model/路由文件: 3 个
  • 修改 CSS: 1 个

⚠️ 升级注意

如果从旧版升级,需要先初始化 user_tag 表(参见 README 中的 SQL 初始化脚本最后一段)。