一、文档背景
大二下学期某个课程的模拟答辩。
二、小组安排
| 成员 | 职责 | 
|---|---|
| 博主 | 组长、项目部署、项目测试、文档编写 | 
| *** | 后端测试、本地部署 | 
| *** | 前端测试、本地部署 | 
三、项目背景
当今社会,随着教育水平的提高和教育资源的广泛普及,考试成为了人们测量学习成果和能力的重要方式之一。而电子化考试系统的出现,则为传统考试方式的提升带来了新的机遇和挑战。电子化考试系统是指通过计算机技术和网络技术等手段来组织和实施考试活动的系统。它的出现极大的提高了考试活动的效率和便利性,对于解决考试过程中存在的一些问题具有显著作用,它具有以下优点:
1.方便的考试流程
电子化考试系统的实现,可以大大减轻教育管理和组织部门的工作压力。学生可自行缴纳考试费并进行在线注册,组织者可自动统计报名人数,考试时间、地点,安排座位等,这样不仅减轻了组织者的负担,也为学生提供了更便捷的报名、考试流程,同时阳光操作,也减少了人为操作失误。
2.保障考试公平性
考试过程中,学生作答信息可实时上传至服务器,组织者只需输入相应代码或密码即可得到考生试卷。这种检查考生答案的方式极大地减少了人为误判,可以降低误判率,提高考试的安全性。
3.标准化的评估标准
在传统考试方式中,标准化与否通常需要检查评卷教师的专业水平和评分的客观性。而在电子化考试系统中,传输输入信息后均需数字化评分(根据答案的准确率、速度、排版等指标),标记人为操作减少了,评卷的结果更加公正合理,减少了因人而异的成绩评定情况。
4.大数据分析
电子化考试系统可以快速记录学生参加考试的数据,统计学生的考试成绩和考试时间等信息。这些数据可以被用来分析学生学习和考试过程中的种种问题和痛点,之后有针对性地做出改进,调整教学方式,更好的满足学生需求。
总之,电子化考试系统是科技进步带来的一种方式,它既提高了考试效率,改善了考试体验,又增强了考试结果的公正性。未来,带着便利和优化的特点,电子化考试必将成为教育考试领域趋势。
在此背景下,学之思开源考试系统应运而生。
四、项目信息
1.学生系统功能
| 模块 | 介绍 | 
|---|---|
| 登录 | 用户名、密码 | 
| 注册 | 年级、用户名、密码 | 
| 任务中心 | 管理员发布的年级任务,每个学生只能做一次 | 
| 考试 | 题干支持文本、图片、数学公式、表格等,学生答题支持:文本 | 
| 固定试卷 | 可重复练习、自行批改的试卷 | 
| 时段试卷 | 在时间限制内,可重复练习、自行批改的试卷 | 
| 考试记录 | 查看答卷记录和试卷信息 | 
| 错题本 | 答错题目会自动进入错题本,显示题目基本信息 | 
| 个人信息 | 显示学生个人资料 | 
| 更新信息 | 修改个人资料、头像 | 
| 个人动态 | 显示用户最近的个人动态 | 
| 消息中心 | 用于接收管理员发送的消息 | 

2.管理系统功能
| 模块 | 介绍 | 
|---|---|
| 登录 | 用户名、密码 | 
| 主页 | 试卷总数、题目总数、用户活跃度、题目月数量 | 
| 学生列表 | 显示系统所有的学生,新增、修改、删除、禁用 | 
| 管理员列表 | 显示系统所有的管理员,新增、修改、删除、禁用 | 
| 学科列表 | 学科查询、修改、删除 | 
| 学科创编 | 创建学科 | 
| 试卷列表 | 试卷查询、修改、删除 | 
| 试卷创编 | 创建的试卷为时段试卷、固定试卷、任务试卷 | 
| 题目列表 | 题目查询、修改、删除 | 
| 题目创建 | 题目支持单选题、多选题、判断题、填空题、简答题,题干支持文本、图片、表格、数学公式 | 
| 任务列表 | 任务查询、修改、删除 | 
| 消息列表 | 显示已发送的消息,消息已读人数等信息 | 
| 消息发送 | 发送消息给多个用户 | 
| 用户日志 | 显示所有用户日志 | 
| 个人资料 | 显示管理员用户名、真实姓名 | 
| 时间线 | 显示管理员创建时间 | 
| 修改资料 | 修改姓名、手机号 | 

3.数据库ER图

五、项目依赖
1.软件
1.1运行环境
| 环境 | 版本 | 
|---|---|
| 操作系统 | Windows / Linux(centos7.6) | 
| NodeJs | 14 | 
| Jdk | 1.8 | 
| Mysql | 8.0 | 
| docker | 24.0.1 | 
1.2后端系统
- spring-boot 2.1.6.RELEASE
 - spring-boot-security 用户登录验证
 - undertow web容器
 - mysql 最流行的开源数据库
 - mybatis 数据库中间件
 - hikari 速度最快的数据库连接池
 - 七牛云存储 分布式文件存储中心
 
1.3前端系统
- vue 采用新版,使用了vue-cli4搭建的系统,减少大量配置文件
 - element-ui 最流行的vue UI框架
 - vue-element-admin 深度定制版
 - echarts 图表统计
 - ueditor 题目编辑器
 
2.硬件
- 最低配置1C+2G
 - 推荐配置2C+4G
 
六、项目部署
1.前言必看
集成部署:将打包的前端文件放在后端static下面(部署快)。
前后分离:各自部署(好维护)。
2.依赖部署
2.1安装docker
# 安装必要的一些系统工具 
sudo yum install -y yum-utils device-mapper-persistent-data lvm2 
# 添加软件源信息 
sudo yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo 
# 更新并安装 Docker-CE 
sudo yum makecache fast 
sudo yum -y install docker-ce 
# 开启Docker服务 
sudo service docker start 
sudo mkdir -p /etc/docker 
sudo tee /etc/docker/daemon.json <<-'EOF' 
{ 
 "registry-mirrors": ["https://lz5xr9iw.mirror.aliyuncs.com"] 
} 
EOF 
sudo service docker start 
docker info
2.2创建网络
docker network create --driver bridge --subnet=172.18.0.0/16 --gateway=172.18.0.1 mynet
2.3安装MySQL
docker pull mysql:8.0.21;
docker run \
-dp 3306:3306 \
--restart=always \
--privileged=true \
--name mysql-8.0.21 \
--network=mynet \
--ip 172.18.0.21 \
-e MYSQL_ROOT_PASSWORD=123456 \
-e TZ="Asia/Shanghai" \
-v /opt/docker-mysql/conf:/etc/mysql/conf.d \
-v /opt/docker-mysql/data:/var/lib/mysql \
mysql:8.0.21;
2.4安装nginx
rpm -Uvh http://nginx.org/packages/centos/7/noarch/RPMS/nginx-release-centos-7-0.el7.ngx.noarch.rpm
yum -y install nginx
systemctl start nginx
systemctl enable nginx
2.5创建数据库
1.SQL文件下载
2.Navicat创建

3.datagrip创建

2.6数据库设计
1.试卷表
- 表名:t_exam_paper
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| name | varchar | 试卷名称 | 
| subject_id | int | 学科 | 
| paper_type | int | 试卷类型( 1.固定试卷 4.时段试卷 6.任务试卷 ) | 
| grade_level | int | 年级 | 
| score | int | 试卷总分(千分制) | 
| question_count | int | 题目数量 | 
| suggest_time | int | 建议时长(分钟) | 
| limit_start_time | datetime | 时段试卷 开始时间 | 
| limit_end_time | datetime | 时段试卷 结束时间 | 
| frame_text_content_id | int | 试卷框架 内容为JSON | 
| create_user | int | |
| create_time | datetime | |
| deleted | bit | |
| task_exam_id | int | 
2.试卷答案表
- 表名:t_exam_paper_answer
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| exam_paper_id | int | |
| paper_name | varchar | 试卷名称 | 
| paper_type | int | 试卷类型( 1.固定试卷 4.时段试卷 6.任务试卷 ) | 
| subject_id | int | 学科 | 
| system_score | int | 系统判定得分 | 
| user_score | int | 最终得分(千分制) | 
| paper_score | int | 试卷总分 | 
| question_correct | int | 做对题目数量 | 
| question_count | int | 题目总数量 | 
| do_time | int | 做题时间(秒) | 
| status | int | 试卷状态(1待判分 2完成) | 
| create_user | int | 学生 | 
| create_time | datetime | 提交时间 | 
| task_exam_id | int | 
3.试卷题目答案表
- 表名:t_exam_paper_question_customer_answer
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| question_id | int | 题目Id | 
| exam_paper_id | int | 答案Id | 
| exam_paper_answer_id | int | |
| question_type | int | 题型 | 
| subject_id | int | 学科 | 
| customer_score | int | 得分 | 
| question_score | int | 题目原始分数 | 
| question_text_content_id | int | 问题内容 | 
| answer | varchar | 做题答案 | 
| text_content_id | int | 做题内容 | 
| do_right | bit | 是否正确 | 
| create_user | int | 做题人 | 
| create_time | datetime | |
| item_order | int | 
4.消息表
- 表名:t_message
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| title | varchar | 标题 | 
| content | varchar | 内容 | 
| create_time | datetime | |
| send_user_id | int | 发送者用户ID | 
| send_user_name | varchar | 发送者用户名 | 
| send_real_name | varchar | 发送者真实姓名 | 
| receive_user_count | int | 接收人数 | 
| read_count | int | 已读人数 | 
5.用户消息表
- 表名:t_message_user
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| message_id | int | 消息内容ID | 
| receive_user_id | int | 接收人ID | 
| receive_user_name | varchar | 接收人用户名 | 
| receive_real_name | varchar | 接收人真实姓名 | 
| readed | bit | 是否已读 | 
| create_time | datetime | |
| read_time | datetime | 阅读时间 | 
6.题目表
- 表名:t_question
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| question_type | int | 1.单选题 2.多选题 3.判断题 4.填空题 5.简答题 | 
| subject_id | int | 学科 | 
| score | int | 题目总分(千分制) | 
| grade_level | int | 级别 | 
| difficult | int | 题目难度 | 
| correct | text | 正确答案 | 
| info_text_content_id | int | 题目 填空、 题干、解析、答案等信息 | 
| create_user | int | 创建人 | 
| status | int | 1.正常 | 
| create_time | datetime | 创建时间 | 
| deleted | bit | 
7.学科表
- 表名:t_subject
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| name | varchar | 语文 数学 英语 等 | 
| level | int | 年级 (1-12) 小学 初中 高中 大学 | 
| level_name | varchar | 一年级、二年级等 | 
| item_order | int | 排序 | 
| deleted | bit | 
8.任务表
- 表名:t_task_exam
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| title | varchar | |
| grade_level | int | 级别 | 
| frame_text_content_id | int | 任务框架 内容为JSON | 
| create_user | int | |
| create_time | datetime | |
| deleted | bit | |
| create_user_name | varchar | 
9.用户任务表
- 表名:t_task_exam_customer_answer
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| task_exam_id | int | |
| create_user | int | |
| create_time | datetime | |
| text_content_id | int | 任务完成情况(Json) | 
10.文本表
- 表名:t_text_content
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| content | text | |
| create_time | datetime | 
11.用户表
- 表名:t_user
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| user_uuid | varchar | |
| user_name | varchar | 用户名 | 
| password | varchar | |
| real_name | varchar | 真实姓名 | 
| age | int | |
| sex | int | 1.男 2女 | 
| birth_day | datetime | |
| user_level | int | 学生年级(1-12) | 
| phone | varchar | |
| role | int | 1.学生 3.管理员 | 
| status | int | 1.启用 2禁用 | 
| image_path | varchar | 头像地址 | 
| create_time | datetime | |
| modify_time | datetime | |
| last_active_time | datetime | |
| deleted | bit | 是否删除 | 
| wx_open_id | varchar | 微信openId | 
12.用户日志表
- 表名:t_user_event_log
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| user_id | int | 用户id | 
| user_name | varchar | 用户名 | 
| real_name | varchar | 真实姓名 | 
| content | text | 内容 | 
| create_time | datetime | 时间 | 
13.用户Token表
- 表名:t_user_token
 - 字段注释:
 
| 字段名 | 类型 | 注释 | 
|---|---|---|
| id | int | |
| token | varchar | |
| user_id | int | 用户Id | 
| wx_open_id | varchar | 微信openId | 
| create_time | datetime | |
| end_time | datetime | |
| user_name | varchar | 用户名 | 
3.集成部署
3.1前端打包
1.打包项目
分别在\source\vue\xzs-student目录和source\vue\xzs-admin目录,执行前端打包命令
npm config set sass_binary_site https://npm.taobao.org/mirrors/node-sass/
npm install --registry https://registry.npm.taobao.org
npm run build
打包后的目录为student和admin,如下图所示:


3.2后端打包
1.导入前端
将前端打包好的文件放到\source\xzs\src\main\resources\static下,如下图所示:

2.修改数据库
修改配置文件中的数据库地址,默认运行的是 application-prod.yml,所以只修改它,如下图所示:

3.打包项目
将项目打包成jar包

3.3服务器
1.上传
将上面打包的项目文件上传到服务器
2.编写Dockerfile
这个Dockerfile要放在“/**/”下面。
如:我将项目文件放在了"/huaweiCloud"下面,则Dockerfile就要放在“/huaweiCloud/”下面。
FROM openjdk:8-jre-alpine
ENV LANG en_US.UTF-8
RUN set -xe && apk --no-cache add ttf-dejavu fontconfig
VOLUME /tmp
ADD xzs-3.9.0.jar app.jar
EXPOSE 8089
ENTRYPOINT ["java","-Djava.security.egd=file:/dev/./urandom","-jar","/app.jar"]
3.构建镜像
docker build -t xzs-3.9.0:2 ./
4.构建容器
docker run -d \
-p 8089:8089 \
--restart=always \
--privileged=true \
--name xzs-3.9.0 \
--network=mynet \
--ip 172.18.0.12 \
-e TZ="Asia/Shanghai" \
-e XZS_MYSQL_DB_NAME="xzs" \
-e XZS_MYSQL_DB_PORT="3306" \
-e XZS_MYSQL_HOST="172.18.0.21" \
-e XZS_MYSQL_USER="root" \
-e XZS_MYSQL_PASSWORD="123456" \
xzs-3.9.0:2;
5.查看容器是否运行
docker ps
6.访问地址
- 教师端访问地址htpp://IP:8089/admin
 - 学生端访问地址htpp://IP:8089/student
 
4.前后分离
4.1后端打包
1.删掉前端目录
将“\source\xzs\src\main\resources\static”中的static删掉

2.打包后端
将后端打包成jar包

4.2前端打包
1.打包项目
分别在\source\vue\xzs-student目录和source\vue\xzs-admin目录,执行前端打包命令
npm config set sass_binary_site https://npm.taobao.org/mirrors/node-sass/
npm install --registry https://registry.npm.taobao.org
npm run build
打包后的目录为student和admin,如下图所示:


4.3服务器
1.上传前后端项目文件
先打包下面三个文件,然后再上传服务器。
admin和student存放位置在上一步中。

2.创建目录
创建/usr/local/xzs/web/目录,然后将打包后的student、admin放到此目录下

3.配置nginx
先删除下列文件中的所有内容。
vi /etc/nginx/conf.d/default.conf
然后添加下面的内容。
server {
    listen      8001;
    server_name xzs;
    location / {
        root /usr/local/xzs/web/;
        index index.html;
    }
    location /api/ {
       proxy_pass  http://localhost:8000;
    }
}
4.构建镜像
编写Dockerfile。
Dockerfile要放在jar包存放处。
FROM openjdk:8-jre-alpine
ENV LANG en_US.UTF-8
RUN set -xe && apk --no-cache add ttf-dejavu fontconfig
VOLUME /tmp
ADD xzs-3.9.0.jar app.jar
EXPOSE 8090
ENTRYPOINT ["java","-Djava.security.egd=file:/dev/./urandom","-jar","/app.jar"]
构建镜像
docker build -t xzs-3.9.0:1.1 ./
5.构建容器
docker run -d \
-p 8090:8090 \
--restart=always \
--privileged=true \
--name xzs-3.9.1 \
--network=mynet \
--ip 172.18.0.13 \
-e TZ="Asia/Shanghai" \
-e XZS_MYSQL_DB_NAME="xzs" \
-e XZS_MYSQL_DB_PORT="3306" \
-e XZS_MYSQL_HOST="172.18.0.10" \
-e XZS_MYSQL_USER="root" \
-e XZS_MYSQL_PASSWORD="123456" \
-v /huaweiCloud:/xzs/ \
xzs-3.9.0:1.1;
6.访问地址
- 教师端访问地址htpp://IP:8001/admin
 - 学生端访问地址htpp://IP:8001/student
 
七、集成测试
1.学生端
点击查看学生端访问地址或访问学生端 测试账户:张三 密码:123456 亦可自行注册。


2.管理员端
点击查看管理员端访问地址或访问管理员端 测试账户:admin 密码:123456
