# YOJ **Repository Path**: do_free/yoj ## Basic Information - **Project Name**: YOJ - **Description**: 基于SpringBoot的在线刷题OJ系统 - **Primary Language**: Java - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2024-09-21 - **Last Updated**: 2024-12-18 ## Categories & Tags **Categories**: Uncategorized **Tags**: Vue, SpringBoot, Redis, SpringCloud, ElasticSearch ## README # YOJ #### 介绍 > 基于SpringBoot的OJ系统。 > 主要功能: 用户在线刷题(支持语言Java、C++)、参加竞赛、学习算法。 > 管理员管理题目、发布比赛 #### 软件架构 SpringBoot + MybatisPlus + JWT + Redis + RabbitMQ + Elastic ,前端: arco design Vue + Vuex + openapi - 详细功能实现: 1. 提交代码:题目提交到后端以后,后端插入提交信息并置状态字段为0表示结果未出,同时将消息通过RabbitMQ传入队列, 队列处理消息,请求沙箱(提供执行代码返回结果的服务)得到code结果,比对结果,修改数据库提交记录,返回。 2. 题目搜索和评论搜索:使用Elasticsearch搭建搜索引擎,主要实现流程是,创建索引,导入数据并同步,通过增删改查实现接口。 - 数据同步: 通过继承CommendLine实现单次任务执行实现初步ES和Mysql。 - 增量同步: 定时任务固定周期(使用spring自带的任务调度实现)查询数据库变化,更新到ES中,其中评论同步周期为10m,题目周期为一天。 - 题目搜索引擎优化: 对需要检索的字段添加索引,减小不必要的开销。对content这种可能会很长的字段加限制,当他大于256时不做分词,避免影响性能。 3. 计算竞赛结果: 添加定时任务,每天的下午1:30和晚上11:30去数据库查询已经结束且未计算的竞赛计算。 4. 比赛时提交代码: 比赛表的字段设计主要为标题、内容、题号列表、题目的列表、判题限制。比赛和用户为多对多关系,中间表字段为用户id、竞赛id、提交id列表。 用户每次提交只需要向中间表中的提交id列表push提交id即可。在计算分数时,会直接根据提交id列表查询提交记录,取最大值。 5. 每天提交次数: key设计优化中使用uid和年份,过期时间为一年。submit:year:{userId}:{year} -> map, map(day -> times)。 6. 保持登录态:使用JWT对用户信息加密生成token,在登录时返回给前端,前端保存token,以后每次请求将token放到head中。 - 用拦截器实现登录拦截:在拦截器中实现获取请求头中的token,解析,判断信息正确性。其中判断密码是否正确时都需要查询数据库,怎样每次请求接口都会触发查询,影响效率。使用redis优化。key设计为 login:userKey:{userid} - 创建注解,给注解添加通知,在通知中实现用户权限限制。相比于直接使用拦截器更灵活。 7. 提交代码接口防刷: - 判题服务请求沙箱时在请求头上添加字段标识,沙箱判断请求头后接受请求。 - 防重放: 判题服务请求沙箱时添加唯一数到请求头,并且添加一个当前时间到请求头,沙箱接受时将唯一数(有过期时间)存到redis中,判断时间是否已超时。 #### 产品展示 ###### 搜索题目 ![img_5.png](imgs/img_5.png) ###### 提交题目 ###### 搜索评论功能 ![img_1.png](imgs/img_1.png) ###### 查看自己每天的提交数 ![img_10.png](imgs/img_10.png) ###### 参加竞赛 ![img_9.png](imgs/img_9.png) ![img_8.png](imgs/img_8.png) ###### 动态学习算法 ![img_6.png](imgs/img_6.png) ###### ![img_7.png](imgs/img_7.png) ###### 编辑题目 ![img_3.png](imgs/img_3.png) ###### 添加或修改竞赛 ![img_2.png](imgs/img_2.png) #### 安装教程 1. xxxx 2. xxxx 3. xxxx