课程信息不看视频的情况下基本上自己已经能写出来了,就是关联查询后端逻辑遇到一点问题,写了两天这个功能(毕竟不能全天写)

逻辑

查询课程:

前端有个搜索框可以输入课程名称查询
点击查询按钮会向后端发送请求,后端根据课程名称模糊匹配返回结果
表格会显示所有课程信息,包括课程名称、学分、教师、上课时间地点等

新增课程:

点击”新增”按钮弹出表单
填写课程信息(名称、介绍、学分、人数限制等)
需要选择授课教师和所属学院(从下拉框选择)
点击保存后,后端会创建新课程

编辑课程:

点击表格行的”编辑”按钮
会弹出表单并自动填充该课程现有信息
修改后点击保存,后端会更新这条课程信息

删除课程:

点击”删除”按钮会弹出确认框
确认后后端会删除这条课程记录

分页功能:

表格底部有分页控件
可以切换页码查看不同页的课程数据

数据关联:

课程关联了教师和学院信息
新增/编辑时可以选择已有教师和学院
表格中会显示教师姓名和学院名称(而不是ID)

创建数据库

1
2
3
4
5
6
7
8
9
10
11
12
13
CREATE TABLE `course` (
`id` int NOT NULL AUTO_INCREMENT COMMENT '主键ID',
`name` varchar(255) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '课程名称',
`content` varchar(255) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '课程介绍',
`score` int DEFAULT NULL COMMENT '课程学分',
`teacher_id` int DEFAULT NULL COMMENT '授课教师',
`num` int DEFAULT NULL COMMENT '开班人数',
`time` varchar(255) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '上课时间',
`location` varchar(255) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '上课地点',
`college_id` int DEFAULT NULL COMMENT '所属学院',
`already_num` int DEFAULT NULL COMMENT '已选人数',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='课程信息';

image-20250426214149453

前端

Manager.vue

1
2
3
4
<el-menu-item index="/course" v-if ="data.user.role === 'ADMIN'">
<el-icon><Reading /></el-icon>
<span>课程信息</span>
</el-menu-item>

index.js

1
{ path: 'course', component: () => import('@/views/manager/Course.vue')},

Course.vue

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
<template>
<div>

<div class="card" style="margin-bottom: 5px;">
<el-input v-model="data.name" style="width: 300px; margin-right: 10px" placeholder="请输入课程名称查询"></el-input>
<el-button type="primary" @click="load">查询</el-button>
<el-button type="info" style="margin: 0 10px" @click="reset">重置</el-button>
</div>

<div class="card" style="margin-bottom: 5px">
<div style="margin-bottom: 10px">
<el-button type="primary" @click="handleAdd">新增</el-button>
</div>
<el-table :data="data.tableData" stripe>
<el-table-column label="课程名称" prop="name"></el-table-column>
<el-table-column label="课程介绍" prop="content" show-overflow-tooltip></el-table-column>
<el-table-column label="课程学分" prop="score"></el-table-column>
<el-table-column label="授课教师" prop="teacherName"></el-table-column>
<el-table-column label="开班人数" prop="num"></el-table-column>
<el-table-column label="上课时间" prop="time"></el-table-column>
<el-table-column label="上课地点" prop="location"></el-table-column>
<el-table-column label="所属学院" prop="collegeName"></el-table-column>
<el-table-column label="已选人数" prop="alreadyNum"></el-table-column>
<el-table-column label="操作" align="center" width="160">
<template #default="scope">
<el-button type="primary" @click="handleEdit(scope.row)">编辑</el-button>
<el-button type="danger" @click="handleDelete(scope.row.id)">删除</el-button>
</template>
</el-table-column>
</el-table>
</div>

<div class="card">
<el-pagination background layout="prev, pager, next" v-model:page-size="data.pageSize" v-model:current-page="data.pageNum" :total="data.total"/>
</div>

<el-dialog title="课程信息" width="40%" v-model="data.formVisible" :close-on-click-modal="false" destroy-on-close>
<el-form :model="data.form" label-width="100px" style="padding-right: 50px">
<el-form-item label="课程名称" prop="name">
<el-input v-model="data.form.name" autocomplete="off" />
</el-form-item>
<el-form-item label="课程介绍" prop="content">
<el-input type="textarea" :rows="4" v-model="data.form.content" autocomplete="off" />
</el-form-item>
<el-form-item label="课程学分" prop="score">
<el-input v-model="data.form.score" autocomplete="off" />
</el-form-item>
<el-form-item label="开班人数" prop="num">
<el-input v-model="data.form.num" autocomplete="off" />
</el-form-item>
<el-form-item label="上课时间" prop="time">
<el-input v-model="data.form.time" autocomplete="off" />
</el-form-item>
<el-form-item label="上课地点" prop="location">
<el-input v-model="data.form.location" autocomplete="off" />
</el-form-item>
<!-- 授课教师 绑定的是教师的id 显示的是教师的name 下拉框的宽度为100% 遍历教师信息
设置每个教师的key为id 设置每个教师的label为name 设置每个教师的value为id-->
<el-form-item label="授课教师" prop="teacherId">
<el-select v-model="data.form.teacherId" placeholder="请选择教师" style="width: 100%">
<el-option v-for="item in data.teacherDate"
:key="item.id"
:label="item.name"
:value="item.id">
</el-option>
</el-select>
</el-form-item>
<el-form-item label="所属学院" prop="collegeId">
<!-- 专业信息是关联学院的,所以在新增(编辑)专业信息的时候,需要选择对应的学院,绑定起来。-->
<el-select v-model="data.form.collegeId" placeholder="请选择学院" style="width: 100%">
<el-option v-for="item in data.collegeDate"
:key="item.id"
:label="item.name"
:value="item.id">
</el-option>
<!-- v-model="data.form.collegeId" 绑定专业信息的学院id-->
<!-- placeholder="请选择学院" 提示用户选择学院-->
<!-- style="width: 100%" 设置下拉框的宽度为100%-->
<!-- v-for="item in data.collegeDate" 遍历学院信息-->
<!-- :key="item.id" 设置每个学院的key为id-->
<!-- :label="item.name" 设置每个学院的label为name-->
<!-- :value="item.id" 设置每个学院的value为id-->
</el-select>
</el-form-item>
</el-form>
<template #footer>
<span class="dialog-footer">
<el-button @click="data.formVisible = false">取 消</el-button>
<el-button type="primary" @click="save">保 存</el-button>
</span>
</template>
</el-dialog>

</div>
</template>

<script setup>
import request from "@/utils/request";
import {reactive} from "vue";
import {ElMessageBox, ElMessage} from "element-plus";


const data = reactive({
pageNum: 1,
pageSize: 10,
total: 0,
formVisible: false,
form: {},
tableData: [],
name: null,
collegeDate: [],// 用于存储学院信息
teacherDate: []// 用于存储教师信息
})

// 分页查询
const load = () => {
request.get('/course/selectPage', {
params: {
pageNum: data.pageNum,
pageSize: data.pageSize,
name: data.name
}
}).then(res => {
data.tableData = res.data?.list
data.total = res.data?.total
})
}

// 新增
const handleAdd = () => {
data.form = {}
data.formVisible = true
}

// 编辑
const handleEdit = (row) => {
data.form = JSON.parse(JSON.stringify(row))
data.formVisible = true
}

// 新增保存
const add = () => {
request.post('/course/add', data.form).then(res => {
if (res.code === '200') {
load()
ElMessage.success('操作成功')
data.formVisible = false
} else {
ElMessage.error(res.msg)
}
})
}

// 编辑保存
const update = () => {
request.put('/course/update', data.form).then(res => {
if (res.code === '200') {
load()
ElMessage.success('操作成功')
data.formVisible = false
} else {
ElMessage.error(res.msg)
}
})
}

// 弹窗保存
const save = () => {
// data.form有id就是更新,没有就是新增
data.form.id ? update() : add()
}

// 删除
const handleDelete = (id) => {
ElMessageBox.confirm('删除后数据无法恢复,您确定删除吗?', '删除确认', { type: 'warning' }).then(res => {
request.delete('/course/deleteById/' + id).then(res => {
if (res.code === '200') {
load()
ElMessage.success('操作成功')
} else {
ElMessage.error(res.msg)
}
})
}).catch(err => {})
}

// 重置
const reset = () => {
data.name = null
load()
}

const loadTeacher = () => {//查询所有教师信息
request.get('/teacher/selectAll').then(res => {//调用后端接口查询所有教师信息
if (res.code === '200') {//如果查询成功,将查询到的教师信息赋值给data.teacherDate
data.teacherDate = res.data
}else {//如果查询失败,提示用户
ElMessage.error(res.msg)
}
})
}

const loadCollege= () => {//查询所有学院信息
request.get('/college/selectAll').then(res => {//调用后端接口查询所有学院信息
if (res.code === '200') {//如果查询成功,将查询到的学院信息赋值给data.collegeDate
data.collegeDate = res.data
}else {//如果查询失败,提示用户
ElMessage.error(res.msg)
}
})
}

load()
loadCollege()
loadTeacher()
</script>

entity—Course.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
public class Course {
private Integer id;
private String name;
private String content;
private Integer score;
private Integer teacherId;
private String teacherName;
private Integer num;
private String time;
private String location;
private Integer collegeId;
private String collegeName;
private Integer alreadyNum;

public Integer getId() {
return id;
}

public void setId(Integer id) {
this.id = id;
}

public String getName() {
return name;
}

public void setName(String name) {
this.name = name;
}

public String getContent() {
return content;
}

public void setContent(String content) {
this.content = content;
}

public Integer getScore() {
return score;
}

public void setScore(Integer score) {
this.score = score;
}

public Integer getTeacherId() {
return teacherId;
}

public void setTeacherId(Integer teacherId) {
this.teacherId = teacherId;
}

public String getTeacherName() {
return teacherName;
}

public void setTeacherName(String teacherName) {
this.teacherName = teacherName;
}

public Integer getNum() {
return num;
}

public void setNum(Integer num) {
this.num = num;
}

public String getTime() {
return time;
}

public void setTime(String time) {
this.time = time;
}

public String getLocation() {
return location;
}

public void setLocation(String location) {
this.location = location;
}

public Integer getCollegeId() {
return collegeId;
}

public void setCollegeId(Integer collegeId) {
this.collegeId = collegeId;
}

public String getCollegeName() {
return collegeName;
}

public void setCollegeName(String collegeName) {
this.collegeName = collegeName;
}

public Integer getAlreadyNum() {
return alreadyNum;
}

public void setAlreadyNum(Integer alreadyNum) {
this.alreadyNum = alreadyNum;
}
}

Controller—CourseController.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
/**
* 课程信息模块前端操作接口入口
* 拿到数据后,调用service层的方法,返回结果
* 前端调用接口时,需要传入参数,调用service层的方法,返回结果
**/
@RestController

@RequestMapping("/course")
public class CourseController {
@Resource
// 注入CourseService
private CourseService courseService;

/**
* 新增课程信息
* */
@PostMapping("/add")
public Result add(@RequestBody Course course){
courseService.add(course);
return Result.success();
}

/**
* 更新课程信息
*/
@PutMapping("/update")//更新课程信息信息,前端调用接口时,需要传入参数,调用service层的方法,返回结果
public Result update(@RequestBody Course course){//接收前端传来的参数
courseService.updateById(course);//调用service层的方法,返回结果
return Result.success();
}

/**
* 删除课程信息
*/
@DeleteMapping("/deleteById/{id}")
public Result deleteById(@PathVariable Integer id) {
courseService.deleteById(id);
return Result.success();
}

/**
* 分页查询
* */
@GetMapping("selectPage")
public Result selectPage(Course course,
@RequestParam(defaultValue = "1") Integer pageNum,
@RequestParam(defaultValue = "5") Integer pageSize){
// 调用service层的方法,返回结果
PageInfo<Course> pageInfo = courseService.selectPage(course,pageNum,pageSize);
// 总数
return Result.success(pageInfo);
}
/**
* 查询所有课程信息
*/
@GetMapping("/selectAll")
public Result selectAll(){
List<Course> list = courseService.selectAll();
return Result.success(list);
}
}

Service—CourseService.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
/**
* 课程模块业务逻辑接口
* 要把数据往数据库里存,调用mapper层的方法,返回结果
* 业务逻辑接口调用mapper层的方法,返回结果
*/
@Service
public class CourseService {
// 注入CourseMapper
@Resource
private CourseMapper courseMapper;
/**
* 新增课程
*/
public void add(Course course) {
course.setAlreadyNum(0);//设置已选人数为0
courseMapper.insert(course);//调用mapper层的方法,返回结果
}
/**
* 分页查询
*/
public PageInfo<Course> selectPage(Course course,Integer pageNum, Integer pageSize) {
// ToDo 分页查询逻辑处理
// 1. 分页查询课程信息
// 2. 返回课程信息
// 3. 如果没有课程信息,返回空列表
// 4. 如果有课程信息,返回课程信息列表
List<Course> list;//定义一个list集合
PageHelper.startPage(pageNum,pageSize);//分页查询
if(ObjectUtil.isNotEmpty(course.getName())){//如果name不为空,就查询name对应的课程信息
list = courseMapper.selectByName(course.getName());
}else{//如果name为空,就查询所有课程信息
list = courseMapper.selectAll();
}
return PageInfo.of(list);//返回课程信息列表
}

//根据id查询课程信息,返回一个course对象
public void updateById(Course course) {//传入一个course对象
courseMapper.updateById(course);//调用mapper层的方法,返回结果
}


//根据id删除课程信息
public void deleteById(Integer id) {
courseMapper.deleteById(id);
}
//查询所有课程信息
public List<Course> selectAll() {
return courseMapper.selectAll();
}
}

Mapper

CourseMapper.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
@Mapper
public interface CourseMapper {
//新增
void insert(Course course);

//查询所有
@Select("select course.*, college.name as collegeName,teacher.name as teacherName from course " +
"left join college on course.college_id = college.id " +
"left join teacher on course.teacher_id = teacher.id")
//查询所有专业信息,并且把专业信息对应的学院名称也查询出来,并且把专业信息对应的教师名称也查询出来
List<Course> selectAll();

//根据name查询
@Select("select course.*, college.name as collegeName, teacher.name as teacherName from course " +
"left join college on course.college_id = college.id " +
"left join teacher on course.teacher_id = teacher.id " +
"where course.name like concat('%',#{name},'%')")
//查询所有专业信息,并且把专业信息对应的学院名称也查询出来,并且把专业信息对应的教师名称也查询出来,并且模糊查询
List<Course> selectByName(String name);

//修改
void updateById(Course course);

//删除
@Delete("delete from course where id = #{id}")
void deleteById(Integer id);
}

CourseMapper.xml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.example.mapper.CourseMapper">
<insert id="insert" parameterType="com.example.entity.Course" useGeneratedKeys="true">
insert into course (name, content, score, teacher_id, num, time, location, college_id, already_num)
values (#{name}, #{content}, #{score}, #{teacherId}, #{num}, #{time}, #{location}, #{collegeId}, #{alreadyNum})
</insert>

<update id="updateById" parameterType="com.example.entity.Course">
update course
set name = #{name},
content = #{content},
score = #{score},
teacher_id = #{teacherId},
num = #{num},
time = #{time},
location = #{location},
college_id = #{collegeId},
already_num = #{alreadyNum}
where id = #{id}
-- 这里的id是实体类中的属性名,不是数据库中的字段名
</update>
</mapper>

id="insert":对应Mapper接口中的方法名
parameterType:指定参数类型为Course实体类
useGeneratedKeys="true":启用自增主键
SQL语句将实体类属性映射到数据库字段:
#{name}对应实体类的name属性
teacher_id字段对应实体类的teacherId属性(MyBatis自动转换驼峰命名)

涉及的主要知识点可以总结如下:

MyBatis持久层框架:

XML映射文件配置(如CourseMapper.xml
SQL语句编写(INSERT/UPDATE语句)
参数绑定(#{fieldName}语法)
结果集映射(自动映射到实体类)

Spring Boot核心:

RESTful API设计(@RestController
请求映射(@RequestMapping, @PostMapping等)
依赖注入(@Resource, @Autowired
分层架构(Controller-Service-Mapper

数据库操作:

CRUD操作(增删改查)
事务管理(默认自动提交)
主键自增(useGeneratedKeys="true"

实体类设计:

与数据库表字段映射
关联关系(如teacher_id关联教师表)
驼峰命名与下划线命名转换(如teacherId -> teacher_id

业务逻辑:

新增课程时初始化已选人数(setAlreadyNum(0)
分页查询实现(PageHelper
条件查询(按课程名称模糊查询)

前后端交互:

JSON数据格式(@RequestBody
统一响应格式(Result对象)
参数传递(路径参数@PathVariable,查询参数@RequestParam

关联查询:

多表联查(left join教师和学院表)
结果集扩展(返回教师姓名而非ID)

角色权限控制

逻辑

角色划分:

系统有三种角色:管理员(ADMIN)、教师(TEACHER)和学生(STUDENT)
每个用户登录后,系统会根据其角色显示不同的菜单和操作权限

前端控制:

通过v-if="data.user.role === 'ADMIN'"这类判断语句控制按钮/菜单的显示
例如:只有管理员能看到”新增课程”按钮,教师只能看到自己教授的课程

后端验证:

后端接口会根据用户角色返回不同数据
例如教师查询课程时,会自动过滤只返回该教师自己的课程
权限示例:

管理员:可以管理所有用户、课程、学院等信息
教师:只能管理自己教授的课程,查看自己的课表
学生:只能选课、查看自己的课程和成绩

数据存储:

用户登录后,角色信息会保存在localStorage中(system-user)
每次请求都会携带这个角色信息,后端会进行验证

简单来说就是:不同身份的人进系统后,看到的东西和能做的事情不一样。

管理员什么都能管,老师只能管自己的课,学生只能选课看课。

系统会根据你是谁,自动显示你能用的功能。

image-20250428165403408

user.role,那么如果这个user是个undefined(未被定义)的时候,再去访问这个user里面的某个属性变量的时候,就会报这种错误。

课程信息,多角色权限

Course.vue

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
<div class="card" style="margin-bottom: 5px">
<div style="margin-bottom: 10px" v-if ="data.user.role === 'ADMIN'">
<el-button type="primary" @click="handleAdd">新增</el-button>
</div>
<el-table :data="data.tableData" stripe>
<el-table-column label="课程名称" prop="name"></el-table-column>
<el-table-column label="课程介绍" prop="content" show-overflow-tooltip></el-table-column>
<el-table-column label="课程学分" prop="score"></el-table-column>
<el-table-column label="授课教师" prop="teacherName"></el-table-column>
<el-table-column label="开班人数" prop="num"></el-table-column>
<el-table-column label="上课时间" prop="time"></el-table-column>
<el-table-column label="上课地点" prop="location"></el-table-column>
<el-table-column label="所属学院" prop="collegeName"></el-table-column>
<el-table-column label="已选人数" prop="alreadyNum"></el-table-column>
<el-table-column label="操作" align="center" width="160" v-if ="data.user.role !== 'TEACHER'">
<template #default="scope" v-if ="data.user.role === 'ADMIN'">
<el-button type="primary" @click="handleEdit(scope.row)">编辑</el-button>
<el-button type="danger" @click="handleDelete(scope.row.id)">删除</el-button>
</template>
<template #default="scope" v-else>
<el-button type="primary" @click="">选课</el-button>

</template>
</el-table-column>
</el-table>
</div>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
const data = reactive({
user: JSON.parse(localStorage.getItem('system-user') || '{}'),// 获取当前登录的用户信息
pageNum: 1,
pageSize: 10,
total: 0,
formVisible: false,
form: {},
tableData: [],
name: null,
collegeDate: [],// 用于存储学院信息
teacherDate: []// 用于存储教师信息
})

// 分页查询
const load = () => {
let teacherId = null// 用于存储教师id
if (data.user.role === 'TEACHER') {
teacherId = data.user.id// 如果是教师,就查询自己的课程信息
}
request.get('/course/selectPage', {
params: {
pageNum: data.pageNum,
pageSize: data.pageSize,
name: data.name,
teacherId: teacherId,// 如果是教师,就查询自己的课程信息
}
}).then(res => {
data.tableData = res.data?.list
data.total = res.data?.total
})
}

CourseService.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
/**
* 分页查询
*/
public PageInfo<Course> selectPage(Course course,Integer pageNum, Integer pageSize) {
// ToDo 分页查询逻辑处理
// 1. 分页查询课程信息
// 2. 返回课程信息
// 3. 如果没有课程信息,返回空列表
// 4. 如果有课程信息,返回课程信息列表
List<Course> list;//定义一个list集合
PageHelper.startPage(pageNum,pageSize);//分页查询
//表示当前登录是教师
if(ObjectUtil.isNotEmpty(course.getTeacherId())){//如果teacherId不为空,就查询teacherId对应的课程信息
Integer teacherId = course.getTeacherId();
//如果name不为空,就查询name对应的课程信息,否则就查询所有课程信息
if (ObjectUtil.isNotEmpty(course.getName())) {//如果name不为空,就查询name对应的课程信息
list = courseMapper.selectByNameAndTeacherId(course.getName(),teacherId);
} else {//如果name为空,就查询所有课程信息
list = courseMapper.selectAllByTeacherId(teacherId);
}
}
else {
//如果name不为空,就查询name对应的课程信息,否则就查询所有课程信息
if (ObjectUtil.isNotEmpty(course.getName())) {//如果name不为空,就查询name对应的课程信息
list = courseMapper.selectByName(course.getName());
} else {//如果name为空,就查询所有课程信息
list = courseMapper.selectAll();
}
}
return PageInfo.of(list);//返回课程信息列表
}

CourseMapper.java

1
2
3
4
5
6
7
8
9
10
11
12
13
//根据name查询,并且根据teacherId查询    模糊查询
@Select("select course.*, college.name as collegeName, teacher.name as teacherName from course " +
"left join college on course.college_id = college.id " +
"left join teacher on course.teacher_id = teacher.id " +
"where course.name like concat('%',#{name},'%') and teacher_id = #{teacherId}")
List<Course> selectByNameAndTeacherId(@Param("name") String name, @Param("teacherId") Integer teacherId);

//根据teacherId查询,并且把专业信息对应的学院名称也查询出来,把专业信息对应的教师名称也查询出来
@Select("select course.*, college.name as collegeName,teacher.name as teacherName from course " +
"left join college on course.college_id = college.id " +
"left join teacher on course.teacher_id = teacher.id " +
"where teacher_id = #{teacherId}")
List<Course> selectAllByTeacherId(Integer teacherId);

同一个功能模块里面(同一个页面里面),不同的角色有不同的权限(权限的控制),达到不同的角色有不同的功能的效果。