- 发布日期
员工管理:查询回显、ResultMap与动态更新
- 作者
- 姓名
- 缘
- 社交账号
文章目录
修改员工的两个阶段
员工编辑通常包含:
查询回显
+
提交修改
员工基本信息保存在 emp,工作经历保存在 emp_expr,所以详情不是简单单表查询。
实体对象中包含:
private List<EmpExpr> exprList;
用于封装多条工作经历。
根据ID查询员工详情
@GetMapping("/{id}")
public Result getInfo(@PathVariable Integer id) {
log.info("根据id查询员工信息, id: {}", id);
Emp emp = empService.getInfo(id);
return Result.success(emp);
}
查询需要连接两张表:
select ...
from emp e
left join emp_expr ee on e.id = ee.emp_id
where e.id = ?;
一个员工可能对应多条工作经历,因此需要把多行结果封装为一个 Emp 和一个 List<EmpExpr>。
resultType与resultMap
课程结论:
- 字段名和实体属性可以直接对应时,使用
resultType。 - 字段名无法直接对应,或者实体属性结构复杂时,使用
resultMap手动封装。
自定义resultMap
<resultMap id="empResultMap" type="com.itheima.pojo.Emp">
<id column="id" property="id" />
<result column="username" property="username" />
<result column="password" property="password" />
<result column="name" property="name" />
<result column="gender" property="gender" />
<result column="image" property="image" />
<result column="entry_date" property="entryDate" />
<result column="dept_id" property="deptId" />
<result column="create_time" property="createTime" />
<result column="update_time" property="updateTime" />
<collection property="exprList" ofType="com.itheima.pojo.EmpExpr">
<id column="ee_id" property="id"/>
<result column="ee_company" property="company"/>
<result column="ee_job" property="job"/>
<result column="ee_begin" property="begin"/>
<result column="ee_end" property="end"/>
<result column="ee_empid" property="empId"/>
</collection>
</resultMap>
collection 用于映射集合属性,property="exprList" 对应 Emp 中的列表,ofType 指定集合元素类型。
查询SQL字段别名
为避免 emp 与 emp_expr 中同名字段冲突,课程给工作经历字段起别名:
<select id="getById" resultMap="empResultMap">
select
e.*,
ee.id ee_id,
ee.company ee_company,
ee.job ee_job,
ee.begin ee_begin,
ee.end ee_end,
ee.emp_id ee_empid
from emp e
left join emp_expr ee on e.id = ee.emp_id
where e.id = #{id}
</select>
修改员工数据
@PutMapping
public Result update(@RequestBody Emp emp) {
log.info("修改员工信息, {}", emp);
empService.update(emp);
return Result.success();
}
Service 中的处理流程:
更新员工基本信息
↓
删除原工作经历
↓
插入新的工作经历
课程代码:
@Transactional(rollbackFor = Exception.class)
public void update(Emp emp) {
emp.setUpdateTime(LocalDateTime.now());
empMapper.updateById(emp);
empExprMapper.deleteByEmpIds(Arrays.asList(emp.getId()));
Integer empId = emp.getId();
List<EmpExpr> exprList = emp.getExprList();
if (!CollectionUtils.isEmpty(exprList)) {
exprList.forEach(empExpr -> empExpr.setEmpId(empId));
empExprMapper.insertBatch(exprList);
}
}
因为涉及多次数据库操作,所以同样需要事务。
动态更新
固定 Update 会更新所有字段,不够灵活。MyBatis 可以通过 <if> 根据实际参数决定是否生成字段:
<if test="name != null and name != ''">
name = #{name},
</if>
多个 <if> 容易产生末尾多余逗号,因此使用 <set>:
<update id="updateById">
update emp
<set>
<if test="username != null and username != ''">
username = #{username},
</if>
<if test="name != null and name != ''">
name = #{name},
</if>
<if test="gender != null">
gender = #{gender},
</if>
<if test="updateTime != null">
update_time = #{updateTime},
</if>
</set>
where id = #{id}
</update>
这样就能实现“传哪些字段,就更新哪些字段”。
核心知识点
左连接查询
+
resultMap
+
collection
+
动态SQL
+
<if>
+
<set>
+
事务
这一部分比普通单表 CRUD 更接近真实业务中的复杂数据处理。