MyBatis是一款优秀的的持久层框架。几乎免除所有的JDBC配置。
1.MyBatis
MyBatis是一款优秀的的持久层框架。几乎免除所有的JDBC配置。
持久化:将事物从瞬时状态转化为持久状态。(内存–>磁盘)
官网:https://mybatis.org/mybatis-3/zh/index.html
maven依赖:
1 | <dependency> |
2.SqlSessionFactory
SqlSessionFactory用于创建SqlSession。
xml:
1 | InputStream resourceAsStream = Resources.getResourceAsStream("MyBatis-config.xml"); |
1 |
|
配置类(不推荐使用):
MyBatis提供了完整的配置类,但是有些复杂的配置和Java的注解不能很好的使用,因此还是推荐使用xml文件
1 | DataSource dataSource = new UserDataSourceFactory().getDataSource(); |
3.SqlSession
执行Sql语句,在旧版本中,直接使用SqlSession执行Sql,现在新版本改进了许多xml的配置,更提倡使用xml。
使用xml
1 |
|
1 | SqlSession SqlSession = DBHelper.getSqlSession(); |
根据getMapper(Class)方法获取mapper。
4.作用域
5.XML配置
XML中有些符号需要转移才能表达。
符号转义:
转义结果 | 转义 | 转义十进制 |
---|---|---|
空格 | |   |
< | < | < |
> | > | > |
& | & | & |
“ | " | " |
‘ | ' | ' |
× | × | × |
÷ | &divde; | ÷ |
configuration(配置):
- properties(属性)
- settings(设置)
- typeAliases(类型别名)
- typeHandlers(类型处理器)
- objectFactory(对象工厂)
- plugins(插件)
- environments(环境配置)
- environment(环境变量)
- transactionManager(事务管理器)
- dataSource(数据源)
- environment(环境变量)
- databaseIdProvider(数据库厂商标识)
- mappers(映射器)
properties(属性):
1 | <properties resource="./db.properties"> |
读取顺序:
- 读取properties元素体内指定的属性
- properties元素中的resource 或url 属性指定的文件,覆盖之前同名属性
- 作为方法参数传递的属性,覆盖之前读取过的属性
参数默认值:
1 | <properties resource="org/mybatis/example/config.properties"> |
settings(设置)
设置可以改变Mybatis运行时行为。
typeAliases(类型别名)
为java类型设置一个别名,减少冗余的名称书写。
1 | <typeAliases> |
package在没有注解的情况下,类型别名为类名首字母小写的非限定类名(大写也行),当有注解时,使用注解内的。
1 |
|
一些常用的类型的在MyBatis中的类型别名
别名 | 映射的类型 |
---|---|
_byte | byte |
_long | long |
_short | short |
_int | int |
_integer | int |
_double | double |
_float | float |
_boolean | boolean |
string | String |
byte | Byte |
long | Long |
short | Short |
int | Integer |
integer | Integer |
double | Double |
float | Float |
boolean | Boolean |
date | Date |
decimal | BigDecimal |
bigdecimal | BigDecimal |
object | Object |
map | Map |
hashmap | HashMap |
list | List |
arraylist | ArrayList |
collection | Collection |
iterator | Iterator |
environments(环境配置)
MyBatis 可以配置成适应多种环境,这种机制有助于将 Sql 映射应用于多种数据库之中, 现实情况下有多种理由需要这么做。
1 | <environments default="development"> |
使用default=”id”切换环境。
事务管理器(transactionManager)
Mybatis有两套事务管理器:type=”[JDBC|MANAGED]”
- JDBC – 这个配置直接使用了 JDBC 的提交和回滚设施,它依赖从数据源获得的连接来管理事务作用域。
- MANAGED – 这个配置几乎没做什么。它从不提交或回滚一个连接,而是让容器来管理事务的整个生命周期(比如 JEE 应用服务器的上下文)。 默认情况下它会关闭连接。然而一些容器并不希望连接被关闭,因此需要将 closeConnection 属性设置为 false 来阻止默认的关闭行为。
注:如果你正在使用 Spring + MyBatis,则没有必要配置事务管理器,因为 Spring 模块会使用自带的管理器来覆盖前面的配置。
mappers(映射器)
1.相对路径
1 | <mappers> |
2.使用URL
1 | <mappers> |
3.使用映射器接口实现类的完全限定名
1 | <mappers> |
4.包内映射器接口实现全部注册为映射器
1 | <mappers> |
6.映射器
cache
– 该命名空间的缓存配置。cache-ref
– 引用其它命名空间的缓存配置。resultMap
– 描述如何从数据库结果集中加载对象,是最复杂也是最强大的元素。parameterMap
– 此元素已被废弃,并可能在将来被移除!Sql
– 可被其它语句引用的可重用语句块。insert
– 映射插入语句。update
– 映射更新语句。delete
– 映射删除语句。select
– 映射查询语句。
6.1.取值符${}与#{}
例子:
1 | select * from user where id=[ ${id} | #{id} ] |
#{id}为预编译,在预处理时会将字符串拼接成select * from user where id=?在JDBC中相当于PreparedStatement。
${id}非预编译,只是简单的字符替换。
#{id}可以很大程度的防止Sql注入。
6.2.生成主键
方法一:
1 | <!--useGeneratedKeys设置为ture,mybatis会获取数据库的主键,keyProperty指定识别对象的属性--> |
方法二:
1 | <!--不推荐使用,该插入语句会先执行selectKey,根据结果作为主键--> |
6.3.crud
crud标签:
- select
- insert
- update
- delete
6.4.Sql
Sql标签意在减少Sql语句重复部分的书写。
1 | <!--id用于在导入时做标识--> |
include的refid 属性或内部语句中使用属性值
1 | <Sql id="test"> |
6.5参数
单一变量:
1 | <select id="getUser" parameterType="int" resultType="User"> |
当参数只有一个java基本数据类型或String的时候,我们可以直接传递。
Bean:
1 | <insert id="insertUser" parameterType="pojo.User"> |
对于javabean,mybatis可以直接识别它的属性,并获取其值。
Map:
1 | <insert id="insertUser" parameterType="map"> |
万能的Map,Map<String,Object>可以映射多个参数值。Map在MyBatis中使用map代表。
注解:
1 |
|
crud:@Select()、Update()、Insert()、Delete()
参数@Param()
6.6.列名
列名不匹配问题:
当在数据库查询出数据时,与javabean或pojo的列不匹配时,造成赋值失败。
在使用ReaultType时,Mybatis会创建一个ResultMap,对返回的Javabean或pojo的属性进行匹配,若不匹配可对查询结果起别名。
解决方法:
1.在查询语句使用别名
2.结果映射
1 | <resultMap id="userMap" type="User"> |
使用别名不能很好解决组合等关系(一个javabean类中有一个javabean类),
关联的嵌套select查询
assocation(对象映射):javaType返回的类型
collection(集合映射):ofType代表集合的泛型T
7.动态Sql
动态 Sql 是 MyBatis 的强大特性之一。大大优化了字符串的拼接。
MyBatis3元素:
- if
- choose (when, otherwise)
- trim (where, set)
- foreach
if
1 | <select id="getUserList" resultType="User"> |
choose (when, otherwise)
1 | <choose> |
choose类似java的switch语句,每个when是case,otherwise是default。test与if相同用作判断。
trim (where, set)
使用choose的语句容易出现多余and 、or、where等情况,这导致了sql语句错误。有俩种解决方法
1 | <!--方法一:在判断where后追加(1=1)--> |
where规则:where元素只有在子元素返回任何内容的情况下才插入”where”子句。若子句开头是”and”、”or”,where元素也会将其去除。
where语句也可以这样子实现,prefixOverrides属性会忽略管道符分隔的文本。
1 | <trim prefix="WHERE" prefixOverrides="AND |OR "> |
修改sql会存在动态的set,在Mybatis也有方法实现:
1 | <update id="update"> |
trim页可以实现该语句
1 |
|
foreach
在动态sql中,经常出现批量处理的语句。例:values…、in…、
1 | <insert id="insertUser" parameterType="pojo.User"> |
注解
在crud的注解中,我们可以嵌入script元素。(不推荐使用)
8.缓存
8.1一级缓存
一级缓存又称本地缓存。
缓存失效原因:
- 查询不同事物。
- 增删改操作,刷新缓存。
- 查询不同的Mapper.xml
- 手动清理缓存
一级缓存默认开启的,作用域为一次sql会话(Sqlsession)
8.2二级缓存
开启
1 | <cache/> |
小结:
- 只要开启二级缓存,在同一个Mapper下二级缓存有效。
- 所有数据都会先放在一级缓存。
- 只有当会话提交,关闭,才会将一级缓存提交到二级缓存。
参考文献
尽管这不是一个详尽的清单,但还是希望对大家有所启示。
[1]佚名.Mybatis官方文档[EB/OL]:[2021]