第 2 章 MybatisPlus 通用 CRUD

1、概述

回想一下,如果我们有一张 User 表,并且已经创建好了对应的实体类,实现 User 表的 CRUD 操作我们需要做什么呢?

Mybatis 通用 CRUD 的步骤

首先我们需要编写 UserMapper 映射接口,手动在 UserMapper 接口中定义 CRUD 方法

接着我们需要创建 UserMapper.xml 映射文件,并手动编写每个方法对应的 SQL 语句

MybatisPlus 通用 CRUD 的步骤

只需要创建 UserMapper 接口,并继承 BaseMapper接口。这就是使用 MP 需要完成的所有操作,甚至不需要创建 SQL映射文件,就能使我们自己创建的 Mapper 接口拥有最基本的 CRUD 方法

2、插入操作

0、Insert API

// 插入一条记录
int insert(T entity);

参数说明

类型 参数名 描述
T entity 实体对象

1、插入一条记录:int insert(T entity);

@Test
public void insert() {User userOneby = new User();userOneby.setName("Oneby");userOneby.setAge(21);userOneby.setEmail("Oneby@baomidou.com");int result = userMapper.insert(userOneby);System.out.println("影响行数:" + result);System.out.println(userOneby);User userHeygo = new User();userHeygo.setName("Heygo");userHeygo.setAge(21);userHeygo.setEmail(null);result = userMapper.insert(userHeygo);System.out.println("影响行数:" + result);System.out.println(userHeygo);
}

insert() 方法在插入数据时,会根据实体类的每个属性进行非空判断,只有非空的属性对应的字段才会出现到 SQL 语句中

打印输出 user 对象,其 id 字段不为 null,这说明主键默认自动回填,但是有个问题:主键貌似并不是自增主键,这个问题得请 @TableId 注解来解决,后面会讲

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@51e0301d] was not registered for synchronization because synchronization is not active
2021-04-22 21:45:52.571  INFO 8228 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:45:52.696  INFO 8228 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@2097614581 wrapping com.mysql.cj.jdbc.ConnectionImpl@7a55f148] will not be managed by Spring
==>  Preparing: INSERT INTO user ( id, name, age, email ) VALUES ( ?, ?, ?, ? )
==> Parameters: 1385228362414358529(Long), Oneby(String), 21(Integer), Oneby@baomidou.com(String)
<==    Updates: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@51e0301d]
影响行数:1
User(id=1385228362414358529, name=Oneby, age=21, email=Oneby@baomidou.com)
Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@bd1111a] was not registered for synchronization because synchronization is not active
JDBC Connection [HikariProxyConnection@501650218 wrapping com.mysql.cj.jdbc.ConnectionImpl@7a55f148] will not be managed by Spring
==>  Preparing: INSERT INTO user ( id, name, age ) VALUES ( ?, ?, ? )
==> Parameters: 1385228363135778818(Long), Heygo(String), 21(Integer)
<==    Updates: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@bd1111a]
影响行数:1
User(id=1385228363135778818, name=Heygo, age=21, email=null)

3、更新操作

0、Update API

// 根据 whereWrapper 条件,更新记录
int update(@Param(Constants.ENTITY) T updateEntity, @Param(Constants.WRAPPER) Wrapper<T> whereWrapper);
// 根据 ID 修改
int updateById(@Param(Constants.ENTITY) T entity);

参数说明

类型 参数名 描述
T entity 实体对象 (set 条件值,可为 null)
Wrapper updateWrapper 实体对象封装操作类(可以为 null,里面的 entity 用于生成 where 语句)

1、根据主键修改:int updateById(@Param(Constants.ENTITY) T entity);

@Test
public void updateById() {User user = new User();user.setId(1L);user.setName("Heygo");user.setAge(21);user.setEmail(null);int result = userMapper.updateById(user);System.out.println("影响行数:" + result);User retUser = userMapper.selectById(1);System.out.println(retUser);
}

updateById() 方法在更新数据时,SQL 语句的更新条件为 WHERE id=?,并且会根据实体类的每个属性进行非空判断,只有非空的属性对应的字段才会出现到 SQL 语句中

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@5f303ecd] was not registered for synchronization because synchronization is not active
2021-04-22 21:46:10.286  INFO 18636 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:46:10.411  INFO 18636 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@1066656936 wrapping com.mysql.cj.jdbc.ConnectionImpl@12b5454f] will not be managed by Spring
==>  Preparing: UPDATE user SET name=?, age=? WHERE id=?
==> Parameters: Heygo(String), 21(Integer), 1(Long)
<==    Updates: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@5f303ecd]
影响行数:1
Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@5d01ea21] was not registered for synchronization because synchronization is not active
JDBC Connection [HikariProxyConnection@596905862 wrapping com.mysql.cj.jdbc.ConnectionImpl@12b5454f] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM user WHERE id=?
==> Parameters: 1(Integer)
<==    Columns: id, name, age, email
<==        Row: 1, Heygo, 21, test1@baomidou.com
<==      Total: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@5d01ea21]
User(id=1, name=Heygo, age=21, email=test1@baomidou.com)

2、根据条件构造器修改:int update(@Param(Constants.ENTITY) T entity, @Param(Constants.WRAPPER) Wrapper<T> updateWrapper);

@Test
public void update() {User user = new User();user.setName("NiuNiu");user.setAge(18);user.setEmail(null);QueryWrapper<User> wrapper = new QueryWrapper<>();wrapper.eq("id", 2);wrapper.eq("age", 20);int result = userMapper.update(user, wrapper);System.out.println("影响行数:" + result);User retUser = userMapper.selectById(2);System.out.println(retUser);
}

update() 方法在更新数据时,会根据 wrapper 对象动态拼接 SQL 语句中 WHERE 子句的条件,并且会根据实体类的每个属性进行非空判断,只有非空的属性对应的字段才会出现到 SQL 语句中

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@3b08f438] was not registered for synchronization because synchronization is not active
2021-04-22 21:46:25.325  INFO 20524 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:46:25.450  INFO 20524 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@203401172 wrapping com.mysql.cj.jdbc.ConnectionImpl@7a93b263] will not be managed by Spring
==>  Preparing: UPDATE user SET name=?, age=? WHERE (id = ? AND age = ?)
==> Parameters: NiuNiu(String), 18(Integer), 2(Integer), 20(Integer)
<==    Updates: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@3b08f438]
影响行数:1
Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@6d5037a9] was not registered for synchronization because synchronization is not active
JDBC Connection [HikariProxyConnection@1412612727 wrapping com.mysql.cj.jdbc.ConnectionImpl@7a93b263] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM user WHERE id=?
==> Parameters: 2(Integer)
<==    Columns: id, name, age, email
<==        Row: 2, NiuNiu, 18, test2@baomidou.com
<==      Total: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@6d5037a9]
User(id=2, name=NiuNiu, age=18, email=test2@baomidou.com)

4、查询操作

0、Select API

// 根据 ID 查询
T selectById(Serializable id);
// 根据 entity 条件,查询一条记录
T selectOne(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);// 查询(根据ID 批量查询)
List<T> selectBatchIds(@Param(Constants.COLLECTION) Collection<? extends Serializable> idList);
// 根据 entity 条件,查询全部记录
List<T> selectList(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);
// 查询(根据 columnMap 条件)
List<T> selectByMap(@Param(Constants.COLUMN_MAP) Map<String, Object> columnMap);
// 根据 Wrapper 条件,查询全部记录
List<Map<String, Object>> selectMaps(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);
// 根据 Wrapper 条件,查询全部记录。注意: 只返回第一个字段的值
List<Object> selectObjs(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);// 根据 entity 条件,查询全部记录(并翻页)
IPage<T> selectPage(IPage<T> page, @Param(Constants.WRAPPER) Wrapper<T> queryWrapper);
// 根据 Wrapper 条件,查询全部记录(并翻页)
IPage<Map<String, Object>> selectMapsPage(IPage<T> page, @Param(Constants.WRAPPER) Wrapper<T> queryWrapper);
// 根据 Wrapper 条件,查询总记录数
Integer selectCount(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);

参数说明

类型 参数名 描述
Serializable id 主键ID
Wrapper queryWrapper 实体对象封装操作类(可以为 null)
Collection<? extends Serializable> idList 主键ID列表(不能为 null 以及 empty)
Map<String, Object> columnMap 表字段 map 对象
IPage page 分页查询条件(可以为 RowBounds.DEFAULT)

1、根据主键查询一条记录:T selectById(Serializable id);

@Test
public void selectById() {User user = userMapper.selectById(1);System.out.println(user);
}

selectById() 方法会查询表中所有字段,SQL 语句的筛选条件为 WHERE id=?

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@62e6a3ec] was not registered for synchronization because synchronization is not active
2021-04-22 21:46:38.630  INFO 20528 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:46:38.763  INFO 20528 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@1289834245 wrapping com.mysql.cj.jdbc.ConnectionImpl@71dfcf21] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM user WHERE id=?
==> Parameters: 1(Integer)
<==    Columns: id, name, age, email
<==        Row: 1, Heygo, 21, test1@baomidou.com
<==      Total: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@62e6a3ec]
User(id=1, name=Heygo, age=21, email=test1@baomidou.com)

2、根据主键列表批量查询:List<T> selectBatchIds(@Param(Constants.COLLECTION) Collection<? extends Serializable> idList);

@Test
public void selectBatchIds() {List<User> users = userMapper.selectBatchIds(Arrays.asList(1, 2));users.forEach(System.out::println);
}

selectBatchIds() 方法会查询表中所有字段,SQL 语句的筛选条件为 WHERE id IN ( ? , ? )

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@3be4f71] was not registered for synchronization because synchronization is not active
2021-04-22 21:46:51.438  INFO 8972 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:46:51.563  INFO 8972 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@338765435 wrapping com.mysql.cj.jdbc.ConnectionImpl@342726f1] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM user WHERE id IN ( ? , ? )
==> Parameters: 1(Integer), 2(Integer)
<==    Columns: id, name, age, email
<==        Row: 1, Heygo, 21, test1@baomidou.com
<==        Row: 2, NiuNiu, 18, test2@baomidou.com
<==      Total: 2
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@3be4f71]
User(id=1, name=Heygo, age=21, email=test1@baomidou.com)
User(id=2, name=NiuNiu, age=18, email=test2@baomidou.com)

3、根据 columnMap 条件批量查询:List<T> selectByMap(@Param(Constants.COLUMN_MAP) Map<String, Object> columnMap);

@Test
public void selectByMap() {Map<String, Object> params = new HashMap<>() ;params.put("name", "NiuNiu");params.put("age", 18);List<User> users = userMapper.selectByMap(params);users.forEach(System.out::println);
}

selectByMap() 方法会查询表中所有字段;会根据 Map 对象动态拼接 SQL 语句中 WHERE 子句的筛选条件

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@3be4f71] was not registered for synchronization because synchronization is not active
2021-04-22 21:47:26.111  INFO 9296 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:47:26.252  INFO 9296 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@1061806694 wrapping com.mysql.cj.jdbc.ConnectionImpl@5f18f9d2] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM user WHERE name = ? AND age = ?
==> Parameters: NiuNiu(String), 18(Integer)
<==    Columns: id, name, age, email
<==        Row: 2, NiuNiu, 18, test2@baomidou.com
<==      Total: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@3be4f71]
User(id=2, name=NiuNiu, age=18, email=test2@baomidou.com)

4、根据条件构造器查询一条记录:T selectOne(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);

@Test
public void selectOne() {QueryWrapper<User> wrapper = new QueryWrapper<>();wrapper.eq("name", "Oneby");User user = userMapper.selectOne(wrapper);System.out.println(user);wrapper.clear();wrapper.eq("age", 21);user = userMapper.selectOne(wrapper);System.out.println(user);
}

selectOne() 方法会查询表中所有字段;会根据 wrapper 对象动态拼接 SQL 语句中 WHERE 子句的筛选条件。如果查询得到的结果不止一个,那么则会抛出 TooManyResultsException

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@7a344b65] was not registered for synchronization because synchronization is not active
2021-04-22 21:47:41.497  INFO 13692 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:47:41.628  INFO 13692 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@1689723487 wrapping com.mysql.cj.jdbc.ConnectionImpl@33db72bd] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM user WHERE (name = ?)
==> Parameters: Oneby(String)
<==    Columns: id, name, age, email
<==        Row: 1385228362414358529, Oneby, 21, Oneby@baomidou.com
<==      Total: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@7a344b65]
User(id=1385228362414358529, name=Oneby, age=21, email=Oneby@baomidou.com)
Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@72d0f2b4] was not registered for synchronization because synchronization is not active
JDBC Connection [HikariProxyConnection@1831717330 wrapping com.mysql.cj.jdbc.ConnectionImpl@33db72bd] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM user WHERE (age = ?)
==> Parameters: 21(Integer)
<==    Columns: id, name, age, email
<==        Row: 1, Heygo, 21, test1@baomidou.com
<==        Row: 4, Sandy, 21, test4@baomidou.com
<==        Row: 1385228362414358529, Oneby, 21, Oneby@baomidou.com
<==        Row: 1385228363135778818, Heygo, 21, null
<==      Total: 4
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@72d0f2b4]org.mybatis.spring.MyBatisSystemException: nested exception is org.apache.ibatis.exceptions.TooManyResultsException: Expected one result (or null) to be returned by selectOne(), but found: 4

5、根据条件构造器查询总记录数:Integer selectCount(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);

@Test
public void selectCount() {QueryWrapper<User> wrapper = new QueryWrapper<>();wrapper.eq("age", 21);Integer count = userMapper.selectCount(wrapper);System.out.println(count);
}

selectCount() 方法会查询表中所有字段;会根据 wrapper 对象动态拼接 SQL 语句中 WHERE 子句的筛选条件

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@6b474074] was not registered for synchronization because synchronization is not active
2021-04-22 21:50:12.402  INFO 15376 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:50:12.527  INFO 15376 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@2140322192 wrapping com.mysql.cj.jdbc.ConnectionImpl@31e04b13] will not be managed by Spring
==>  Preparing: SELECT COUNT( * ) FROM user WHERE (age = ?)
==> Parameters: 21(Integer)
<==    Columns: COUNT( * )
<==        Row: 4
<==      Total: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@6b474074]
4

6、根据条件构造器查询全部记录:List<T> selectList(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);

@Test
public void selectList() {QueryWrapper<User> wrapper = new QueryWrapper<>();wrapper.eq("age", 21);List<User> users = userMapper.selectList(wrapper);users.forEach(System.out::println);
}

selectList() 方法会查询表中所有字段;会根据 wrapper 对象动态拼接 SQL 语句中 WHERE 子句的筛选条件

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@108531c2] was not registered for synchronization because synchronization is not active
2021-04-22 21:50:49.681  INFO 1432 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:50:49.816  INFO 1432 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@870019773 wrapping com.mysql.cj.jdbc.ConnectionImpl@7f92b990] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM user WHERE (age = ?)
==> Parameters: 21(Integer)
<==    Columns: id, name, age, email
<==        Row: 1, Heygo, 21, test1@baomidou.com
<==        Row: 4, Sandy, 21, test4@baomidou.com
<==        Row: 1385228362414358529, Oneby, 21, Oneby@baomidou.com
<==        Row: 1385228363135778818, Heygo, 21, null
<==      Total: 4
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@108531c2]
User(id=1, name=Heygo, age=21, email=test1@baomidou.com)
User(id=4, name=Sandy, age=21, email=test4@baomidou.com)
User(id=1385228362414358529, name=Oneby, age=21, email=Oneby@baomidou.com)
User(id=1385228363135778818, name=Heygo, age=21, email=null)

7、根据分页条件查询记录:<E extends IPage<T>> E selectPage(E page, @Param(Constants.WRAPPER) Wrapper<T> queryWrapper);

@Test
public void selectPage() {Page<User> page = new Page<>();page.setCurrent(1);page.setSize(2);QueryWrapper<User> wrapper = new QueryWrapper<>();wrapper.eq("age", 21);Page<User> userPage = userMapper.selectPage(page, wrapper);userPage.getRecords().forEach(System.out::println);
}

selectList() 方法会查询表中所有字段;会根据 wrapper 对象动态拼接 SQL 语句中 WHERE 子句的筛选条件;会根据 page 对象动态拼接 SQL 语句的 LIMIT OFFSET 子句

从日志可以看到 SQL 语句并没有 LIMIT OFFSET 子句,这表明 page 对象设置的参数没有生效,这是因为我们没有开启分页插件的功能,后面会讲

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@7b7b3edb] was not registered for synchronization because synchronization is not active
2021-04-22 21:51:34.960  INFO 13584 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:51:35.069  INFO 13584 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@870019773 wrapping com.mysql.cj.jdbc.ConnectionImpl@7f92b990] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM user WHERE (age = ?)
==> Parameters: 21(Integer)
<==    Columns: id, name, age, email
<==        Row: 1, Heygo, 21, test1@baomidou.com
<==        Row: 4, Sandy, 21, test4@baomidou.com
<==        Row: 1385228362414358529, Oneby, 21, Oneby@baomidou.com
<==        Row: 1385228363135778818, Heygo, 21, null
<==      Total: 4
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@7b7b3edb]
User(id=1, name=Heygo, age=21, email=test1@baomidou.com)
User(id=4, name=Sandy, age=21, email=test4@baomidou.com)
User(id=1385228362414358529, name=Oneby, age=21, email=Oneby@baomidou.com)
User(id=1385228363135778818, name=Heygo, age=21, email=null)

5、删除操作

0、Delete API

// 根据 entity 条件,删除记录
int delete(@Param(Constants.WRAPPER) Wrapper<T> wrapper);
// 删除(根据ID 批量删除)
int deleteBatchIds(@Param(Constants.COLLECTION) Collection<? extends Serializable> idList);
// 根据 ID 删除
int deleteById(Serializable id);
// 根据 columnMap 条件,删除记录
int deleteByMap(@Param(Constants.COLUMN_MAP) Map<String, Object> columnMap);

参数说明

类型 参数名 描述
Wrapper wrapper 实体对象封装操作类(可以为 null)
Collection<? extends Serializable> idList 主键ID列表(不能为 null 以及 empty)
Serializable id 主键ID
Map<String, Object> columnMap 表字段 map 对象

1、根据主键删除:int deleteById(Serializable id);

@Test
public void deleteById() {int result = userMapper.deleteById(1);System.out.println("影响行数:" + result);
}

deleteById() 方法执行时 SQL 语句的删除筛选条件为 WHERE id=?

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@50d3bf39] was not registered for synchronization because synchronization is not active
2021-04-22 21:59:34.538  INFO 9312 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:59:34.668  INFO 9312 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@1289834245 wrapping com.mysql.cj.jdbc.ConnectionImpl@71dfcf21] will not be managed by Spring
==>  Preparing: DELETE FROM user WHERE id=?
==> Parameters: 1(Integer)
<==    Updates: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@50d3bf39]
影响行数:1

2、根据主键列表批量删除:int deleteBatchIds(@Param(Constants.COLLECTION) Collection<? extends Serializable> idList);

@Test
public void deleteBatchIds() {int result = userMapper.deleteBatchIds(Arrays.asList(2, 3));System.out.println("影响行数:" + result);
}

deleteBatchIds() 方法执行时 SQL 语句的删除筛选条件为 WHERE id IN ( ? , ? )

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@771db12c] was not registered for synchronization because synchronization is not active
2021-04-22 21:59:48.184  INFO 15280 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:59:48.314  INFO 15280 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@253380088 wrapping com.mysql.cj.jdbc.ConnectionImpl@5edf2821] will not be managed by Spring
==>  Preparing: DELETE FROM user WHERE id IN ( ? , ? )
==> Parameters: 2(Integer), 3(Integer)
<==    Updates: 2
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@771db12c]
影响行数:2

3、根据 columnMap 条件批量删除:int deleteByMap(@Param(Constants.COLUMN_MAP) Map<String, Object> columnMap);

@Test
public void deleteByMap() {Map<String, Object> params = new HashMap<>();params.put("name", "Billie");params.put("age", 24);int result = userMapper.deleteByMap(params);System.out.println("影响行数:" + result);
}

deleteByMap 方法在执行时会根据 map 对象动态拼接 SQL 语句中 WHERE 子句的筛选条件

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@1eb6e1c] was not registered for synchronization because synchronization is not active
2021-04-22 22:00:00.418  INFO 15056 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 22:00:00.548  INFO 15056 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@1066656936 wrapping com.mysql.cj.jdbc.ConnectionImpl@12b5454f] will not be managed by Spring
==>  Preparing: DELETE FROM user WHERE name = ? AND age = ?
==> Parameters: Billie(String), 24(Integer)
<==    Updates: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@1eb6e1c]
影响行数:1

4、根据条件构造器批量删除:int delete(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);

@Test
public void delete() {QueryWrapper<User> wrapper = new QueryWrapper<>();wrapper.eq("age", 21);int result = userMapper.delete(wrapper);System.out.println("影响行数:" + result);
}

delete 方法在执行时会根据 wrapper 对象动态拼接 SQL 语句中 WHERE 子句的筛选条件

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@3104351d] was not registered for synchronization because synchronization is not active
2021-04-22 22:00:13.593  INFO 8676 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 22:00:13.723  INFO 8676 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@1077464378 wrapping com.mysql.cj.jdbc.ConnectionImpl@14ac77b9] will not be managed by Spring
==>  Preparing: DELETE FROM user WHERE (age = ?)
==> Parameters: 21(Integer)
<==    Updates: 3
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@3104351d]
影响行数:3

6、全列操作

mapper 层选装件

选装件位于 com.baomidou.mybatisplus.extension.injector.methods 包下 需要配合Sql 注入器使用,案例使用详细见源码注释

最常用的应该就是这个选装件了:AlwaysUpdateSomeColumnById,之前讲得 API 都会先判断字段是否为空,为空则不会进行更新,但是 AlwaysUpdateSomeColumnById 会根据 ID 更新固定的那几个字段(但是不包含逻辑删除)

7、常用注解

@TableName

我们将数据库的表名从 user 改为 t_user,再次执行 selectById() 方法,发现程序抛出异常:BadSqlGrammarException

异常的具体信息为:Cause: java.sql.SQLSyntaxErrorException: Table 'mybatis_plus.user' doesn't exist,说是找不到 mybatis_plus.user 这张表

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@652ab8d9] was not registered for synchronization because synchronization is not active
2021-04-20 08:22:38.576  INFO 3304 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-20 08:22:38.700  INFO 3304 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@665317128 wrapping com.mysql.cj.jdbc.ConnectionImpl@280e8a1a] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM user WHERE id=?
==> Parameters: 1(Integer)
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@652ab8d9]org.springframework.jdbc.BadSqlGrammarException:
### Error querying database.  Cause: java.sql.SQLSyntaxErrorException: Table 'mybatis_plus.user' doesn't exist
### The error may exist in com/oneby/mapper/UserMapper.java (best guess)
### The error may involve defaultParameterMap
### The error occurred while setting parameters
### SQL: SELECT id,name,age,email FROM user WHERE id=?
### Cause: java.sql.SQLSyntaxErrorException: Table 'mybatis_plus.user' doesn't exist
; bad SQL grammar []; nested exception is java.sql.SQLSyntaxErrorException: Table 'mybatis_plus.user' doesn't exist

MybatisPlus 会默认使用实体类的类名到数据库中找对应的表,但实体类的类名与数据库表明不一致时,需要使用 @TableName 注解标注实体类对应的数据库表名

/*** @Author Oneby* @Date 2021/4/18 17:53*/
@Data
@AllArgsConstructor
@NoArgsConstructor
@TableName("t_user")
public class User {private Long id;private String name;private Integer age;private String email;}

我们再次执行查询,发送的 SQL 语句中表名变成了 t_user

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@50d3bf39] was not registered for synchronization because synchronization is not active
2021-04-20 08:25:25.826  INFO 2428 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-20 08:25:25.951  INFO 2428 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@1688526221 wrapping com.mysql.cj.jdbc.ConnectionImpl@2dddc1b9] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM t_user WHERE id=?
==> Parameters: 1(Integer)
<==    Columns: id, name, age, email
<==        Row: 1, Jone, 18, test1@baomidou.com
<==      Total: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@50d3bf39]
User(id=1, name=Jone, age=18, email=test1@baomidou.com)

@TableName 注解

/*** 数据库表相关** @author hubin, hanchunlin* @since 2016-01-23*/
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE, ElementType.ANNOTATION_TYPE})
public @interface TableName {/*** 实体对应的表名*/String value() default "";/*** schema* <p>* 配置此值将覆盖全局配置的 schema** @since 3.1.1*/String schema() default "";/*** 是否保持使用全局的 tablePrefix 的值* <p> 只生效于 既设置了全局的 tablePrefix 也设置了上面 {@link #value()} 的值 </p>* <li> 如果是 false , 全局的 tablePrefix 不生效 </li>** @since 3.1.1*/boolean keepGlobalPrefix() default false;/*** 实体映射结果集,* 只生效与 mp 自动注入的 method*/String resultMap() default "";/*** 是否自动构建 resultMap 并使用,* 只生效与 mp 自动注入的 method,* 如果设置 resultMap 则不会进行 resultMap 的自动构建并注入,* 只适合个别字段 设置了 typeHandler 或 jdbcType 的情况** @since 3.1.2*/boolean autoResultMap() default false;/*** 需要排除的属性名** @since 3.3.1*/String[] excludeProperty() default {};
}

@TableField

我们将 t_user 表的 user 列改为 username,再次执行 selectById() 方法,发现程序抛出异常:BadSqlGrammarException

异常的具体信息为:Cause: java.sql.SQLSyntaxErrorException: Unknown column 'name' in 'field list',说是找不到 name 这个列

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@5f13be1] was not registered for synchronization because synchronization is not active
2021-04-20 08:26:10.119  INFO 8344 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-20 08:26:10.244  INFO 8344 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@1609754699 wrapping com.mysql.cj.jdbc.ConnectionImpl@74abbb] will not be managed by Spring
==>  Preparing: SELECT id,name,age,email FROM t_user WHERE id=?
==> Parameters: 1(Integer)
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@5f13be1]org.springframework.jdbc.BadSqlGrammarException:
### Error querying database.  Cause: java.sql.SQLSyntaxErrorException: Unknown column 'name' in 'field list'
### The error may exist in com/oneby/mapper/UserMapper.java (best guess)
### The error may involve defaultParameterMap
### The error occurred while setting parameters
### SQL: SELECT id,name,age,email FROM t_user WHERE id=?
### Cause: java.sql.SQLSyntaxErrorException: Unknown column 'name' in 'field list'
; bad SQL grammar []; nested exception is java.sql.SQLSyntaxErrorException: Unknown column 'name' in 'field list'

MybatisPlus 会默认使用实体类的字段名到数据库表中找对应的列(默认开启驼峰命名规则),但实体类的类名与数据库表明不一致时,需要使用 @TableField 注解标注实体类对应的数据库表名

/*** @Author Oneby* @Date 2021/4/18 17:53*/
@Data
@AllArgsConstructor
@NoArgsConstructor
@TableName("t_user")
public class User {private Long id;@TableField("username")private String name;private Integer age;private String email;}

我们再次执行查询,发送的 SQL 语句中列名变成了 username

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@17814b1c] was not registered for synchronization because synchronization is not active
2021-04-22 22:16:13.980  INFO 19028 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 22:16:14.110  INFO 19028 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@1487287849 wrapping com.mysql.cj.jdbc.ConnectionImpl@7de843ef] will not be managed by Spring
==>  Preparing: SELECT id,username AS name,age,email FROM t_user WHERE id=?
==> Parameters: 1(Integer)
<==    Columns: id, name, age, email
<==        Row: 1, Jone, 18, test1@baomidou.com
<==      Total: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@17814b1c]
User(id=1, name=Jone, age=18, email=test1@baomidou.com)

@TableField 注解:如果实体类中的某些字段不是数据库字段,则设置 exist = false

/*** 表字段标识** @author hubin sjy tantan* @since 2016-09-09*/
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.FIELD, ElementType.ANNOTATION_TYPE})
public @interface TableField {/*** 数据库字段值* <p>* 不需要配置该值的情况:* <li> 当 {@link com.baomidou.mybatisplus.core.MybatisConfiguration#mapUnderscoreToCamelCase} 为 true 时,* (mp下默认是true,mybatis默认是false), 数据库字段值.replace("_","").toUpperCase() == 实体属性名.toUpperCase() </li>* <li> 当 {@link com.baomidou.mybatisplus.core.MybatisConfiguration#mapUnderscoreToCamelCase} 为 false 时,* 数据库字段值.toUpperCase() == 实体属性名.toUpperCase() </li>*/String value() default "";/*** 是否为数据库表字段* <p>* 默认 true 存在,false 不存在*/boolean exist() default true;/*** 字段 where 实体查询比较条件* <p>* 默认 {@link SqlCondition.EQUAL}*/String condition() default "";/*** 字段 update set 部分注入, 该注解优于 el 注解使用* <p>* 例1:@TableField(.. , update="%s+1") 其中 %s 会填充为字段* 输出 SQL 为:update 表 set 字段=字段+1 where ...* <p>* 例2:@TableField(.. , update="now()") 使用数据库时间* 输出 SQL 为:update 表 set 字段=now() where ...*/String update() default "";/*** 字段验证策略之 insert: 当insert操作时,该字段拼接insert语句时的策略* <p>* IGNORED: 直接拼接 insert into table_a(column) values (#{columnProperty});* NOT_NULL: insert into table_a(<if test="columnProperty != null">column</if>) values (<if test="columnProperty != null">#{columnProperty}</if>)* NOT_EMPTY: insert into table_a(<if test="columnProperty != null and columnProperty!=''">column</if>) values (<if test="columnProperty != null and columnProperty!=''">#{columnProperty}</if>)* NOT_EMPTY 如果针对的是非 CharSequence 类型的字段则效果等于 NOT_NULL** @since 3.1.2*/FieldStrategy insertStrategy() default FieldStrategy.DEFAULT;/*** 字段验证策略之 update: 当更新操作时,该字段拼接set语句时的策略* <p>* IGNORED: 直接拼接 update table_a set column=#{columnProperty}, 属性为null/空string都会被set进去* NOT_NULL: update table_a set <if test="columnProperty != null">column=#{columnProperty}</if>* NOT_EMPTY: update table_a set <if test="columnProperty != null and columnProperty!=''">column=#{columnProperty}</if>* NOT_EMPTY 如果针对的是非 CharSequence 类型的字段则效果等于 NOT_NULL** @since 3.1.2*/FieldStrategy updateStrategy() default FieldStrategy.DEFAULT;/*** 字段验证策略之 where: 表示该字段在拼接where条件时的策略* <p>* IGNORED: 直接拼接 column=#{columnProperty}* NOT_NULL: <if test="columnProperty != null">column=#{columnProperty}</if>* NOT_EMPTY: <if test="columnProperty != null and columnProperty!=''">column=#{columnProperty}</if>* NOT_EMPTY 如果针对的是非 CharSequence 类型的字段则效果等于 NOT_NULL** @since 3.1.2*/FieldStrategy whereStrategy() default FieldStrategy.DEFAULT;/*** 字段自动填充策略* <p>* 在对应模式下将会忽略 insertStrategy 或 updateStrategy 的配置,等于断言该字段必有值*/FieldFill fill() default FieldFill.DEFAULT;/*** 是否进行 select 查询* <p>* 大字段可设置为 false 不加入 select 查询范围*/boolean select() default true;/*** 是否保持使用全局的 columnFormat 的值* <p>* 只生效于 既设置了全局的 columnFormat 也设置了上面 {@link #value()} 的值* 如果是 false , 全局的 columnFormat 不生效** @since 3.1.1*/boolean keepGlobalFormat() default false;/*** JDBC类型 (该默认值不代表会按照该值生效),* 只生效与 mp 自动注入的 method,* 建议配合 {@link TableName#autoResultMap()} 一起使用* <p>* {@link ResultMapping#jdbcType} and {@link ParameterMapping#jdbcType}** @since 3.1.2*/JdbcType jdbcType() default JdbcType.UNDEFINED;/*** 类型处理器 (该默认值不代表会按照该值生效),* 只生效与 mp 自动注入的 method,* 建议配合 {@link TableName#autoResultMap()} 一起使用* <p>* {@link ResultMapping#typeHandler} and {@link ParameterMapping#typeHandler}** @since 3.1.2*/Class<? extends TypeHandler> typeHandler() default UnknownTypeHandler.class;/*** 只在使用了 {@link #typeHandler()} 时判断是否辅助追加 javaType* <p>* 一般情况下不推荐使用* {@link ParameterMapping#javaType}** @since 3.4.0 @2020-07-23*/boolean javaType() default false;/*** 指定小数点后保留的位数,* 只生效于 mp 自动注入的 method,* 建议配合 {@link TableName#autoResultMap()} 一起使用* <p>* {@link ParameterMapping#numericScale}** @since 3.1.2*/String numericScale() default "";
}

@TableId

我们之前执行 insert() 方法时,发现自动回填的主键值并不是自动递增

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@51e0301d] was not registered for synchronization because synchronization is not active
2021-04-22 21:45:52.571  INFO 8228 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 21:45:52.696  INFO 8228 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@2097614581 wrapping com.mysql.cj.jdbc.ConnectionImpl@7a55f148] will not be managed by Spring
==>  Preparing: INSERT INTO user ( id, name, age, email ) VALUES ( ?, ?, ?, ? )
==> Parameters: 1385228362414358529(Long), Oneby(String), 21(Integer), Oneby@baomidou.com(String)
<==    Updates: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@51e0301d]
影响行数:1
User(id=1385228362414358529, name=Oneby, age=21, email=Oneby@baomidou.com)

当我们没有设置主键类型时,MybatisPlus 会帮我们注册自动填充插件进行填充。如果想要设置主键自增,需要使用 @TableId(type = IdType.AUTO) 注解标识主键字段

/*** @Author Oneby* @Date 2021/4/18 17:53*/
@Data
@AllArgsConstructor
@NoArgsConstructor
@TableName("t_user")
public class User {@TableId(type = IdType.AUTO)private Long id;@TableField("name")private String name;private Integer age;private String email;}

我们再次执行插入 insert() 方法插入数据时,发现一件神奇的事情:发行的 SQL 语句中居然没有了 id 字段,但是程序却抛出异常:DataIntegrityViolationException

异常的体信息为:Cause: java.sql.SQLException: Field 'id' doesn't have a default value,意思是 t_user 表中的 id 字段并没有一个默认值

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@58399d82] was not registered for synchronization because synchronization is not active
2021-04-22 22:26:43.141  INFO 2324 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 22:26:43.258  INFO 2324 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@1779219567 wrapping com.mysql.cj.jdbc.ConnectionImpl@67110f71] will not be managed by Spring
==>  Preparing: INSERT INTO t_user ( username, age, email ) VALUES ( ?, ?, ? )
==> Parameters: Oneby(String), 21(Integer), Oneby@baomidou.com(String)
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@58399d82]org.springframework.dao.DataIntegrityViolationException:
### Error updating database.  Cause: java.sql.SQLException: Field 'id' doesn't have a default value
### The error may exist in com/oneby/mapper/UserMapper.java (best guess)
### The error may involve com.oneby.mapper.UserMapper.insert-Inline
### The error occurred while setting parameters
### SQL: INSERT INTO t_user  ( username, age, email )  VALUES  ( ?, ?, ? )
### Cause: java.sql.SQLException: Field 'id' doesn't have a default value
; Field 'id' doesn't have a default value; nested exception is java.sql.SQLException: Field 'id' doesn't have a default value

这是因为我们没有在 MySQL数据库中将 id 字段设置为自增,我们将 id 字段设置为自增之后,再次执行 insert() 方法:SQL 语句中并没有携带 id 字段及其字段值,插入数据成功并且自动回填了自增主键的值

Creating a new SqlSession
SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@3c017078] was not registered for synchronization because synchronization is not active
2021-04-22 22:29:24.961  INFO 17588 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Starting...
2021-04-22 22:29:25.089  INFO 17588 --- [           main] com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Start completed.
JDBC Connection [HikariProxyConnection@313869647 wrapping com.mysql.cj.jdbc.ConnectionImpl@5445f5ba] will not be managed by Spring
==>  Preparing: INSERT INTO t_user ( username, age, email ) VALUES ( ?, ?, ? )
==> Parameters: Oneby(String), 21(Integer), Oneby@baomidou.com(String)
<==    Updates: 1
Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@3c017078]
影响行数:1
User(id=6, name=Oneby, age=21, email=Oneby@baomidou.com)

@TableId 注解

/*** 表主键标识** @author hubin* @since 2016-01-23*/
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.FIELD, ElementType.ANNOTATION_TYPE})
public @interface TableId {/*** 字段名(该值可无)*/String value() default "";/*** 主键类型* {@link IdType}*/IdType type() default IdType.NONE;
}

IdType 主键类型

@Getter
public enum IdType {/*** 数据库ID自增* <p>该类型请确保数据库设置了 ID自增 否则无效</p>*/AUTO(0),/*** 该类型为未设置主键类型(注解里等于跟随全局,全局里约等于 INPUT)*/NONE(1),/*** 用户输入ID* <p>该类型可以通过自己注册自动填充插件进行填充</p>*/INPUT(2),/* 以下3种类型、只有当插入对象ID 为空,才自动填充。 *//*** 分配ID (主键类型为number或string),* 默认实现类 {@link com.baomidou.mybatisplus.core.incrementer.DefaultIdentifierGenerator}(雪花算法)** @since 3.3.0*/ASSIGN_ID(3),/*** 分配UUID (主键类型为 string)* 默认实现类 {@link com.baomidou.mybatisplus.core.incrementer.DefaultIdentifierGenerator}(UUID.replace("-",""))*/ASSIGN_UUID(4),/*** @deprecated 3.3.0 please use {@link #ASSIGN_ID}*/@DeprecatedID_WORKER(3),/*** @deprecated 3.3.0 please use {@link #ASSIGN_ID}*/@DeprecatedID_WORKER_STR(3),/*** @deprecated 3.3.0 please use {@link #ASSIGN_UUID}*/@DeprecatedUUID(4);private final int key;IdType(int key) {this.key = key;}
}

第 2 章 MybatisPlus 通用 CRUD相关推荐

  1. MybatisPlus 通用CRUD操作

    1.插入操作 1.1.方法定义 /** * 插⼊⼀条记录 * * @param entity 实体对象. */ int insert(T entity); 1.2.测试用例 /*测试添加*/@Test ...

  2. Mybatis-Plus入门之通用CRUD+基本配置介绍

    1.了解Mybatis-Plus 1.1.Mybatis-Plus介绍 MyBatis-Plus(简称 MP)是一个 MyBatis 的增强工具,在 MyBatis 的基础上只做增强不做改变,为简化开 ...

  3. MybatisPlus中使用通用CRUD实现插入操作

    场景 项目搭建专栏: https://blog.csdn.net/BADAO_LIUMANG_QIZHI/column/info/37194 在MyBatisPlus介绍入门以及项目集成MyBatis ...

  4. 第 3 章 MybatisPlus 注入 SQL 原理分析

    第 3 章 MybatisPlus 注入 SQL 原理分析 思考问题 我们编写的 UserMapper 继承了 BaseMapper<T>,就拥有了基本的增删改查功能,这是因为 BaseM ...

  5. 第 1 章 MybatisPlus 快速入门

    第 1 章 MybatisPlus 快速入门 1.MybatisPlus 概述 MybatisPlus:一款 Mybatis 的增强工具包 MybatisPlus 官网:https://mybatis ...

  6. 第 8 章 MybatisPlus 扩展

    第 8 章 MybatisPlus 扩展 1.前置说明 关于 MybatisPlus 扩展的说明 emmm,这里我就不肝原理,只写应用吧...字数太多了,Typora 都被我肝卡了,实在是肝不动了.. ...

  7. 第 5 章 MybatisPlus ActiveRecord

    第 5 章 MybatisPlus ActiveRecord 1.ActiveRecord 简介 ActiveRecord(活动记录) Active Record(活动记录 ),是一种领域模型模式,特 ...

  8. 第 4 章 MybatisPlus 条件构造器

    第 4 章 MybatisPlus 条件构造器 1.CRUD API 的思考 对于 BaseMapper 中基本 CRUD 方法的思考 继承了 BaseMapper 接口后,我们只能获得基本的 CRU ...

  9. 浅谈:MyBatis-Plus的CRUD与乐观锁,分页插件,逻辑删除

    浅谈:MyBatis-Plus的CRUD与乐观锁,分页插件,逻辑删除 MyBatis-Plus官方文档连接 什么是MyBatis-Plus 请点击上面官方文档查看 代码演示:代码注释为功能详细解释 数 ...

最新文章

  1. 电子计算机简称什么也称什么,点点点电子美容仪
  2. 2.5亿!华为成立新公司!
  3. xUtils3 注解模块
  4. 改革开放40年·软件产业
  5. 【案例分享】信息化建设改变行业运营形态
  6. 【每天一个 Linux 命令】tree命令
  7. java上传图片压缩大小
  8. pdf合并页面大小不一样
  9. YB5212A充电IC充电芯片sop8
  10. 1ke android逆向助手_android逆向助手
  11. 虚拟机内存管理之内存分配器
  12. 微信删除的聊天记录怎么恢复,教你两个方法
  13. Linux多窗口终端使用、shell快捷键以及修改快捷键
  14. Android系统 小米/三星/索尼 应用启动图标未读消息数(BadgeNumber)动态提醒
  15. java计算机毕业设计基于安卓Android的二手交易app-闲置物品交易app-ssm
  16. 路由器和交换机有什么区别
  17. linux视频日记软件下载,Linux(Ubunt)使用日记------常用软件汇总(不定时更新)
  18. 【时序】DeepGLO:可以学习全局依赖和局部信息的多时间序列预测模型
  19. Excel单元格设置成下拉选
  20. metaBase的字段筛选条件报错问题总结(多字段下拉选择/metaBase中in语句的用法)

热门文章

  1. 2021-2025年中国独立式梳妆浴缸行业市场供需与战略研究报告
  2. IIS未在本地计算机上注册“Microsoft.Jet.OLEDB.4.0”提供程序
  3. 大道至简:微众银行区块链全栈技术体系纵览
  4. 揭晓 2020 年增长最快的技术职位,PHP 成为潜力股!
  5. 72000 Star 下载工具被 GitHub 下架,背后的数字千年版权法案是什么?
  6. 链表反转的两种实现方法,后一种击败了100%的用户
  7. HTML 为啥称“超文本标记语言”?
  8. 新生代的他们,正在续写“黑客”传奇
  9. 京东回应“两年将回购20亿美元股份”;微软即刻关闭全球所有旗下商店;. Net 5首个预览版发布|极客头条...
  10. 虾米音乐的监控体系升级之路