MyBatis 进阶
复杂CURD
返回设置
返回类型:resultType
-
绝⼤数查询场景可以使⽤ resultType 进⾏返回,如下代码所示:
-
它的优点是使⽤⽅便,直接定义到某个实体类即可
-
<select id="getbyUserid" resultType="com.example.mybatis3.entity.Userinfo"> select * from userinfo where id =${id} </select>
-
-
返回字典映射:resultMap
-
resultMap 使⽤场景:
- 字段名称和程序中的属性名不同的情况,可使⽤ resultMap 配置映射;
- ⼀对⼀和⼀对多关系可以使⽤resultMap映射并查询数据。
- 字段名称和程序中的属性名不同的情况,可使⽤ resultMap 配置映射;
-
字段名和属性名不同的情况
-
使用场景:
-
实现实体类中的属性 和 字段映射的功能
-
<resultMap id="userMap" type="com.example.mybatis3.entity.Userinfo"> <id column="id" property="id"/> <result column="username" property="username"/> <result column="password" property="password"/> <result column="photo" property="photo"/> </resultMap>
-
<select id="getbyUserid" resultMap="userMap"> select * from userinfo where id =${id} </select>
-
-
-
当实体类属性名与数据库中名字不一致时:
- 使用 resultMap 进行映射
- 使用 数据库别名 as 重命名 (推荐)
多表查询
- 在多表查询时,如果使⽤ resultType 标签
- 在⼀个类中包含了另⼀个对象是查询不出来被包含的对象的
- ⽐如以下实体类:
- 最终实现:
- 链表查询(left join inner join) + xxxVO
- VO
- view object
- 专门给前端使用的对象
- VO
- 链表查询(left join inner join) + xxxVO
动态SQL使⽤
- 动态 sql 是Mybatis的强⼤特性之⼀,能够完成不同条件下不同的 sql 拼接
<if>标签
-
例子:
-
<insert id="add" useGeneratedKeys="true" keyProperty="id"> insert into userinfo( username, password <if test="updateTime != null"> ,updatetime </if> )values( #{username}, #{password} <if test="updateTime != null"> ,#{updatetime} </if>) </insert>
-
-
效果:
<trim>标签
-
trim 通常配合 if 来用
-
如果所有字段都是⾮必填项
- 就考虑使⽤标签结合标签,对多个字段都采取动态⽣成的⽅式
-
标签中有如下属性:
- prefix:表示整个语句块,以prefix的值作为前缀
- suffix:表示整个语句块,以suffix的值作为后缀
- prefixOverrides:表示整个语句块要去除掉的前缀
- suffixOverrides:表示整个语句块要去除掉的后缀
- 有则去除,没有则啥事不干
-
例子:
-
<insert id="add" useGeneratedKeys="true" keyProperty="id"> insert into userinfo <trim prefix="(" suffix=")" suffixOverrides=","> <if test="username != null"> username, </if> <if test="password != null"> password, </if> <if test="photo != null"> photo, </if> </trim> values <trim prefix="(" suffix=")" suffixOverrides=","> <if test="username != null"> #{username}, </if> <if test="password != null"> #{password}, </if> <if test="photo != null"> #{photo}, </if> </trim> </insert>
-
-
效果:
<where>标签
-
传⼊的⽤户对象,根据属性做 where 条件查询,⽤户对象中属性不为 null 的,都为查询条件。
-
where 可以去除 最前面的 and
- 不会删除最后面的
-
标签也可以使⽤ 替换
-
例:
-
<select id="getListByParm" resultType="com.example.mybatis3.entity.Userinfo"> select * from userinfo <where> <if test="username != null"> username = #{username} </if> <if test="password != null"> and password = #{password} </if> </where> </select>
-
-
效果:
<set>标签
-
根据传⼊的⽤户对象属性来更新⽤户数据,可以使⽤标签来指定动态内容
-
<update id="upUser"> update userinfo <set> <if test="username != null"> username = #{username}, </if> <if test="password != null"> password = #{password}, </if> </set> where id=#{id} </update>
-
-
以上标签也可以使⽤ 替换
<foreach>标签
-
对集合进⾏遍历时可以使⽤该标签。标签有如下属性:
- collection:
- 绑定⽅法参数中的集合,如 List,Set,Map或数组对象
- item:遍历时的每⼀个对象
- open:语句块开头的字符串
- close:语句块结束的字符串
- separator:每次遍历之间间隔的字符串
- collection:
-
例:
-
int deleteUsers(List<Integer> ids);
-
<delete id="deleteUsers"> delete from userinfo where id in <foreach collection="ids" item="id" open="(" close=")" separator=","> #{id} </foreach> </delete>
-
-
效果:
其他
打开日志
mybatis:
mapper-locations: classpath:mapper/**Mapper.xml
configuration: # 配置打印 MyBatis 执行的 SQL
log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
# 配置打印 MyBatis 执行的 SQL
logging:
level:
com:
example:
mybatis3: debug
- 日志内容:
- mybatis底层 就是 JDBC
- mybatis底层 就是 JDBC
单元测试不污染数据库
-
加上@Transactional注解:
-
可以加到类或者方法上
-
@SpringBootTest @Transactional class UserinfoMapperTest { @Autowired private UserinfoMapper userinfoMapper; @Test void deleteUser() { int i = userinfoMapper.deleteUser(2); System.out.println(i); Assertions.assertEquals(1,i); } }
-
-
效果:
- 执行成功
- 并且数据库中数据未删除
- 执行成功