3.Mybatis 基础操作
3.1 打印日志
通过调整 application.yml 配置文件 , 显示日志 ; 查询 sql 语句执行 , 传参 , 结果
java
mybatis:
configuration:
log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
不加日志配置文件

添加日志配置文件

3.2 参数传递 ( #{} )
编写 sql
java
@Select("SELECT * FROM user_info where id = #{id}")
UserInfo queryById(Integer id);
生成 test 并编写 test
java
@Test
public void queryById() {
System.out.println(userInfoMapper.queryById(4));
}

注意 : 如果遇到代码中无 高亮显示 , 可能是 IDEA 索引缓存损坏 , 请重启 IDEA
也可以通过@Param , 设置参数别名 , 如果使用别名 , 那么 #{ } 中的属性名必须和@Param 设置的一样
java
@Select("SELECT * FROM user_info where id=#{UID}")
UserInfo queryById(@Param("UID") Integer id);
3.3 结果映射(重要)

问题 : 查询数据库后发现 , 有几个字段没有赋值成功 , 结果还是 null
原因 : Mybatis 字段名与实体类名映射不匹配导致的问题

解决方法
- 开启自动驼峰映射
在 application.yml 配置文件中
java
mybatis:
configuration:
map-underscore-to-camel-case: true
- 给数据库列名起别名
java
@Select("SELECT id, username, password, age, gender, phone, " +
"delete_flag AS deleteFlag, " +
"create_time AS createTime, " +
"update_time AS updateTime " +
"FROM user_info")
List<UserInfo> selectAll3();
java
@Test
public void selectAll3() {
System.out.println(userInfoMapper.selectAll());
- 使用结果集映射(@Result,@ResultMap)
java
@Results({
@Result(column = "delete_flag",property = "deleteFlag"),
@Result(column = "create_time",property = "createTime"),
@Result(column = "update_time",property = "updateTime")
})
@Select("SELECT * FROM user_info")
List<UserInfo> selectAll();
如果想要服用结果集 , 需要使用 id 属性给结果集起别名 , 在使用@ResultMap 注解来复用结果集
java
@Results(id="resulmp1",value = {
@Result(column = "delete_flag",property = "deleteFlag"),
@Result(column = "create_time",property = "createTime"),
@Result(column = "update_time",property = "updateTime")
})
@Select("SELECT * FROM user_info")
List<UserInfo> selectAll();
@ResultMap(value = "resulmp1")
@Select("SELECT * FROM user_info where id=#{UID}")
UserInfo queryById(@Param("UID") Integer id);
三.MyBatisCRUD 全套模板 (注解型)
1.新增(@Insert)
java
@Insert("insert into user_info(username,`password`,age,gender,phone) values (#{username} , #{password},#{age},#{gender},#{phone})")
Integer insert(UserInfo userInfo);
java
@Test
void insert() {
UserInfo usr = new UserInfo();
usr.setUsername("zhichi0");
usr.setPassword("123456");
usr.setAge((byte) 21);
usr.setGender((byte) 1);
usr.setPhone("15645685465");
userInfoMapper.insert(usr);
}

注意 : #{username} 中的字段名 必须与实体类里的字段名完全一致 ; 书写顺序无所谓
如果设置了@Param 需要使用 [ 参数.属性 ] 来获取
java
@Insert("insert into user_info(username,`password`,age,gender,phone) values (#{userInfo.username},#{userInfo.password},#{userInfo.age},#{userInfo.gender},#{userInfo.phone})")
Integer insert(@Param("userInfo") UserInfo us);
参数中的 us 可以随便写 ,真正对应的@Param("userInfo")
insert 语句默认返回的是 受影响的行数
返回主键
如果想要拿到自增 id , 需要在 Mapper 接口的方法上添加 Options 注解
java
//获取自增主键
@Options(useGeneratedKeys = true,keyProperty = "id")
@Insert("insert into user_info(username,`password`,age,gender,phone) values (#{userInfo.username},#{userInfo.password},#{userInfo.age},#{userInfo.gender},#{userInfo.phone})")
Integer insert2(@Param("userInfo") UserInfo us);
java
@Test
void insert2() {
UserInfo usr = new UserInfo();
usr.setUsername("zhichi0");
usr.setPassword("123456");
usr.setAge((byte) 21);
usr.setGender((byte) 1);
usr.setPhone("15645685465");
Integer count = userInfoMapper.insert(usr);
System.out.println("添加数据条数:" +count +", 数据ID:" + usr.getId());
}

- useGeneratedKeys = true : 开启主键回填功能 , 让 Mybatis 调用 JDBC 的 getGeneratedKeys() 方法 , 获取数据库自动生成的自增主键 ; 默认值为 false
- keyProperty = "id" : 指定将生成的主键值 , 回调到 Java 实体类的哪个属性中 ; 注意这里不是数据库表的字段名
2.删(@Delete)
java
//删除
@Delete("delete from user_info where id = #{id}")
void delete(Integer id);
java
@Test
void delete() {
userInfoMapper.delete(5);
}

注意 :
- SQL 语句拼写问题 ;
- 数据库内容是否合法(是否包含此内容)
3.改(Update)
java
//修改
@Update("update user_info set username=#{username} where id=#{id}")
void update(UserInfo us);
java
@Test
void update() {
UserInfo usr = new UserInfo();
usr.setUsername("787878");
usr.setId(5);
userInfoMapper.update(usr);
}
4.查询(Select)
上述代码已经编写了很多查询相关的代码,并演示问题 , 此处不再演示
对象使用关系
- 需要封装数据(新增 / 修改) → new UserInfo
- 需要调用数据库方法(增删改查) → userInfoMapper
四.XML 实现 CRUD
1.相关配置文件及模板
application.yml , 配置 xml 文件路径
java
# 配置 mybatis xml 的⽂件路径,在 resources/mapper 创建所有表的 xml ⽂件
mapper-locations: classpath:mapper/**MapperXML.xml

① 添加 Mapper 接口
java
package com.boop.mybatis.mapper;
import com.boop.mybatis.model.UserInfo;
import org.apache.ibatis.annotations.Mapper;
import java.util.List;
@Mapper
public interface UserInfoMapperXML {
List<UserInfo> queryAllUser();
}
② 添加 UserInfoMapperXML.xml (路径参考 yml 文件中的配置)
java
<?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">
<!-- namespace 必须是 Mapper 接口的全类名 -->
<mapper namespace="com.boop.mybatis.mapper.UserInfoMapperXML">
<!-- 这里写 select/insert/update/delete -->
<select id="queryAllUser" resultType = "com.boop.mybatis.model.UserInfo">
select * from user_info
</select>
</mapper>
③ 单元测试
java
package com.boop.mybatis.mapper;
import com.boop.mybatis.model.UserInfo;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import java.util.List;
import static org.junit.jupiter.api.Assertions.*;
@SpringBootTest
class UserInfoMapperXMLTest {
@Autowired
private UserInfoMapperXML userInfoMapperXML;
@Test
void queryAllUser() {
List<UserInfo> userInfoList = userInfoMapperXML.queryAllUser();
System.out.println(userInfoList);
}
}
2.完整 CRUD 模板
完整配置文件
java
spring:
application:
name: Mybatis
# 数据库连接配置
datasource:
url: jdbc:mysql://127.0.0.1:3306/mybatis_test?characterEncoding=utf8&useSSL=false
username: root
password: 123456
driver-class-name: com.mysql.cj.jdbc.Driver
mybatis:
configuration:
log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
map-underscore-to-camel-case: true
# 配置 mybatis xml 的⽂件路径,在 resources/mapper 创建所有表的 xml ⽂件
mapper-locations: classpath:mapper/**MapperXML.xml
可以根据 IDEA 自动生成 XML 的 SQL 的格式 , 只需要填写注解类似的 SQL 语句

①Mapper 接口
java
@Mapper
public interface UserInfoMapperXML {
// 查询全部
List<UserInfo> queryAllUser();
// 根据ID查询
UserInfo queryById(Integer id);
// 新增
Integer insert(UserInfo userInfo);
// 修改
Integer update(UserInfo userInfo);
// 删除
Integer delete(Integer id);
}
②XML 格式的 SQL
java
<?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.boop.mybatis.mapper.UserInfoMapperXML">
<resultMap id="UserinfoXMLMap" type="com.boop.mybatis.model.UserInfo">
<id column="id" property="id"></id>
<result column="delete_flag" property="deleteFlag"></result>
<result column="create_time" property="createTime"></result>
<result column="update_time" property="updateTime"></result>
</resultMap>
<!-- 查询全部用户 -->
<select id="queryAllUser" resultType = "com.boop.mybatis.model.UserInfo">
select * from user_info
</select>
<!-- 根据ID查询 -->
<select id="queryById" resultType="com.boop.mybatis.model.UserInfo">
select * from user_info where id = #{id}
</select>
<!-- 新增用户 -->
<insert id="insert" useGeneratedKeys="true"
keyProperty="id">
insert into user_info (username,`password`,age,gender,phone) values (#{username},#{password},#{age},#{gender},#{phone})
</insert>
<!-- 修改用户 -->
<update id="update">
update user_info
set username = #{username},
password = #{password},
age = #{age},
gender = #{gender},
phone = #{phone}
where id = #{id}
</update>
<!-- 删除用户 -->
<delete id="delete">
delete from user_info where id = #{id}
</delete>
</mapper>
③ 测试用例
java
package com.boop.mybatis.mapper;
import com.boop.mybatis.model.UserInfo;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import java.util.List;
import static org.junit.jupiter.api.Assertions.*;
@SpringBootTest
class UserInfoMapperXMLTest {
@Autowired
private UserInfoMapperXML userInfoMapperXML;
@Test
void queryAllUser() {
List<UserInfo> userInfoList = userInfoMapperXML.queryAllUser();
System.out.println(userInfoList);
}
@Test
void queryById() {
UserInfo us = userInfoMapperXML.queryById(1);
System.out.println(us);
}
@Test
void insert() {
UserInfo user = new UserInfo();
user.setUsername("testUser");
user.setPassword("123456");
user.setAge((byte) 20);
user.setGender((byte) 1);
user.setPhone("13800138000");
int rows = userInfoMapperXML.insert(user);
System.out.println("=== 新增影响行数:" + rows + " ===");
System.out.println("新增后自增ID:" + user.getId());
}
@Test
void update() {
UserInfo user = new UserInfo();
user.setId(5);
user.setUsername("updateName");
user.setPassword("updatePwd");
user.setAge((byte) 20);
user.setGender((byte) 1);
user.setPhone("13900139000");
int rows = userInfoMapperXML.update(user);
System.out.println("=== 更新影响行数:" + rows + " ===");
}
@Test
void delete() {
int rows = userInfoMapperXML.delete(5); // 把 5 改成你库里存在的 ID
System.out.println("=== 删除影响行数:" + rows + " ===");
}
}
XML 的结果集映射(解决数据库字段和实体类字段名称不匹配的问题)
XML
<resultMap id="UserinfoXMLMap" type="com.boop.mybatis.model.UserInfo">
<id column="id" property="id"></id>
<result column="delete_flag" property="deleteFlag"></result>
<result column="create_time" property="createTime"></result>
<result column="update_time" property="updateTime"></result>
</resultMap>
