官方网站:点击进入
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus</artifactId>
<version>undefined</version>
</dependency>
1:测试环境
1.1:数据库创建
创建db_mybatis_plus数据库。再创建user表,user表如下
插入如下数据:
1.2:springboot项目创建
依赖引入
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.3.1</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.2.3</version>
</dependency>
</dependencies>
yml配置文件
spring:
datasource:
username: root
password: yfy57609
url: jdbc:mysql://1.15.57.103:3306/db_mybatis_plus?serverTimezone=GMT%2B8
driver-class-name: com.mysql.cj.jdbc.Driver
#mybatis_plus日志配置
mybatis-plus:
configuration:
log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
logback的配置文件
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<Pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n</Pattern>
</encoder>
</appender>
<logger name="com.base22" level="TRACE"/>
<root level="info">
<appender-ref ref="STDOUT"/>
</root>
</configuration>
mapper
记得要在启动类上@MapperScan注解
@Repository
public interface UserMapper extends BaseMapper<user> {
}
实体类
@Data
public class user {
private int id;
private String name;
private Integer age;
private String email;
}
2:ybatis_plus的增删改查
21:简单插入
@Test
public void insert(){
user u=new user();
u.setName("aaa");
u.setAge(21);
u.setEmail("1234@qq.com");
int result=userMapper.insert(u);
System.out.println("影响的行数:"+result);
System.out.println("user id:"+u.getId());
}
输出:
影响的行数:1
user id:1412739741353529345
值得注意的问题: 数据库的id主键并没有设置自增,而且插入时user的id的值应该默认是0.但是插入后为什么会赋予一个1412739741353529345的主键?
分库分表策略
业务分库:将一个数据库按照业务功能的区分分为几个数据库 分库 代价:join无法使用,涉及多个数据库的事务无法使用
主从复制 :主机进行写操作,从机进行读操作
数据库分表: 不同的业务数据坟山储存到不同的数据库服务器。垂直拆分(字段列)或者水平(数据行)拆分
水平拆分-主键自增策略: 每个表存储一定区间的数据,例如表一id位1-999999,表二为100000-199999。缺点是每个表的大小可能不一,一个表可能有1000条数据(这个id区间的数据大部分被删除了),一个表有9万条数据。
水平拆分-hash策略: 比如有十个表,通过id%10的值来决定放在哪个表中,比如id=15的数据放到编号5的表中.难点在于数据库的数量的选取。优点是数据分布均匀。缺点是扩充新的表比较困难
雪花算法:分布式ID生成器: 保证不同表的主键的不重复性,以及相同表的主键的有序性
mybatis_plus的主键策略
默认使用雪花算法.数据库不用设置主键自增
还有主键自增策略:数据库要设置为主键自增。代码的自增差旅也要修改,如下
@Data public class user { @TableId(type = IdType.AUTO) private Long id; private String name; private Integer age; private String email; }全局设置主键生成策略(在配置文件中):
mybatis-plus: global-config: db-config: id-type: auto
2.2:更新操作
通过id修改数据
@Test
public void update(){
user u=new user();
u.setId(0l);
u.setAge(30);
int result=userMapper.updateById(u);
System.out.println("影响的行数:"+result);
System.out.println(u.toString());
}
开发规范,习惯。设置数据的创建和更新时间
数据库表修改如下:
实体类也做修改,添加字段:
@Data
public class user {
private Long id;
private String name;
private Integer age;
private String email;
private Date createTime;//驼峰自动转换
private Date updateTime;
}
业务层添加创建时间和修改更新时间可以通过mybatis_plus的自动填充功能实现,而无需每次手动去设置
自动填充功能
该功能可以用来实现例如添加创建时间和修改更新时间
首先在实体类上添加自动填充注解到要主动填充的字段上面:
@Data
public class user {
private Long id;
private String name;
private Integer age;
private String email;
@TableField(fill = FieldFill.INSERT)
private Date createTime;//驼峰自动转换
@TableField(fill = FieldFill.INSERT_UPDATE)
private Date updateTime;
}
然后实现元对象处理接口:
一般放在handler包下
@Slf4j(topic = "mybatis_plus自动填充")
@Component
public class MyMetaObjectHandler implements MetaObjectHandler {
@Override
public void insertFill(MetaObject metaObject) {
this.setFieldValByName("createTime",new Date(),metaObject);
this.setFieldValByName("updateTime",new Date(),metaObject);
log.info("插入一个数据,自动填充创建时间和更新时间");
}
@Override
public void updateFill(MetaObject metaObject) {
this.setFieldValByName("updateTime",new Date(),metaObject);
log.info("更新数据,自动填充更新时间");
}
}
现在便可以自动设置对象(这里是user)的某些字段值了。这里传入的metaObject其实就是我们调用插入或者更新方法传入的对象,例如
userMapper.insert(user),在调用插入后,就会自动为这个user填充插入时间和更新时间,而不需要我们手动调用setter方法。上面的meteObject里面就包含这个user。setFieldValByName方法就是为meteObject里面的对象的相应字段设置相应值。通俗点说这里就是自动调用setter方法设置一个值
2.3:乐观锁
首先要注入插件,使用springboot配置方式
@Bean
public MybatisPlusInterceptor mybatisPlusInterceptor() {
MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
interceptor.addInnerInterceptor(new OptimisticLockerInnerInterceptor());
return interceptor;
}
在实体类的字段上加上@Version注解
@Version
private Integer version;
2.4:基本查询
2.4.1:批量查询
@Test
public void Beach(){
List<user> userList= userMapper.selectBatchIds(Arrays.asList(1,2,3));
log.info(String.valueOf(userList));
}
2.4.2:条件查询
@Test
public void select(){
Map<String,Object> map=new HashMap<>();
map.put("name","yfy");
map.put("age",30);
List<user> users= userMapper.selectByMap(map);
log.info(String.valueOf(users));
}
2.4.3:分页查询
先配置分页插件
@Bean
public PaginationInterceptor mybatisPlusInterceptor() {
return new PaginationInterceptor();
}
测试
@Test
public void selectPage(){
Page<user> page=new Page<>(1,5);
Page<user> pageParam = userMapper.selectPage(page, null);
List<user> users=pageParam.getRecords();
log.info(String.valueOf(users));
System.out.println("总页数"+pageParam.getPages());
System.out.println("总记录数"+pageParam.getTotal());
System.out.println("当前页"+pageParam.getCurrent());
System.out.println("每页记录数"+pageParam.getSize());
System.out.println("是否有下一页"+pageParam.hasNext());
System.out.println("是否有上一页"+pageParam.hasPrevious());
}
补充
2.5:删除
物理删除
@Test
public void delete(){
//根据id删除
userMapper.deleteById(0);
//批量删除
userMapper.selectBatchIds(Arrays.asList(1,2,3));
//自定义删除条件
Map<String,Object> map=new HashMap<>();
map.put("name","yfy");
userMapper.deleteByMap(map);
}
逻辑删除
增加逻辑删除标志
@Test
public void logdelete(){
userMapper.deleteById(1);
}
这样删除时进行的是update操作