1. 项目概述:SpringBoot+Vue大学生竞赛管理平台
这个基于SpringBoot+Vue技术栈的大学生竞赛管理系统,是我在指导毕业设计和课程设计时反复打磨的一个实战项目。它完美解决了高校竞赛活动管理中的三个核心痛点:赛事信息分散、报名流程繁琐、成绩统计低效。采用前后端分离架构,后端用SpringBoot提供RESTful API,前端用Vue构建交互界面,数据库选用MySQL 8.0,整套系统在校园内网环境下实测可支持500+并发访问。
提示:系统特别设计了评委双盲评审功能,参赛学生看不到评委信息,评委也只能看到匿名作品,确保竞赛公平性
2. 技术选型与架构设计
2.1 后端技术栈解析
SpringBoot 2.7.x作为基础框架,搭配以下关键组件:
- 安全控制:Spring Security + JWT实现RBAC权限模型
- 数据持久层:MyBatis-Plus 3.5.3(带代码生成器)
- 文件处理:Apache POI 5.2.3(Excel导入导出)
- 缓存层:Redis 6.2(存放验证码和热点数据)
- 消息队列:RabbitMQ 3.11(异步处理评审结果通知)
数据库表设计遵循第三范式,核心表包括:
CREATE TABLE `competition` ( `id` int NOT NULL AUTO_INCREMENT, `name` varchar(100) NOT NULL COMMENT '竞赛名称', `start_time` datetime NOT NULL COMMENT '报名开始时间', `end_time` datetime NOT NULL COMMENT '报名结束时间', `max_team_member` int DEFAULT '5' COMMENT '最大团队成员数', `blinded_review` tinyint(1) DEFAULT '1' COMMENT '是否开启盲审', PRIMARY KEY (`id`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;2.2 前端技术方案
Vue 3组合式API开发,主要技术点:
- UI框架:Element Plus(适配管理系统风格)
- 路由控制:Vue Router 4实现动态路由
- 状态管理:Pinia替代Vuex进行全局状态管理
- 可视化:ECharts 5.4展示参赛数据统计
- 特殊处理:使用vue-video-player组件实现m3u8格式的作品视频预览
前端工程结构示例:
src/ ├── api/ # Axios请求封装 ├── assets/ # 静态资源 ├── components/ # 公共组件 │ ├── BlindReview.vue # 盲审组件 │ └── CountDown.vue # 报名倒计时 ├── router/ # 路由配置 ├── stores/ # Pinia状态库 └── views/ # 页面组件3. 核心功能实现细节
3.1 多角色权限控制系统
系统包含5种角色权限:
- 超级管理员:院系管理+赛事管理
- 竞赛负责人:单个赛事全流程管理
- 评委账号:作品评审+分数录入
- 指导教师:团队管理+作品提交
- 学生账号:个人信息维护+赛事报名
权限控制流程图:
// Spring Security配置示例 @Configuration @EnableWebSecurity public class SecurityConfig { @Bean SecurityFilterChain filterChain(HttpSecurity http) throws Exception { http.authorizeRequests() .antMatchers("/admin/**").hasRole("ADMIN") .antMatchers("/judge/**").hasRole("JUDGE") .anyRequest().authenticated() .and() .addFilter(new JwtAuthenticationFilter(authenticationManager())); return http.build(); } }3.2 团队报名与作品提交
创新性地实现了三种报名模式:
- 个人赛:直接报名参赛
- 团队赛:队长创建团队,生成邀请码
- 指导教师带队:教师创建团队,学生申请加入
作品提交采用分片上传技术(基于vue-simple-uploader),支持:
- 作品文档(PDF/DOCX)
- 演示视频(MP4/M3U8)
- 源代码包(ZIP)
- 附件材料(≤50MB)
注意:系统自动检测文件名中的敏感词(如学号、姓名),确保盲审有效性
4. 典型业务场景实现
4.1 评审打分模块设计
评委端采用响应式布局,关键交互逻辑:
- 系统自动隐藏参赛者信息(包括文件名元数据)
- 采用Likert 5点量表评分法
- 支持评分暂存与修改记录
- 最终提交需进行电子签名确认
评分表数据结构:
{ "criteria": [ {"id":1,"name":"创新性","weight":0.3}, {"id":2,"name":"完成度","weight":0.4} ], "scores": [ {"criteriaId":1,"points":4,"comment":"立意新颖"}, {"criteriaId":2,"points":5,"comment":"功能完整"} ] }4.2 数据统计与可视化
使用ECharts实现的三种核心报表:
- 参赛热力图:按院系/专业统计报名密度
- 成绩分布图:正态分布曲线分析评分情况
- 历年对比图:同一赛事多届数据趋势分析
统计SQL示例(使用窗口函数):
SELECT college, COUNT(*) OVER(PARTITION BY college) AS college_total, AVG(score) OVER() AS avg_score FROM participant WHERE competition_id = #{cid}5. 部署与性能优化
5.1 生产环境部署方案
推荐使用Docker Compose编排:
version: '3' services: mysql: image: mysql:8.0 environment: MYSQL_ROOT_PASSWORD: ${DB_PASSWORD} volumes: - ./mysql-data:/var/lib/mysql backend: build: ./backend ports: - "8080:8080" depends_on: - mysql frontend: build: ./frontend ports: - "80:80"5.2 性能调优实战记录
通过JMeter压力测试发现的三个性能瓶颈及解决方案:
- 评审列表加载慢:添加
competition_id+judge_id联合索引 - 成绩汇总卡顿:改用Redis缓存统计结果,设置15分钟过期
- 文件下载超时:配置Nginx直接代理静态资源
JVM参数优化配置:
# application.properties server.tomcat.max-threads=200 spring.datasource.hikari.maximum-pool-size=206. 教学应用与二次开发
6.1 毕业设计改造指南
建议学生从以下方向进行功能扩展:
- 增加AI评审:集成HanLP进行文本相似度检测
- 微信通知:对接公众号模板消息
- 区块链存证:使用Hyperledger Fabric存储获奖证书
- 可视化大屏:用Three.js制作3D数据看板
6.2 常见问题解决方案
开发过程中遇到的典型问题:
- 跨域问题:后端配置
@CrossOrigin时忘记放行OPTIONS方法 - JWT失效:前端axios拦截器未正确处理401状态码
- MyBatis结果映射:字段名含下划线导致属性注入失败
- Vue路由守卫:next()调用时机不当造成无限循环
数据库连接池监控技巧:
// 在SpringBoot Actuator中暴露Hikari指标 management.endpoints.web.exposure.include=health,metrics,hikaricp7. 项目资源与学习路线
配套资源包含:
- 完整ER图(MySQL Workbench格式)
- Postman接口文档集合
- 前端组件设计稿(Figma源文件)
- 答辩PPT模板(含动画效果)
推荐学习路径:
- SpringBoot基础:自动配置原理、Starter机制
- Vue3核心:组合式API、Pinia状态管理
- 系统设计:RBAC权限模型、JWT认证流程
- 性能优化:数据库索引、缓存策略
我在项目中最深刻的体会是:管理系统类项目看似简单,但要处理好并发报名、数据一致性、权限边界这些细节,需要充分考虑业务场景的特殊性。比如在评审高峰期,我们通过引入RabbitMQ削峰填谷,使服务器负载下降了60%