什么是MyBatis

来源:互联网 发布:广东11选5遗漏360数据 编辑:程序博客网 时间:2024/05/21 21:38

1.什么是MyBatis

MyBatis 是支持普通 SQL 查询,存储过程和高级映射的优秀持久层框架。MyBatis 消除 了几乎所有的 JDBC 代码和参数的手工设置以及结果集的检索。MyBatis 使用简单的 XML 或注解用于配置和原始映射,将接口和 Java 的 POJOs(Plain Old Java Objects,普通的 Java 对象)映射成数据库中的记录。(类似Hibernate)

2.从XML中构建 SqlSessionFactory

每一个MyBatis的应用程序都以一个SqlSessionFactory对象的实例为核心。SqlSessionFactory 对象的实例可以通过 SqlSessionFactoryBuilder对象来 获 得 SqlSessionFactoryBuilder 对象可以从 XML 配置文件,或从 Configuration 类的实 例中构建 SqlSessionFactory 对象。

[java] view plain copy
  1. String resource = "domain/configuration.xml"//配置文件的位置  
  2. Reader reader =Resources.getResourceAsReader(resource);  
  3. SqlSessionFactory sf = new SqlSessionFactoryBuilder().build(reader);  

3. 从 SqlSessionFactory 中获取 SqlSession

SqlSession 对象完全包含以数据库为背景的所有执行 SQL 操作的 方法。你可以用 SqlSession 实例来直接执行已映射的 SQL 语句。 

[java] view plain copy
  1. SqlSession session = sqlSessionFactory.openSession();  
  2. try {  
  3.     Blog blog = (Blog)session.selectOne("org.mybatis.example.BlogMapper.selectBlog"101);  
  4. }  
  5. finally {  
  6.     session.close();  
  7. }  

4.Mapper XML 文件

4.1 select

[html] view plain copy
  1. <select id="selectPerson" parameterType="int" resultType="hashmap">  
  2.      SELECT * FROM PERSON WHERE ID = #{id}  
  3. </select>  

Id是select的标识,与Mapper.java中的函数名称一致完成映射。Hashmap代表返回值resultType是<key,value>,其中key是指列名。#{id}是指参数,和Mapper.java中参数同名。

参数也可以指定数据类型#{id,javaType=int,jdbcType=NUMERIC}

类似于java完成以下代码:// Similar JDBC code, NOT MyBatis…

[java] view plain copy
  1. String selectPerson = "SELECT * FROM PERSON WHERE ID=?";  
  2. PreparedStatement ps = conn.prepareStatement(selectPerson);  
  3. ps.setInt(1,id);  

4.2 insert, update, delete

[html] view plain copy
  1. <insert id="insertAuthor" useGeneratedKeys="true" keyProperty="id">  
  2.     insert into Author (username,password,email,bio) values (#{username},#{password},#{email},#{bio})  
  3. </insert>  

Update,delete用法类似,还有parameterType属性等。

4.3 resultMap

要记住类型别名是你的伙伴。使用它们你可以不用输入类的全路径。比如:

[html] view plain copy
  1. <!-- In mybatis-config.xml file -->  
  2. <typeAlias type="com.someapp.model.User" alias="User"/>  
  3. 使用时:  
  4. <select id="selectUsers" resultType="com.someapp.model.User">  
  5. 等同于: <select id="selectUsers" resultType="User">  

Eg: type属性是指实体类,一般要把

resultMap用来解决映射类的属性与数据库字段不一致的情况。

<!-- id是用来对主键映射的 result是用来对一般属性映射的   只需要对不一致的字段进行映射,其它的没有必要, id一致是,可以不映射 -->

[html] view plain copy
  1. <resultMap type="Address" id="addressMap">  
  2.     <id column="id" property="id"/>  
  3.     <result column="postcode" property="postcode" jdbcType=”varchar”/>  
  4. </resultMap>  
  5. <select id="selectById" parameterType="int" resultMap="addressMap">  
  6.     select * from t_address where id=#{id}  
  7. </select>  

4.4 sql

这个元素可以被用来定义可重用的 SQL 代码段,可以包含在其他语句中。比如:

[html] view plain copy
  1. <sql id="userColumns"> id,username,password </sql>  

这个 SQL 片段可以被包含在其他语句中,例如:

[html] view plain copy
  1. <select id="selectUsers" resultType="map">    
  2.     select  <include refid="userColumns"/>  from some_table  
  3.     where id = #{id}  
  4. </select>  

用include元素来引用,refid属性的值必须是某个sql元素的id.

5.动态SQL

5.1 if

在动态 SQL 中所做的最通用的事情是包含部分 where 字句的条件。比如:

[html] view plain copy
  1. <select id="findActiveBlogLike" resultType="Blog">   
  2.     SELECT * FROM BLOG WHERE state = ‘ACTIVE’   
  3.     <if test="title != null">  
  4.         AND title like #{title}  
  5.     </if>  
  6.     <if test="author != null and author.name != null">  
  7.         AND author_name like #{author.name}  
  8.     </if>  
  9. </select>  

理解时注意:其中的参数title、author都是从函数中传过来的值。不属于数据库中字段值。所以需要test判断是否为空。

5.2 choose when otherwise

相当于java语言中的switch……case语句,只需要满足一个条件:

[html] view plain copy
  1. <select id="findActiveBlogLike" resultType="Blog">  
  2.     SELECT * FROM BLOG WHERE state = ‘ACTIVE’  
  3.     <choose>  
  4.         <when test="title != null">  
  5.             AND title like #{title}  
  6.         </when>  
  7.         <when test="author != null and author.name != null">  
  8.             AND author_name like #{author.name}  
  9.         </when>  
  10.         <otherwise>  
  11.             AND featured = 1  
  12.         </otherwise>  
  13.     </choose>  
  14. </select>  

如果title、author二者都没提供,只返回 featured blogs(也许是由管理员策略地选 择的结果列表,而不是返回大量没有意义的随机博客结果列表)。

5.3 trim where set

为了变面下面代码这种情况,定义了where,set

[html] view plain copy
  1. <select id="findActiveBlogLike" resultType="Blog">  
  2.     SELECT * FROM BLOG WHERE   
  3.     <if test="state != null">  
  4.         state = #{state}  
  5.     </if>   
  6.     <if test="title != null">  
  7.         AND title like #{title}  
  8.     </if>  
  9.     <if test="author != null and author.name != null">  
  10.         AND author_name like #{author.name}  
  11.     </if>  
  12. </select>  

上面那代码会因为其中某些条件不满足导致下面的sql代码的出现:

[sql] view plain copy
  1. SELECT * FROM BLOG WHERE  
  2. SELECT * FROM BLOG WHERE   AND title like ‘someTitle’  

导致查询失败,为了避免这种情况,大多使用where元素:

[html] view plain copy
  1. <select id="findActiveBlogLike" resultType="Blog">  
  2.     SELECT * FROM BLOG   
  3.     <where>   
  4.         <if test="state != null">  
  5.             state = #{state}  
  6.         </if>   
  7.         <if test="title != null">  
  8.             AND title like #{title}  
  9.         </if>  
  10.         <if test="author != null and author.name != null">  
  11.             AND author_name like #{author.name}  
  12.         </if>  
  13.     </where>  
  14. </select>  

Where碰到and开头会自动过滤掉and.动态更新语句相似的解决方案是 set。set 元素可以被用于动态包含更新的列,而不包含不需更新的,可以自动过滤掉句末的符号。

[html] view plain copy
  1. <update id="updateAuthorIfNecessary">  
  2.     update Author  
  3.     <set>  
  4.         <if test="username != null">username=#{username},</if>  
  5.         <if test="password != null">password=#{password},</if>  
  6.         <if test="email != null">email=#{email},</if>  
  7.         <if test="bio != null">bio=#{bio}</if>  
  8.     </set>  
  9.     where id=#{id}  
  10. </update>  

不管是where元素和set元素遇到的问题都可以用trim来解决:

[html] view plain copy
  1. <trim prefix="WHERE" prefixOverrides="AND |OR ">  ...      </trim>  
  2. <trim prefix="SET" suffixOverrides=",">  ...   </trim>  
  3. prefixOverriders、suffixOverriders分别表示前后缀的过滤  

5.4 foreach

迭代用法,一般用在in条件中。

[html] view plain copy
  1. <select id="selectPostIn" resultType="domain.blog.Post">  
  2.     SELECT * FROM POST P WHERE ID in  
  3.     <foreach item="item" index="index" collection="list" open="(" separator="," close=")">  
  4.         #{item}//会组合成(1,2,3.....)  
  5.     </foreach>  
  6. </select>  

foreach 元素是非常强大的,它允许你指定一个集合,声明集合项和索引变量,它们可 以用在元素体内。它也允许你指定开放和关闭的字符串,在迭代之间放置分隔符。这个元素 是很智能的,它不会偶然地附加多余的分隔符。