一、什么是Mybatis
MyBatis 是一款优秀的持久层框架,它支持自定义 SQL、存储过程以及高级映射。MyBatis 免除了几乎所有的 JDBC 代码以及设置参数和获取结果集的工作。MyBatis 可以通过简单的 XML 或注解来配置和映射原始类型、接口和 Java POJO(Plain Old Java Objects,普通老式 Java 对象)为数据库中的记录。
二、Mybatis的优点
简单的说一下mybatis相对jdbc的优势:
1.mybatis是把连接数据库的信息都是写在配置文件中,因此不存在硬编码问题,方便后期维护。
2.mybatis执行的sql语句都是通过配置文件进行配置,不需要写在java代码中。
3.mybatis的连接池管理、缓存管理等让连接数据库和查询数据效率更高。
三、Mybatis全局配置文件
Mybatis全局配置文件是用来配置一些环境信息的,一般名称为mybatis-config.xml,但也可以根据个人喜好改变。
4.1全局配置的内容和顺序
Properties(属性)
Settings(全局参数设置)(最好要)
typeAliases(类型别名)(必要)
typeHandlers(类型处理器)
objectFactory(对象工厂)
plugins(插件)
environments(环境信息集合)
environment(单个环境信息)
transactionManager(事物)
dataSource(数据源)(必要)
mappers(映射器)(必要)
4.2 常见配置的详解
1. properties标签
通过该标签读取java配置信息
例如数据源信息写在文件jdbc.properties里,可以通过properties属性读取该文件里的内容。
jdbc.properites:
jdbc.driver=com.mysql.cj.jdbc.Driver
jdbc.url=jdbc:mysql://localhost:3307/saolei?useUnicode=true&characterEncoding=UTF-8&serverTimezone=UTC
jdbc.uid=root
jdbc.password=111111
mybatis全局配置文件mybatis-config.xml可以使用properties标签读取外部文件jdbc.properties里的内容,properties文件的内容通常以键值对的形式呈现,之后可以通过${键名}的方式获取键值了。
<!-- 通过properties标签,读取java配置文件的内容
properties: 引入外部的属性文件
resource: 从类路径下引入属性文件
url: 引入网络路径或者是磁盘路径下的属性文件 -->
<properties resource="jdbc.properties" />
<!--举例使用,将参数引入到连接池配置中-->
<dataSource type="POOLED">
<property name="driver" value="${jdbc.driver}"/>
<property name="url" value="${jdbc.url}"/>
<property name="username" value="${jdbc.uid}"/>
<property name="password" value="${jdbc.password}"/>
</dataSource>
注意事项:jdbc.properties文件中的键名最好加一个前缀比如jdbc,这样可以防止与其他属性冲突
2.settings标签
该标签是mybaits的全局设置,设置结果会影响mybatis的运行。以下是该标签下的一些配置项的说明
以下是Mybatis的默认配置
<settings>
<setting name="cacheEnabled" value="true"/>
<setting name="lazyLoadingEnabled" value="true"/>
<setting name="multipleResultSetsEnabled" value="true"/>
<setting name="useColumnLabel" value="true"/>
<setting name="useGeneratedKeys" value="false"/>
<setting name="autoMappingBehavior" value="PARTIAL"/>
<setting name="autoMappingUnknownColumnBehavior" value="WARNING"/>
<setting name="defaultExecutorType" value="SIMPLE"/>
<setting name="defaultStatementTimeout" value="25"/>
<setting name="defaultFetchSize" value="100"/>
<setting name="safeRowBoundsEnabled" value="false"/>
<setting name="mapUnderscoreToCamelCase" value="false"/>
<setting name="localCacheScope" value="SESSION"/>
<setting name="jdbcTypeForNull" value="OTHER"/>
<setting name="lazyLoadTriggerMethods"
value="equals,clone,hashCode,toString"/>
</settings>
3.typeAliases标签
该标签的作用是对某个类进行别名设置,这样之后引用就不需要使用全限定类名,简化开发,提高效率,Mybatis对常用的数据类型提供了默认别名,以下列举一些
别名 | 映射类型 |
---|---|
_byte | byte |
byte | Byte |
_int | int |
_integer | int |
int | Integer |
integer | Integer |
当有下划线时,映射类型是基本数据类型,当没有下划线时,映射类型时基本数据类型对应的对象类型
如果想要自定义单个类别名
<typeAliases>
<!-- 设置单个别名 -->
<typeAlias type="com.lc.mybatis.po.User" alias="user"/>
</typeAliases>
自定义之批量定义别名:默认的别名就是类名
<!-- 设置别名 -->
<typeAliases>
<!-- 批量设置别名 -->
<!-- package:指定包名称来为该包下的po类声明别名,默认的别名就是类名(类名首字母大小写都可以) -->
<package name="com.lc.mybatis.po"/>
</typeAliases>
4.mappers标签
该标签的作用是加载映射文件,有两种方式来映射文件
方式一:< mapper resource=""/ >
该方式是加载相对于类路径下的映射文件,类路径默认为Root Resource路径下:
<mappers>
<mapper resource="mapper/User.xml"/>
</mappers>
方式二:
该方式使用全限定路径:
<mapper url="file:///D:\workspace_spingmvc\mybatis_01\config\sqlmap\User.xml" />`在这里插入代码片`
方式三:
该方式使用Mapper接口:
有SQL映射文件 , 要求Mapper接口与 SQL映射文件同名同位置.
没有SQL映射文件 , 使用注解在接口的方法上写SQL语句.
<package name="cn.lc.mybatis.mapper"/>
5.environments
- MyBatis可以配置多种环境,比如开发、测试和生产环境需要有不同的配置
- 每种环境使用一个environment标签进行配置并指定唯一标识符
- 可以通过environments标签中的default属性指定一个环境的标识符来快速的切换环境
- environment-指定具体环境
- id:指定当前环境的唯一标识 transactionManager、和dataSource都必须有
<environments default="oracle">
<environment id="mysql">
<transactionManager type="JDBC" />
<dataSource type="POOLED">
<property name="driver" value="${jdbc.driver}" />
<property name="url" value="${jdbc.url}" />
<property name="username" value="${jdbc.username}" />
<property name="password" value="${jdbc.password}" />
</dataSource>
</environment>
<environment id="oracle">
<transactionManager type="JDBC"/>
<dataSource type="POOLED">
<property name="driver" value="${orcl.driver}" />
<property name="url" value="${orcl.url}" />
<property name="username" value="${orcl.username}" />
<property name="password" value="${orcl.password}" />
</dataSource>
</environment>
</environments>
下面是enviroment标签下的标签配置
transactionManager
1.type参数
JDBC:使用JDBC的提交和回滚设置,依赖于从数据源得到的连接来管理事务范围。 JdbcTransactionFactory
MANAGED:不提交或回滚一个连接、让容器来管理事务的整个生命周期(比如JEE应用服务器的上下文)。 ManagedTransactionFactory
自定义:实现TransactionFactory接口,type=全类名/别名
2.dataSource
UNPOOLED:不使用连接池, UnpooledDataSourceFactory
POOLED:使用连接池, PooledDataSourceFactory
JNDI: 在EJB 或应用服务器这类容器中查找指定的数据源
实际开发中我们使用Spring管理数据源,并进行事务控制的配置来覆盖上述配置
4.映射文件
映射文件
#能在很大程度上防止sql注入,而 $ 则不行。
对于sql语句:select * from user where account = #{account} and password = #{pwd},
如果前台传来的账户名是“a”,密码是 “1 or 1=1”,用#的方式就不会出现sql注入,sql语句为
select * from user where account = ‘a’ and password = ‘1 or 1=1’ 查出account为a,password为1 or 1=1的用户
,而如果换成$方式,sql语句就变成了
select * from user where account = a and password = 1 or 1=1 查出全部用户数据
这样会产生sql注入的情况,比较不安全
MyBatis排序时使用order by 动态参数时需要注意,用$而不是#
<select id="findUserById" parameterType="java.lang.Integer" resultType="user">
SELECT * FROM USER WHERE id = #{id}
</select>
在进行模糊查询时,需要进行模糊匹配,采用$ 可以使用like “%${remark}%” 方法,
<select id="findUsersByName" parameterType="java.lang.String" resultType="com.lc.mybatis.po.User">
SELECT * FROM USER WHERE username LIKE "%${value}%"
</select>
5.测试代码
public class UserMapperTest {
private SqlSessionFactory sqlSessionFactory ;
@Before//每次test之前运行before函数
public void setUp() throws IOException {
//将配置文件导成输入流
InputStream inputStream = Resources.getResourceAsStream("SqlMapConfig.xml");
//创建工厂类
sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
}
@Test
public void testFindUserById() {
//创建sqlSession对象
SqlSession sqlSession = sqlSessionFactory.openSession();
//获取UserMapper的代理类
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
User user = userMapper.findUserById(10);
System.out.println(user);
sqlSession.close();
}
}
6.Mybatis一级缓存
也称为本地缓存,用于保存用户在一次会话过程中查询的结果,用户一次会话中只能使用一个sqlSession,一级缓存是自动开启的,不允许关闭。
一级缓存是sqlSession级别的缓存,在操作数据库的时候,需要构造sqlSession对象,在对象中有一个数据结构(HashMap)用于存储缓存数据。不同的SqlSession的缓存区域(HashMap)是互相不受影响的。
当sqlSession对象第一次执行sql语句时,会从底层数据库去读取数据并添加到缓存对象PerpetualCache中,第二次执行相同的语句时,会直接从缓存对象中读数据。
如果sqlSession执行了增删改操作,则会清除缓存,保证读到的数据是最新的数据,防止脏读。
7.Mybatis二级缓存
也称为全局缓存,是mapper级别的缓存,是针对一个表的查结果的存储,可以共享给所有针对这张表的查询的用户。也就是说对于mapper级别的缓存不同的sqlsession是可以共享的。
二级缓存的作用域是mapper的同一个namespace。不同的sqlSession两次执行相同的namespace下的sql语句,且向sql中传递的参数也相同,即最终执行相同的sql语句,则第一次执行完毕会将数据库中查询的数据写到缓存,第二次查询会从缓存中获取数据,不再去底层数据库查询,从而提高效率。
更多参考:https://www.cnblogs.com/jiangxiangit/p/7257935.html添加链接描述