SpringBoot中的Mybatis

一级目录

二级目录

三级目录

什么是mybatis

(1)Mybatis 是一个半 ORM(对象关系映射)框架,它内部封装了 JDBC,开发时只需要关注 SQL 语句本身,不需要花费精力去处理加载驱动、创建连接、创建statement 等繁杂的过程。程序员直接编写原生态 sql,可以严格控制 sql 执行性能,灵活度高。
(2)MyBatis 可以使用 XML 或注解来配置和映射原生信息,将 POJO 映射成数据库中的记录,避免了几乎所有的 JDBC 代码和手动设置参数以及获取结果集。 @Insert @Repository
(3)通过 xml 文件或注解的方式将要执行的各种 statement 配置起来,并通过java 对象和 statement 中 sql 的动态参数进行映射生成最终执行的 sql 语句,最后由 mybatis 框架执行 sql 并将结果映射为 java 对象并返回。(从执行 sql 到返回 result 的过程)。

Mybaits 的优点:(1)基 于 SQL 语句编程,相当灵活,不会对应用程序或者数据库的现有设计造成任何影响,SQL 写在 XML 里,解除 sql 与程序代码的耦合,便于统一管理;提供 XML标签,支持编写动态 SQL 语句,并可重用。(2)与 JDBC 相比,减少了 50%以上的代码量,消除了 JDBC 大量冗余的代码,不需要手动开关连接;(3)很好的与各种数据库兼容(因为 MyBatis 使用 JDBC 来连接数据库,所以只要JDBC 支持的数据库 MyBatis 都支持)。(4)能够与 Spring 很好的集成;

Mybatis是如何进行分页的?分页插件的原理是什么?

Mybatis使用RowBounds对象进行分页,它是针对ResultSet结果集执行的内存分页,而非物理分页。可以在sql内直接书写带有物理分页的参数来完成物理分页功能,也可以使用分页插件来完成物理分页。

mapper 接口层代码如下

List selectBookByName(Map<String, Object> map, RowBounds rowBounds);

调用如下

List list = bookMapper.selectBookByName(map, new RowBounds(0, 5));

说明: new RowBounds(0, 5),即第一页,每页取5条数据

分页插件的基本原理是使用Mybatis提供的插件接口,实现自定义插件,在插件的拦截方法内拦截待执行的sql,然后重写sql,根据dialect方言,添加对应的物理分页语句和物理分页参数。

RowBounds(int offset, int limit)

mybatis指定POJO扫描包来让mybatis自动扫描到自定义POJO

在application.yml中
type-aliases-package: com.example.de.mapper

mybatis使用的注解

@Repository 只能标注在 DAO 类上呢?这是因为该注解的作用不只是将类识别为Bean,同时它还能将所标注的类中抛出的数据访问异常封装为 Spring 的数据访问异常类型

@MapperScan(“com.com.example.de.mapper”)

@MapperScan可以指定要扫描的Mapper类的包的路径。

这个DAO交給Spring管理,让mapper能够让别的类进行引用

从mybatis3.4.0开始加入了@Mapper注解,目的就是为了不再写mapper映射文件(那个xml写的是真的蛋疼。。。)

这样就可以用注解来完成对DAO层接口的实现

#{}和${}的区别是什么?

#{}是预编译处理,${}是字符串替换。

Mybatis在处理#{}时,会将sql中的#{}替换为?号,调用PreparedStatement的set方法来赋值;

Mybatis在处理 时 , 就 是 把 {}时,就是把 {}替换成变量的值。

使用#{}可以有效的防止SQL注入,提高系统安全性

比如ps.setInt(0, parameterValue),#{item.name}的取值方式为使用反射从参数对象中获取item对象的name属性值,相当于param.getItem().getName()

mybatis用分页插件PageHelper

  1. 需要引入PageHelper的jar包

  2. 在mybatis的全局配置文件SqlMapConfig.xml中配置该插件

<plugins>
    <plugin interceptor="com.github.pagehelper.PageHelper">
        <!-- 设置数据库类型 Oracle,Mysql,MariaDB,SQLite,Hsqldb,PostgreSQL六种数据库-->        
        <property name="dialect" value="mysql"/>
    </plugin>
</plugins>
  1. 在执行sql前添加插件,完成分页功能
     在查询的sql语句执行之前,添加一行代码PageHelper.startPage(1, 10);第一个参数表示第几页,第二个参数表示每页显示的记录数。这样在执行sql后就会将记录按照语句中设置的那样进行分页。如果需要获取总记录数的话,需要PageInfo类的对象,这个对象可以获取总记录数
    在这里插入图片描述

在这里插入图片描述

4.pageIn

在这里插入图片描述

mybatis生命周期

正确理解SqlSessionFactory、SqlSessionFactoryBuilder、SqlSession和Mapper的生命周期对于优化Mybatis尤为重要,这样可以使Mybatis高效正确完成;同为重要时Mybatis的生命周期对于理解Myabtis缓存的配置也尤为重要,我这里只做简单的文字介绍(其实也好理解):

(1)SqlSessionFactoryBuilder:作用就是创建一个构建器,一旦创建了SqlSessionFactory,它的任务就算完成了,可以回收。

(2)SqlSessionFactory:作用是创建SqlSession,而SqlSession相当于JDBC的一个Connection对象,每次应用程序需要访问数据库,我们就要通过SqlSessionFactory创建一个SqlSession,所以SqlSessionFactory在整Mybatis整个生命周期中(每个数据库对应一个SqlSessionFactory,是单例产生的)。

(3)SqlSession:生命周期是存在于请求数据库处理事务的过程中,是一个线程不安全的对象(在多线程的情况下,需要特别注意),即存活于一个应用的请求和申请,可以执行多条SQL保证事务的一致性。

(4)Mapper:是一个接口,并没有实现类它的作用是发送SQL,返回我们需要的结果,或者发送SQL修改数据库表,所以它存活于一个SqlSession内,是一个方法级别的东西。当SqlSession销毁的时候,Mapper也会销毁。

Mybatis 缓存

(1)系统缓存:包括一级缓存与二级缓存

一级缓存:默认情况下Myabtis对于同一个SqlSession开启一级缓存

在默认没有配置的情况下,只会开启一级缓存(只针对同一个SqlSession而言);
在参数与SQL完全一样的情况下并且不声明刷新缓存没超时的,使用同一个SqlSession对象调用同一个Mapper方法时(SqlSession对象生命周期为方法级别),SqlSession只会取出当前缓存数据,不会再到数据库中进行查询;
如果不同的SqlSession,即使同一个Mapper也会进行到数据库中进行不同的查询,即不同的SqlSession一级缓存是无效的。

二级缓存:这里可以结合SqlSessionFactory等的生命周期能加深理解

不同的SqlSession是隔离的,为了解决这个问题,我们可以在SqlSessionFactory层面上设置二级缓存提供各个对象SqlSession
二级缓存默认是不开启的,需要进行配置,Mybatis要求返回的POJO必须是可序列化的,即POJO实现Serializable接口。
  缓存的配置只需要在XML配置即可,或者指定算法,刷新时间间隔,缓存状态,大小等

<缓存逐出=“ LRU” readOnly =“ true” flushInterval =“ 100000” size =“ 1024” > </缓存>
    A. 映射语句文件中所有select语句将会被缓存;

B. 映射语句文件中所有insert、update和delete语句会被刷新缓存;

C. 缓存使用默认的LRU最近最少使用算法回收;

D. 根据时间表,缓存不会任何时间顺序刷新;

E. 缓存会存储列表集合或对象的1024个引用

F. 缓存被视为可read/write的缓存,意味着是不可以被共享的,而可以被安全地修改。

mybatis plus

条件构造器queryWrapper

在这里插入图片描述
QueryWrapper : Entity 对象封装操作类,不是用lambda语法

在这里插入图片描述
上图表格为条件构造器使用中的各个方法格式和说明

mybatis-plus BaseMapper

在使用Mybatis-Plus中我们可能用到一个比较多的类是BaseMapper接口,其最终也是利用的Mybatis接口编程的实现机制,其默认提供了一系列的增删改查的基础方法,并且开发人员对于这些基础操作不需要写SQL进行处理操作(Mybatis提供的机制就是需要开发人员在mapper.xml中提供sql语句),那样我们可以猜测肯定是Mybatis-Plus完成了BaseMapper接口提供的方法的SQ L语句的生成操作

支持热加载:Mapper 对应的 XML 支持热加载,对于简单的 CRUD 操作,甚至可以无 XML 启动

在Mybatis-Plus中提供了SqlMethod类,从这个类中我们可以看到针对BaseMapper类中的每个方法,SqlMethod都提供了一个SQL语句的模板来生成SQL语句,最终还是一个namespace+method对应一条sql语句

映射数据库的表名

1.@TableName(value = “user”)

2.默认:采用驼峰映射规则,例如MyUserTable 对应的数据库表为 my_user_table ; TEMyUserTable 对应表名为t_e_my_user_table;

java8中::的作用与LambdaQueryWrapper对象使用

::在java8中的作用就是获得方法

LambdaQueryWrapper是mybatis plus中的一个条件构造器对象,只是是需要使用Lambda 语法使用 Wrapper

DynamicFormStruct dynamicFormStruct = dynamicFormStructMapper.selectOne(
new LambdaQueryWrapper().eq(DynamicFormStruct::getDynamicFormId, buildParam.getDynamicFormId()));
//DynamicFormStruct::getDynamicFormId=buildParam.getDynamicFormId()
//这是一个查询语句,在dynamicFormStructMapper中查出一条DynamicFormStruct::getDynamicFormId=buildParam.getDynamicFormId()的信息

mybatisplus @TableName注解

写在实体类里面
@TableName(schema = “isc_flow”,
value = “flow_dynamic_form_struct”)
指定数据库里对应的表

java8中::的作用与LambdaQueryWrapper对象使用

LambdaQueryWrapper().eq(DynamicFormStruct::getDynamicFormId, buildParam.getDynamicFormId()));

从对应的表中找到 DynamicFormStruct.DynamicFormId=buildParam.getDynamicFormId()的记录

::作用
::在java8中的作用就是获得方法

update(T entity, Wrapper updateWrapper)使用

只需要注意,入参第一位是需要update的实体类,updateWrapper里的实体类是用于生成where条件的

代码实例:
CategoryManage category =
new CategoryManage().setIsDelete(ACTIVE).setUpdaterId(currentUser.getUserId()).setUpdaterName(currentUser.getNickName()).setUpdateTime(now);

categoryManageMapper.update(category,
new LambdaUpdateWrapper().eq(CategoryManage::getId, categoryId).eq(CategoryManage::getIsDelete, INACTIVE));

CategoryManage category是设置的更新参数

new LambdaUpdateWrapper().eq(CategoryManage::getId, categoryId).eq(CategoryManage::getIsDelete, INACTIVE)
是定位到需要更新的记录

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值