依赖
<properties>
<mybatis.plus.version>3.4.0</mybatis.plus.version>
</properties>
<dependencies>
<!--mybatis-plus下面这两个依赖必须加-->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>${mybatis.plus.version}</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
<!--mybatis-plus以下依赖是拓展,比如分页插件-->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-extension</artifactId>
<version>${mybatis.plus.version}</version>
</dependency>
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-annotation</artifactId>
<version>${mybatis.plus.version}</version>
</dependency>
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-core</artifactId>
<version>${mybatis.plus.version}</version>
</dependency>
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-generator</artifactId>
<version>${mybatis.plus.version}</version>
</dependency>
<!--单元测试依赖-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
SpringBoot的数据表配置:
spring.datasource.driver-class-name=com.mysql.jdbc.Driver
#注意mysql的版本,如果是8.0及以上,要使用以下驱动,并修改pom文件的Mysql版本。
#spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.url=jdbc:mysql://mysql的ip:端口/库名?useUnicode=true&characterEncoding=utf-8&allowMultiQueries=true&serverTimezone=Asia/Shanghai&useTimezone=true
spring.datasource.username=xxx
spring.datasource.password=xxx
mybatisPlus 打印sql日志:
# mybatis-plus配置控制台打印完整带参数SQL语句
mybatis-plus.configuration.log-impl=org.apache.ibatis.logging.stdout.StdOutImpl
创建数据表:
CREATE TABLE tb_order_test
(
id INT NOT NULL AUTO_INCREMENT COMMENT '主键,自增id',
order_id VARCHAR(25) NOT NULL UNIQUE COMMENT '订单号,唯一',
pay_status INT UNSIGNED DEFAULT 0 COMMENT '10:未支付,20:支付成功,30:支付失败, 40:已下单,50:申请退款,60:退款成功,70:退款失败 ',
user_id BIGINT(20) NOT NULL COMMENT '用户id',
total_price DECIMAL(25, 2) DEFAULT 0.00 COMMENT '交易金额',
result TEXT COMMENT '结果',
order_desc VARCHAR(128) DEFAULT '' COMMENT '订单描述',
order_date DATE DEFAULT NULL COMMENT '订单日期',
create_time DATETIME DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间,默认当前时间',
update_time DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间,更新时默认当前时间',
is_delete TINYINT(1) DEFAULT 0 COMMENT '是否删除,0表示否,1表示是',
PRIMARY KEY (id),
INDEX idx_order (order_id)
) ENGINE = INNODB
DEFAULT CHARSET = utf8
AUTO_INCREMENT = 1 COMMENT ='示例表';
实体类
-
注解 @TableName(),指定数据表名称。
-
注解 @TableId指定主键。
@TableId(type = IdType.AUTO) : 表示自增id。
@TableId(type = IdType.ID_WORKER) :ID_WORKER生成19位数字,对应类型Long
@TableId(type = IdType.ID_WORKER_STR) :ID_WORKER_STR 生成19位值字符串
@TableId(type = IdType.INPUT) INPUT:设置id
@TableId(type = IdType.UUID) UUID:随机唯一值
@TableId(type = IdType.NONE) NONE:自动输入 -
fill属性可以表示插入或更新。
@TableField(fill = FieldFill.INSERT):插入填充字段。
@TableField(fill = FieldFill.UPDATE): 更新填充字段。
@TableField(fill = FieldFill.INSERT_UPDATE):插入和更新填充字段。
@TableName("tb_order_test")
public class Order {
//此处忽略 getter、setter、构造方法,自行添加
@TableId(type = IdType.AUTO)
private Integer id;
private String orderId;
private Integer payStatus;
private Long userId;
private BigDecimal totalPrice;
private String orderDesc;
private Date orderDate;
@TableField(fill = FieldFill.INSERT)
private Date createTime;
@TableField(fill = FieldFill.INSERT_UPDATE)
private Date updateTime;
private Boolean isDelete;
private String result;
}
扫描Mapper文件夹:
在spring boot启动类中添加@MapperScan注解,扫描Mapper接口的文件夹。
@SpringBootApplication(scanBasePackages = {"com.example.demo"})
@MapperScan(basePackages = { "com.example.demo.dao" })
public class demoApplication {
public static void main(String[] args) {
SpringApplication.run(DemoApplication.class, args);
}
}
Mapper接口:
- Mapper接口,继承 BaseMapper
- mybatisPlus,不需要配置xml文件。
public interface OrderMapper extends BaseMapper<Order> {
}
增删改查(不是很好用,更优的做法见后面的Service层)
- 普通的增删改查:
原生的不是很好用,代码如下。更好的增删改查,详情见后面的Service层讲解。
@RunWith(SpringJUnit4ClassRunner.class)
@SpringBootTest(classes = DemoApplication.class)
public class MybatisPlusTest {
@Autowired
private OrderMapper orderMapper;
@Test
public void selectAll() {
List<Order> orderList = orderMapper.selectList(null);
System.out.println(orderList);
}
@Test
public void selectById() {
Order order = orderMapper.selectById(123456);
System.out.println(order);
}
@Test
public void insert() {
Order order = new Order();
order.setOrderId("sdfdfegegergb");
order.setTotalPrice(new BigDecimal("99.3"));
order.setUserId(789012L);
orderMapper.insert(order);
System.out.println(order);
}
@Test
public void updateById() {
Order order = new Order();
order.setId(1);
order.setOrderDesc("update");
orderMapper.updateById(order);
}
@Test
public void delete() {
orderMapper.deleteById(1L);
}
}
条件查询
QueryWrapper条件查询:
eq:等于
ne:不等于
gt:大于
ge:大于等于
lt:小于
le:小于等于
between and:区间查询
like:模糊查询
notLike:模糊查询
likeLeft:左模糊
likeRight: 右模糊
in:范围查询
orderByDesc:降序
orderByAsc: 升序
代码示例如下 :
/**
* SELECT id,order_id,pay_status,user_id,total_price,order_desc,order_date,create_time,update_time,is_delete,result
* FROM
* tb_order_test
* WHERE
* user_id = 789012
* ORDER BY
* create_time DESC
*
*/
public void selectByWrapper() {
QueryWrapper<Order> queryWrapper = new QueryWrapper<>();
LambdaQueryWrapper<Order> wrapper = queryWrapper.lambda();
//等于
wrapper.eq(Order::getUserId, 789012L);
wrapper.orderByDesc(Order::getCreateTime);
List<Order> orderList = orderMapper.selectList(queryWrapper);
System.out.println(orderList);
}
/**
* 以下代码,相当于sql:
* SELECT id,order_id,pay_status,user_id,total_price,order_desc,order_date,create_time,update_time,is_delete,result
* FROM
* tb_order_test
* WHERE
* user_id >= 10000
* AND pay_status IN (1, 2, 3)
* AND total_price BETWEEN 1.0 AND 1000.0
* ORDER BY
* create_time ASC
*/
public void selectWrapper() {
QueryWrapper<Order> queryWrapper = new QueryWrapper<>();
LambdaQueryWrapper<Order> wrapper = queryWrapper.lambda();
//大于等于
wrapper.ge(Order::getUserId, 10000);
wrapper.in(Order::getPayStatus, 1, 2, 3);
wrapper.between(Order::getTotalPrice, 1.0, 1000.0);
wrapper.orderByAsc(Order::getCreateTime);
List<Order> orderList = orderMapper.selectList(queryWrapper);
System.out.println(orderList);
}
- 动态查询:
在查询条件,比如 wrapper.ge(Order::getUserId, 10000); 前面可以加一些判断条件,满足条件时,才会进行查询。
比如 wrapper.ge(paramNum==123, Order::getUserId, 10000); 表示当传入的动态参数 paramNum为 123时,才拼接此查询条件。
public void selectConditionTest() {
int paramNum = 100;
LambdaQueryWrapper<Order> wrapper = new LambdaQueryWrapper<>();
//动态sql,第一个参数是条件,条件成立才会执行
wrapper.ge(paramNum==123, Order::getUserId, 10000);
List<Order> orderList = orderMapper.selectList(wrapper);
System.out.println(orderList);
}
- 只查一条数据:
调用MybatisPlus的getOne和selectOne方法。如果存在多条结果,会报错如下:
org.mybatis.spring.MyBatisSystemException: nested exception is org.apache.ibatis.exceptions.TooManyResultsException:
Expected one result (or null) to be returned by selectOne(), but found:
解决方法:
在查询语句后面,加上 .last(“LIMIT 1”)
如下:
public void selectOne() {
LambdaQueryWrapper<Order> lambdaQueryWrapper =new LambdaQueryWrapper<>();
lambdaQueryWrapper.in(Order::getPayStatus, 1, 2, 3);
//加上 LIMIT 1
lambdaQueryWrapper.last("LIMIT 1");
Order orderList = orderService.getOne(lambdaQueryWrapper);
System.out.println("orderList:"+orderList);
}
分页常用的方法:
Page.java :
/**
* 分页构造函数
*
* @param current 当前页
* @param size 每页显示条数
*/
public Page(long current, long size) {
this(current, size, 0);
}
/**
* 查询数据列表
*/
@Override
public List<T> getRecords() {
return this.records;
}
/**
* 数据的总数
*/
@Override
public long getTotal() {
return this.total;
}
/**
* 每页显示条数,默认 10
*/
@Override
public long getSize() {
return this.size;
}
/**
* 当前页
*/
@Override
public long getCurrent() {
return this.current;
}
/**
* 当前分页总页数
*/
default long getPages() {
if (getSize() == 0) {
return 0L;
}
long pages = getTotal() / getSize();
if (getTotal() % getSize() != 0) {
pages++;
}
return pages;
}
BaseMapper 查询分页结果:selectPage 第一个参数是分页page,第二个参数是查询条件
<E extends IPage<T>> E selectPage(E page, @Param("ew") Wrapper<T> queryWrapper);
分页的示例
@Test
public void page() {
//Page第一个参数current表示第几页,从1开始。size表示每页多少条。
Page<Order> pageQuery = new Page<>(1,10);
//selectPage 第一个参数是分页page,第二个参数是查询条件
Page<Order> page = orderMapper.selectPage(pageQuery, null);
//分页返回的数据
List<Order> records = page.getRecords();
//数据的总数
long total = page.getTotal();
//每页数量
long size = page.getSize();
//当前页
long current = page.getCurrent();
//总页数
long pages = page.getPages();
System.out.println("分页返回的数据:"+records);
System.out.println("数据的总数:"+ total);
System.out.println("每页数量:"+size);
System.out.println("当前页:"+ current);
System.out.println("总页数:"+ pages);
}
Service层,更常用的增删改查
pom.xml文件中,添加了 mybatis-plus-extension 依赖后。
可以继承 ServiceImpl,直接使用ServiceImpl和 IService 已有的方法。
条件查询:list()
分页:page()
查询一条数据:getOne()。原生的selectOne()如果查到多条数据会报错,可以用getOne()代替,查到多条不报错。
根据id查询:getById()
插入:save()
更新:update(T entity, Wrapper updateWrapper)。第一个参数是要更新的字段,第二个参数是查询条件。
插入或更新:saveOrUpdate()等方法。
批量保存:saveBatch()
根据id批量更新:updateBatchById()
@Service
public class OrderServiceImpl
extends ServiceImpl<OrderMapper, Order>
implements OrderService {
@Override
public List<Order> getList() {
LambdaQueryWrapper<Order> queryWrapper = new LambdaQueryWrapper<>();
queryWrapper.eq(Order::getOrderId, "12345");
//直接复用 IService 已有的方法list()
List<Order> list = list(queryWrapper);
return list;
}
@Override
public Page<Order> getPageList() {
Page<Order> pageQuery = new Page<>(1,10);
//直接复用 IService 已有的方法page()
Page<Order> page = page(pageQuery, null);
return page;
}
/**
* boolean update(T entity, Wrapper<T> updateWrapper) 返回的是boolean 类型。
* 如果需要返回 int 类型,可以继承ServiceImpl<Mapper接口, 数据表对应的Entity类>,然后用 baseMapper.update(T entity, Wrapper<T> updateWrapper)
*
*/
public boolean updateByQuery() {
//要修改的字段
Order updateOrder = new Order();
updateOrder.setOrderDesc("upadteDesc123");
//查询条件
LambdaUpdateWrapper<Order> wrapper = new LambdaUpdateWrapper<>();
wrapper.eq(Order::getUserId, "12345");
return update(updateOrder, wrapper);
}
}
分页查询,并将数据表的entity 对象转换成 展示层的vo数据 :
mybatisPlus分页查询后,并把查询得到的数据表的entity 对象转换成 展示层的vo 数据,如下
public Page<MyVo> list(Integer pageNo, Integer pageSize) {
if (pageNo == null) {
pageNo = 1;
}
if (pageSize == null) {
pageSize = 10;
}
Page<MyEntity> pageQuery = new Page<>(pageNo,pageSize);
LambdaQueryWrapper<MyEntity> queryWrapper = new LambdaQueryWrapper<>();
//补充查询条件,此处忽略
IPage<MyEntity> page = page(pageQuery, queryWrapper);
List<MyEntity> records = page.getRecords();
//遍历list,将entity转换为 vo, changeEntityToVo是转换的方法
List<MyVo> voList = Optional.ofNullable(records).orElse(new ArrayList<>())
.stream().map(this::changeEntityToVo).collect(Collectors.toList());
return new Page<MyVo>(page.getCurrent(), page.getSize(), page.getTotal())
.setRecords(voList);
}
public MyVo changeEntityToVo(MyEntity myEntity) {
MyVo myVo = new MyVo();
BeanUtils.copyProperties(myEntity, myVo);
//其他的set,此处忽略
return myVo;
}
MybatisPlus 报错:
- 报错如下:
org.mybatis.spring.MyBatisSystemException: nested exception is org.apache.ibatis.reflection.ReflectionException:
Could not set property 'id' of '' with value ''
Cause: java.lang.IllegalArgumentException: argument type mismatch
解决方法:
字段上面加上注解 @TableId(type = IdType.AUTO)文章来源:https://www.toymoban.com/news/detail-735704.html
参考资料:
https://blog.csdn.net/m0_46313726/article/details/124187527文章来源地址https://www.toymoban.com/news/detail-735704.html
到了这里,关于SpringBoot集成MybatisPlus的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!