MyBatis 简介
MyBatis
是一个基于 Java
的长久层框架,它外部封装了 JDBC
,使开发者只需关注 SQL
语句自身,而不必再破费精力去解决诸如注册驱动、创立 Connection
、配置 Statement
等繁冗过程。
Mybatis
通过 xml
或注解的形式将要执行的各种 Statement
、PreparedStatement
等配置起来,并通过 Java
对象和 Statement
中 SQL
的动静参数进行映射生成最终执行的 SQL
语句,最初由 MyBatis
框架执行 SQL
并将后果映射成 Java
对象并返回。
MyBatis 与 Hibernate
Hibernate 框架是提供了全面的数据库封装机制的 全自动 ORM,即实现了 POJO 和数据库表之间的映射,以及 SQL 的主动生成和执行。
绝对于此,MyBatis 只能算作是 半自动 ORM。其着力点,是在 POJO 类与 SQL 语句之间的映射关系。也就是说,MyBatis 并不会为程序员主动生成 SQL 语句。具体的 SQL 须要程序员本人编写,而后通过 SQL 语句映射文件,将 SQL 所需的参数,以及返回的后果字段映射到指定 POJO。
MyBatis 特点
- 在
XML
文件中配置SQL
语句,实现了SQL
语句与代码的拆散,给程序的保护带来了很大便当。 - 能够联合数据库本身的特点灵便管制
SQL
语句,因而可能实现比Hibernate
等全自动ORM
框架更高的查问效率,可能实现简单查问。
Spring 整合 Mybatis
引入依赖
在 pom.xml
引入 Mybatis 相干依赖。
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.2.8</version>
</dependency>
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis-spring</artifactId>
<version>1.3.1</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>4.3.17.RELEASE</version>
</dependency>
创立 Mybatis 配置文件
在 resource
目录下创立 mybatis-config
配置文件。
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
<!-- 全局参数 -->
<settings>
<!-- 打印 SQL 语句 -->
<setting name="logImpl" value="STDOUT_LOGGING" />
<!-- 使全局的映射器启用或禁用缓存。-->
<setting name="cacheEnabled" value="false"/>
<!-- 全局启用或禁用提早加载。当禁用时,所有关联对象都会即时加载。-->
<setting name="lazyLoadingEnabled" value="true"/>
<!-- 当启用时,有提早加载属性的对象在被调用时将会齐全加载任意属性。否则,每种属性将会按须要加载。-->
<setting name="aggressiveLazyLoading" value="true"/>
<!-- 是否容许单条 SQL 返回多个数据集 (取决于驱动的兼容性) default:true -->
<setting name="multipleResultSetsEnabled" value="true"/>
<!-- 是否能够应用列的别名 (取决于驱动的兼容性) default:true -->
<setting name="useColumnLabel" value="true"/>
<!-- 容许 JDBC 生成主键。须要驱动器反对。如果设为了 true,这个设置将强制应用被生成的主键,有一些驱动器不兼容不过依然能够执行。default:false -->
<setting name="useGeneratedKeys" value="false"/>
<!-- 指定 MyBatis 如何主动映射 数据基表的列 NONE:不映射 PARTIAL:局部 FULL: 全副 -->
<setting name="autoMappingBehavior" value="PARTIAL"/>
<!-- 这是默认的执行类型(SIMPLE: 简略;REUSE: 执行器可能重复使用 prepared statements 语句;BATCH: 执行器能够反复执行语句和批量更新)-->
<setting name="defaultExecutorType" value="SIMPLE"/>
<!-- 应用驼峰命名法转换字段。-->
<setting name="mapUnderscoreToCamelCase" value="true"/>
<!-- 设置本地缓存范畴 session: 就会有数据的共享 statement: 语句范畴 (这样就不会有数据的共享) defalut:session -->
<setting name="localCacheScope" value="SESSION"/>
<!-- 设置 JDBC 类型为空时, 某些驱动程序 要指定值, default:OTHER,插入空值时不须要指定类型 -->
<setting name="jdbcTypeForNull" value="NULL"/>
</settings>
</configuration>
创立集成配置文件
在 resource
目录下创立一个 spring-context-mybatis.xml
的集成配置文件。
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd">
<!-- 配置 SqlSession -->
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource"/>
<!-- 用于配置对应实体类所在的包,多个 package 之间能够用 ',' 号宰割 -->
<property name="typeAliasesPackage" value="com.antoniopeng.ssm.domain"/>
<!-- 用于配置对象关系映射 -->
<property name="mapperLocations" value="classpath:/mapper/**/*.xml"/>
<!-- - 用于配置文件所在目录 ->
<property name="configLocation" value="classpath:/mybatis-config.xml"></property>
</bean>
<!-- 扫描 Mapper -->
<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
<property name="basePackage" value="com.antoniopeng.ssm.dao" />
</bean>
</beans>
CRUD 案例
新增
<insert id="insert">
INSERT INTO tb_user (
id,
username,
password,
phone,
email,
created,
updated
)
VALUES
(#{id},
#{username},
#{password},
#{phone},
#{email},
#{created},
#{update}
)
</insert>
删除
<delete id="delete">
DELETE FROM tb_user WHERE id = #{id}
</delete>
查问
<select id="getById" resultType="TbUser">
SELECT
a.id,
a.username,
a.password,
a.phone,
a.email,
a.created,
a.updated AS "update"
FROM
tb_user AS a
WHERE
a.id = #{id}
</select>
更新
<update id="update">
UPDATE
tb_user
SET
username = #{username},
password = #{password},
phone = #{phone},
email = #{email},
created = #{created},
updated = #{update}
WHERE id = #{id}
</update>
MyBatis 动静 SQL
动静 SQL 次要用于解决查问条件不确定的状况:在程序运行期间,依据用户提交的查问条件进行查问。提交的查问条件不同,执行的 SQL 语句不同。若将每种可能的状况均逐个列出,对所有条件进行排列组合,将会呈现大量的 SQL 语句。此时,可应用动静 SQL 来解决这样的问题。这里的条件判断应用的表达式为 OGNL
表达式。罕用的动静 SQL 标签有 <if>
、<where>
、<choose>
、<foreach>
等。
留神:在 mapper 的动静 SQL 中若呈现 >
、<
、>=
,<=
等符号,最好将其转换为实体符号。否则,XML 可能会呈现解析出错问题,特地是 <
在 XML 中是相对不能呈现的。
if 标签
对于该标签的执行,当 test 的值为 true 时,会将其蕴含的 SQL 片断拼接到其所在的 SQL 语句中。
案例
为了解决两个条件均未做设定的状况,在 where 后增加了一个“1=1”的条件。这样就不至于两个条件均未设定而呈现只剩下一个 where,而没有任何可拼接的条件的不残缺 SQL 语句。
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.antoniopeng.ssm.dao.StudentDao">
<!-- if -->
<select id="selectByIf" resultType="com.antoniopeng.ssm.entity.Student">
SELECT
*
FROM
student
WHERE 1 = 1
<if test="name != null and name !=''">
AND name LIKE concat('%', #{name}, '%')
</if>
<if test="age != null and age > 0">
AND age > #{age}
</if>
</select>
</mapper>
where 标签
<if/> 标签的中存在一个比拟麻烦的中央:须要在 where 后手工增加 1=1 的子句。因为,若 where 后的所有 <if/> 条件均为 false,而 where 后若又没有 1=1 子句,则 SQL 中就会只剩下一个空的 where,SQL 出错。所以,在 where 后,须要增加永为真子句 1=1,以避免这种状况的产生。但当数据量很大时,会重大影响查问效率。
案例
<select id="selectByWhere" resultType="com.antoniopeng.ssm.entity.Student">
SELECT
*
FROM
student
<where>
<if test="name != null and name !=''">
AND name LIKE concat('%', #{name}, '%')
</if>
<if test="age != null and age > 0">
AND age > #{age}
</if>
</where>
</select>
choose 标签
该标签中只能够蕴含 <when/>
、<otherwise/>
,能够蕴含多个 <when/>
与一个 <otherwise/>
。它们联结应用,实现 Java 中的开关语句 switch case 性能。
案例
本例要实现的需要是,若姓名不空,则依照姓名查问;若姓名为空,则依照年龄查问;若没有查问条件,则没有查问后果。
<!-- choose -->
<select id="selectByChoose" resultType="com.antoniopeng.ssm.entity.Student">
SELECT
*
FROM
student
<where>
<choose>
<when test="name != null and name !=''">
AND name LIKE concat('%', #{name}, '%')
</when>
<when test="age != null and age > 0">
AND age > #{age}
</when>
<otherwise>
AND 1 != 1
</otherwise>
</choose>
</where>
</select>
foreach 标签
该标签用于实现对于数组与汇合的遍历。对其应用,须要留神:collection
示意要遍历的汇合类型,这里是数组,即 array。open
、close
、separator
为对遍历内容的 SQL 拼接。
遍历数组案例
<!-- foreach -->
<select id="selectByForeach" resultType="com.antoniopeng.ssm.entity.Student">
SELECT
*
FROM
student
<if test="array != null and array.length > 0">
WHERE id IN
<foreach collection="array" open="(" close=")" item="id" separator=",">
#{id}
</foreach>
</if>
</select>
遍历泛型为根本类型的汇合案例
/**
* 应用 foreach 标签以 list 根本类型的模式查问
* @param ids
* @return
*/
public List<Student> selectByForeachWithListBase(List<Long> ids);
<!-- foreach -->
<select id="selectByForeachWithListBase" resultType="com.antoniopeng.ssm.entity.Student">
SELECT
*
FROM
student
<if test="list != null and list.size > 0">
WHERE id IN
<foreach collection="list" open="(" close=")" item="id" separator=",">
#{id}
</foreach>
</if>
</select>
遍历泛型为自定义类型的汇合案例
/**
* 应用 foreach 标签以 list 自定义类型的模式查问
* @param students
* @return
*/
public List<Student> selectByForeachWithListCustom(List<Student> students);
<!-- foreach -->
<select id="selectByForeachWithListCustom" resultType="com.antoniopeng.ssm.entity.Student">
SELECT
*
FROM
student
<if test="list != null and list.size > 0">
WHERE id IN
<foreach collection="list" open="(" close=")" item="student" separator=",">
#{student.id}
</foreach>
</if>
</select>
sql 标签
该标签用于定义 SQL 片断,以便其它 SQL 标签复用。而其它标签应用该 SQL 片断,须要应用 <include/>
子标签。该标签能够定义 SQL 语句中的任何局部,所以 <include/>
子标签能够放在动静 SQL 的任何地位。
案例
<sql id="select">
SELECT
id,
name,
age,
score
FROM
student
</sql>
应用 sql 标签
<!-- foreach -->
<select id="selectByForeachWithListCustom" resultType="com.antoniopeng.ssm.entity.Student">
<include refid="select" />
</select>
- 文章作者:彭超
- 原文链接:[]()
- 版权申明:本博客所有文章除特地申明外,均采纳 CC BY-NC-SA 4.0 许可协定。转载请注明来自 彭超的博客!