一、mybatis 介绍
今天,一起来说说mybits这个框架吧。这是一个持久层的框架。之前叫做ibatis。
所以,在它的代码中出现ibatis这个词的时候,不要感到惊讶。不是写错了,它确实就是这个样子的。
MyBatis 是一款优秀的持久层框架,它支持定制化 SQL、存储过程以及高级映射。
MyBatis 避免了几乎所有的 JDBC 代码和手动设置参数以及获取结果集。
MyBatis 可以使用简单的 XML 或注解来配置和映射原生信息,将接口和 Java 的 POJOs(Plain Old Java Objects,
普通的 Java对象)映射成数据库中的记录。
MyBatis 本是apache的一个开源项目iBatis, 2010年这个项目由apache software foundation 迁移到了google code,并且改名为MyBatis 。
2013年11月迁移到Github。
二、mybatis 入门
-
新建一个maven工程
-
配置依赖
<dependencies> <!-- 添加MySQL数据库驱动依赖包. --> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>5.1.30</version> </dependency> <!-- 添加mybatis依赖 --> <dependency> <groupId>org.mybatis</groupId> <artifactId>mybatis</artifactId> <version>3.3.0</version> </dependency> <!--log4j--> <dependency> <groupId>log4j</groupId> <artifactId>log4j</artifactId> <version>1.2.17</version> </dependency> <!--junit--> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.12</version> <scope>test</scope> </dependency> </dependencies> <build> <plugins> <plugin> <artifactId>maven-compiler-plugin</artifactId> <configuration> <source>1.8</source> <target>1.8</target> <encoding>UTF-8</encoding> </configuration> </plugin> </plugins> </build>
-
导入jdbc.properties 和log4j.properties
-
新建mybatis-config.xml(mybatis配置)文件,并且复制如下内容
<?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> <!-- 加载属性文件 --> <properties resource="jdbc.properties"></properties> <!-- 和spring整合后 environments配置将废除 --> <environments default="development"> <environment id="development"> <!-- 使用jdbc事务管理,事务控制由mybatis --> <transactionManager type="JDBC" /> <!-- 数据库连接池,由mybatis管理 --> <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> </environments> <!-- 加载配置文件 --> <mappers> <mapper resource="xxxxxxxx" /> </mappers> </configuration>
-
编写 mapper接口 && mapper.xml(可以理解为mapper.xml是mapper接口的实现类)
<?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="接口地址"> </mapper>
-
编写测试类
InputStream cof = Resources.getResourceAsStream("mybatis-config.xml"); // 创建会话工厂 SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(cof); SqlSession sqlSession = sqlSessionFactory.openSession(); XXX mapper = sqlSession.getMapper(XXX.class);
三、mapper配置文件的三种方式
<!-- 第一种方式:通过resource指定 -->
<!--<mapper resource="com/dy/dao/userDao.xml" /> -->
<!-- 第二种方式, 通过class指定接口,进而将接口与对应的xml文件形成映射关系 不过,使用这种方式必须保证 接口与mapper文件同名(不区分大小写), 我这儿接口是UserDao,那么意味着mapper文件为UserDao.xml -->
<!-- <mapper class="com.dy.dao.UserDao"/> -->
<!-- 第三种方式,直接指定包,自动扫描,与方法二同理 -->
<!-- <package name="com.dy.dao"/> -->
四、增删查改
<select id="方法名字" parameterType="参数类型(可忽略)" resultType="返回类型">
sql
</select>
<delete id="方法名字" parameterType="参数类型(可忽略)">
sql
</delete>
<update id="方法名字" parameterType="参数类型(可忽略)">
sql
</update>
<insert id="方法名字" parameterType="参数类型(可忽略)" keyProperty="注入id属性(可忽略)" useGeneratedKeys="true(可忽略)">
sql
</insert>
五、别名配置
<typeAliases>
<!--配置单个-->
<typeAlias alias="xxx" type="xxx"/>
<!--配置多个-->
<package name="包名"/>
</typeAliases>
六、# 和 $的区别
-
是预编译的(防住sql注入),$不是
- 如果方法只有单个参数的情况下,#可以忽略不写@Param(""),$必须写\
- 单个参数用上if for标签的时候,要写@Param("").#使用like 条件请参考https://www.cnblogs.com/icewee/articles/6927841.html
七、如何传入多个参数
-
利用下标(String xxId, String xxCode)
#{0} #{1} 下标从0开始
-
在参数加@Param("")
( @Param(“x”) String xxId,@Param(“y”) String xxCode) #{x} #{y} 下标从0开始
-
利用HashMap map 或实体类
#{xxId} #{xxCode}
八、resultType和resultMap区别
- resultType 不支持字段的别名
resultMap 支持字段的别名
支持orm
九、sql片段
-
声明片段名称
<sql id="片段名称"></sql>
-
引入片段
<include refid="片段名称"></include>
十、if标签
<if test="条件">内容</if>
十一、where标签
十二、foreach标签
<foreach collection="遍历的集合(没有给别名填写collection或array,生命参数名,写参数名字)" item="每次迭代的临时对象" index="每次迭代的下标" open="未开始前遍历的内容" close="遍历后的内容" separator="每次遍历的内容" >
</foreach>
批量新增的例子
<insert id="batchInsert">
insert into user (name,sex,birth,pwd,city,head)
values
<foreach collection="collection" item="user" index="index" open="" close="" separator=",">
(#{user.name},#{user.sex},#{user.birth},#{user.pwd},#{user.city},#{user.head})
</foreach>
</insert>
批量删除例子
<delete id="batchDelete">
delete from user where id in
<foreach collection="ids" item="id" index="index" open="(" close=")" separator=",">
#{id}
</foreach>
</delete>
十三、表关联关系
-
一对一
1)在任意一方表上设计外键
2)在不设计外键的情况下,可以使用主键一致来设计 -
一对多
在多的一方设计外键
-
多对多
使用中间表(记录双方外键)
十四、orm 配置
即Object-Relationl Mapping,它的作用是在关系型数据库和对象之间作一个映射,这样,我们在具体的操作数据库的时候,就不需要再去和复杂的SQL语句打交道,只要像平时操作对象一样操作它就可以了 。
-
一对一
双方向配置以下配置 <association property="属性名" column="字段名" javaType="类型" select="映射查询" > </association>
-
一对多
多的一方
<collection property="属性名" column="字段名" ofType="类型" select="映射查询" > </collection>
一的一方
<association property="属性名" column="字段名" javaType="类型" select="映射查询" > </association>
-
多对多
双方向配置以下配置
<collection property="属性名" column="字段名" ofType="类型" select="映射查询" > </collection>
十五、赖加载模式
-
按需赖加载
1)在mybatis-config.xml文件下添加按需加载模式 <!-- 配置设置 --> <settings> <!-- 将积极加载改为消息加载即按需加载 --> <setting name="aggressiveLazyLoading" value="false" /> </settings> 2)在要赖加载的地方加上fetchType="lazy"
-
全局赖加载
1)在mybatis-config.xml文件下添加按需加载模式 <!-- 配置设置 --> <settings> <!-- 打开延迟加载的开关 --> <setting name="lazyLoadingEnabled" value="true" /> <!-- 将积极加载改为消息加载即按需加载 --> <setting name="aggressiveLazyLoading" value="false" /> </settings>
十六、二级缓存
-
在mybatis-config.xml 里面的settings标签添加
<!-- 开启二级缓存 --> <setting name="cacheEnabled" value="true" />
-
在需要的mapper.xml文件配置
LRU:(Least Recently Used),最近最少使用算法,即如果缓存中容量已经满了,会将缓存中最近做少被使用的缓存记录清除掉,然后添加新的记录; FIFO:(First in first out),先进先出算法,如果缓存中的容量已经满了,那么会将最先进入缓存中的数据清除掉; <!-- eviction LRU flushInterval缓存时间,以毫秒为单位 size缓存大小 readOnly 是否只读,如果为true,则所有相同的sql语句返回的是同一个对象(有助于提高性能,但并发操作同一条数据时,可能不安全),如果设置为false,则相同的sql,后面访问的是cache的clone副本 --> <cache eviction="LRU" type="org.apache.ibatis.cache.impl.PerpetualCache" flushInterval="120000" size="1024" readOnly="true"/>
十七、PageHelper
-
在pom.xml文件添加依赖
<dependency> <groupId>com.github.pagehelper</groupId> <artifactId>pagehelper</artifactId> <version>4.2.1</version> </dependency> <dependency> <groupId>com.github.jsqlparser</groupId> <artifactId>jsqlparser</artifactId> <version>0.9.5</version> </dependency>
-
在mybatis-config.xml下添加插件配置(plugins标签一定要声明在settings和typeAliases标签下)
<!-- 配置PageHelper拦截器插件 --> <plugins> <!-- com.github.pagehelper为PageHelper类所在包名 --> <plugin interceptor="com.github.pagehelper.PageHelper"> <!-- 4.0.0以后版本可以不设置该参数 --> <property name="dialect" value="mysql" /> <!-- 该参数默认为false --> <!-- 设置为true时,会将RowBounds第一个参数offset当成pageNum页码使用 --> <!-- 和startPage中的pageNum效果一样 --> <property name="offsetAsPageNum" value="true" /> <!-- 该参数默认为false --> <!-- 设置为true时,使用RowBounds分页会进行count查询 --> <property name="rowBoundsWithCount" value="true" /> <!-- 设置为true时,如果pageSize=0或者RowBounds.limit = 0就会查询出全部的结果 --> <!-- (相当于没有执行分页查询,但是返回结果仍然是Page类型) --> <property name="pageSizeZero" value="true" /> <!-- 3.3.0版本可用 - 分页参数合理化,默认false禁用 --> <!-- 启用合理化时,如果pageNum<1会查询第一页,如果pageNum>pages会查询最后一页 --> <!-- 禁用合理化时,如果pageNum<1或pageNum>pages会返回空数据 --> <property name="reasonable" value="false" /> <!-- 3.5.0版本可用 - 为了支持startPage(Object params)方法 --> <!-- 增加了一个`params`参数来配置参数映射,用于从Map或ServletRequest中取值 --> <!-- 可以配置pageNum,pageSize,count,pageSizeZero,reasonable,orderBy,不配置映射的用默认值 --> <!-- 不理解该含义的前提下,不要随便复制该配置 --> <property name="params" value="pageNum=pageHelperStart;pageSize=pageHelperRows;" /> <!-- 支持通过Mapper接口参数来传递分页参数 --> <property name="supportMethodsArguments" value="false" /> <!-- always总是返回PageInfo类型,check检查返回类型是否为PageInfo,none返回Page --> <property name="returnPageInfo" value="none" /> </plugin> </plugins>
-
在查询之前添加分页代码
PageHelper.startPage(pageNum, pageSize);