# 课程资源分享(需求规格 v2) 更新时间:2025-10-18 ## 概览 - 目标:面向“专业 → 课程 → 资源”的资料分享与审核发布;支持压缩包(OSS)或外链;下载计数与排行榜纳入 MVP;支持“最佳推荐”。 - 架构:前台门户(登录后默认进入)+ 后台管理(RuoYi 管理台)。 - 门户仅查询;写操作统一走后台接口;所有接口需登录。 ## 界面信息架构(门户) - 顶栏(Banner) - 左:站点 Logo(点击回到门户首页 `/portal/course-resource`) - 中:面包屑(课程资源 / 专业 / 课程),按路由上下文动态展示 - 右: - “管理后台”按钮(仅对 admin/super_admin/major_lead/librarian 可见,跳转 `/index`) - 用户头像下拉:个人信息、退出登录 - 左侧导航(层叠) - 课程资源分享 - 资源首页(/portal/course-resource) - 我上传的(/portal/course-resource/my) - 排行榜(/portal/course-resource/top) - 资源排行:支持 全站/按专业/按课程 + 天数筛选;名称列显示“最佳”徽标;下载跳转前先计数 - 用户积分:展示用户积分排名;每行展示“代表作Top5”(按下载数降序);点击用户名打开抽屉查看该用户“全部代表作”,支持筛选与排序 - 数字图书馆(预留) - 内容区:承载“专业卡片 / 课程卡片 / 资源列表与上传 / 我的资源 / 排行榜”等页面 ## 角色与权限 - 普通用户(user) - 门户:浏览、下载、查看排行榜 - 写操作(需授权以下按钮权限): - `manage:upload:oss`, `manage:courseResource:add`, `manage:courseResource:edit`, `manage:courseResource:remove`, `manage:courseResource:offline`, `manage:courseResource:online` - 限制:仅能删除本人“待审/驳回/已下架”;已通过仅可下架;编辑或重新上架会回到“待审”。 - 专业负责人(major_lead) - 具备用户能力;后台可维护本专业课程与审核本专业待审资源(通过/驳回),可对资源执行下架/硬删除(仅删库);可将本专业优质资源标记为“最佳推荐”。 - 管理员(admin/super_admin) - 跨专业全量管理:专业、课程、资源、审核、硬删除等。 ## 状态机与业务规则 - 资源状态:0 待审 / 1 已通过 / 2 驳回 / 3 已下架 - 规则: - 创建即待审;任何编辑回到待审;驳回可编辑后再提审;下架可再次上架(进入待审) - 去重: - 文件:`(course_id, resource_type, file_hash)` 唯一 - 外链:`(course_id, resource_type, link_url)` 唯一(URL 规范化) - 下载计数:通过 `/portal/resource/{id}/download` 计数并 302 跳转 - 文件限制:仅压缩包;≤100MB;前后端双重校验;DB 不存扩展名 - 审计:`tb_course_resource_log` 记录 CREATE/EDIT/APPROVE/REJECT/OFFLINE/ONLINE/DOWNLOAD/DELETE/HARD_DELETE ## 数据模型(与 book-mis.sql 对齐) - `tb_major` 专业:`id, major_name(唯一), status, remark, 审计, del_flag` - `tb_course` 课程:`id, major_id, course_name(同专业唯一), course_code?, status, remark, 审计, del_flag` - `tb_major_lead` 专业负责人映射:`id, major_id, user_id(唯一组合), remark, 审计, del_flag` - `tb_course_resource` 课程资源: - 基础:`id, major_id(冗余), course_id, resource_name, resource_type(0文件/1外链), description` - 文件:`file_url, file_hash(SHA-256), file_size` - 外链:`link_url` - 审核:`status, audit_by/time, audit_reason, publish_time` - 统计:`download_count, last_download_time` - 上传者:`uploader_id, uploader_name` - `tb_course_resource_best` 最佳标记:`id, resource_id(唯一), best_by, best_time, 审计, del_flag` - `tb_course_resource_log` 审计日志:`resource_id, action, actor*, ip, ua, detail, result, 审计, del_flag` ### 新增:积分与排行榜(本次草案) - `tb_cr_user_score`(CR 专属)用户积分聚合:`id, user_id, username, major_id(0=全站), total_score, approve_count, best_count, 审计, del_flag` - `tb_cr_user_score_log`(CR 专属)用户积分流水:`id, user_id, username, major_id, resource_id, event_type(APPROVE/BEST), delta, remark, 审计, del_flag` 业务规则(防刷): - 上传资源“第一次审核通过”加少量积分(默认 +5);资源被“第一次设置为最佳”加分(默认 +10)。 - 编辑后再次提交、再次审核通过不重复加分;取消“最佳”不扣分;再次设置为最佳不重复加分。 - 以 `(user_id, resource_id, event_type)` 在流水表唯一约束实现“只发一次”。 - 聚合表维护两类行:`major_id=资源专业` 与 `major_id=0(全站)`,用于“按专业排行榜”与“全站排行榜”(专业名称通过与 `tb_major` 关联获取)。 ## 接口分层(冻结) - 门户只读(登录即可): - GET `/portal/major/list`、`/portal/course/list`、`/portal/resource/list|{id}|{id}/download|/top` - 后台管理(按钮权限控制): - 专业:GET/POST/PUT/DELETE `/manage/major` - 课程:GET/POST/PUT/DELETE `/manage/course` - 资源:GET/POST/PUT/DELETE `/manage/courseResource` + 审核/上下架 `/approve|reject|offline|online` - 最佳:PUT `/manage/courseResource/{id}/best|unbest`(权限:`manage:courseResource:best`;管理员或本专业负责人) - 排行榜(新增): - 门户只读:GET `/portal/score/rank`(Query:`majorId?`,0/缺省=全站) - 后台查询:GET `/manage/score/user/rank`(权限:`manage:score:list`) ## 用户流程(门户) - 学生 1) 登录 → 进入 `/portal/course-resource`(专业卡片) 2) 选择专业 → `/portal/course-resource/course`(课程卡片) 3) 选择课程 → `/portal/course-resource/list`(资源卡片列表,显示已通过,最佳资源带“最佳”徽标并置顶) 4) 分享资源(需权限):选择“OSS 上传或外链”、填写名称与简介 → 提交审核(进入待审) 5) “我上传的”管理:查看所有状态、编辑(回到待审)、删除(待审/驳回/下架)、下架、重新上架(回到待审) 6) 排行榜:进入“课程资源分享 → 排行榜” - 资源排行:选择 scope(全站/专业/课程)与天数;可直接下载(名称列显示“最佳”徽标) - 用户积分:可筛选专业(或全站),按积分从高到低展示;每行显示代表作Top5;点击用户名打开抽屉查看该用户全部代表作,支持关键词/课程/类型/仅最佳/排序(按下载或时间) - 专业负责人(后台) - 课程维护(本专业);待審审核(通过/驳回,填写理由);已通过可下架;已下架可硬删除或重新上架 - 管理员(后台) - 跨专业全量管理 ## 边界与异常 - 重复:文件按 hash、外链按 URL 去重;重复则 400 提示 - 外链有效性:由负责人审核把关;系统仅做基础格式校验 - 并发审核:MVP 未做乐观锁;后续可加版本号字段 - 下载作弊:可后续引入最小间隔与限流;MVP 不做复杂防刷 - 硬删除:仅删数据库记录,不删 OSS 对象 - 最佳:最佳为“标记”而非资源状态;同一资源最多存在一条最佳标记;置顶展示优先级高于时间排序 - 积分: - 发放仅一次,基于流水唯一约束;数据修复可通过重算任务(后续)按流水回放 - 若资源变更专业(非常规操作),历史积分不回溯;按首次发放时的专业维度入账 ## 非功能性 - 性能:分页≤50;排行榜按下载数,建议 5 分钟缓存(后续加入 Redis) - 安全:文件类型/大小二次校验;OSS 凭据环境变量注入;密钥不入库不入 Git - 审计:失败回滚并落错误信息到日志表 ## RuoYi 后台菜单与路由建议(模块化分层) - 目录:课程资源(/manage/course-resource) - 菜单:课程管理(/manage/course-resource/course) - 菜单:待审核(/manage/course-resource/audit) - 菜单:资源列表(已上架)(/manage/course-resource/approved) - 菜单:回收站(已驳回/已下架)(/manage/course-resource/trash) - 菜单:专业管理(/manage/course-resource/major) - 菜单:专业负责人(/manage/course-resource/major-lead) - 按钮: - 资源:`manage:courseResource:add|edit|remove|approve|reject|offline|online|list|query` - 课程:`manage:course:add|edit|remove|list|query` - 专业:`manage:major:add|edit|remove|list|query` ## DoD(完成标准) - 表结构与示例数据就绪(book-mis.sql) - 门户与后台接口可用;普通用户具备上传所需按钮权限 - 前端页面可操作(上传/审核/下架/排行榜) - API 文档(v2)与 Apifox 指南可用 - 后端测试覆盖:成功/失败/权限三类场景 - 模块报告(ER/流程/权限矩阵/限制与计划)