Mybatis入門和簡單Demo


一、Mybatis的誕生

  回顧下傳統的數據庫開發,JDBC和Hibernate是使用最普遍的技術,但這兩種ORM框架都存在一定的局限性:

  JDBC:最原生的技術,簡單易學,執行速度快,效率高,適合大數據量的操作,但存在代碼繁瑣,需要關心驅動的加載,連接的關閉等操作,對於分頁等復雜用法,需要自己手動寫代碼實現。

  Hibernate:以面向對象的方式設計和訪問,不用寫SQL,不用管底層具體數據庫的語法,但對於多表操作靈活性差,復雜的HQL難寫難理解,執行速度慢,只適合小數據量的操作。

  基於上述技術的瓶頸,誕生了一種在這兩者之間找到平衡點的ORM框架,結合它們的優點,摒棄它們的缺點,這就是myBatis,現今myBatis被廣泛的企業所采用。MyBatis 本是apache的一個開源項目iBatis, 2010年這個項目由apache software foundation 遷移到了google code,並且改名為MyBatis 。2013年11月遷移到Github。iBATIS一詞來源於“internet”和“abatis”的組合,是一個基於Java的持久層框架。iBATIS提供的持久層框架包括SQL Maps和Data Access Objects(DAO)

二、Mybatis入門Demo(基於MySQL)

  Mybatis程序的運行流程大概如下:

  (1)通過Reader對象讀取src目錄下的mybatis.xml配置文件(該文件名稱可自定義,主要用來配置數據源,類型別名以及mapper文件的總配置文件)

  (2)通過SqlSessionFactoryBuilder對象創建SqlSessionFactory對象

  (3)從當前線程,即ThreadLocal中獲取SqlSession對象
  (4)開啟事務(默認開啟)
  (5)通過SqlSession對象讀取對應Mapper.xml映射文件中的操作編號,從而讀取sql語句
  (6)提交或回滾事務
  (7)關閉SqlSession對象,並且分開當前線程與SqlSession對象,讓GC盡早回收

  基於上述步驟開始Mybatis入門Demo案例的編寫:

  步驟1.引入Mybatis所需jar包依賴

       <dependency>
            <groupId>org.mybatis</groupId>
            <artifactId>mybatis</artifactId>
            <version>3.3.0</version>
        </dependency>

        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>5.1.38</version>
        </dependency>

        <dependency>
            <groupId>org.slf4j</groupId>
            <artifactId>slf4j-api</artifactId>
            <version>1.7.12</version>
        </dependency>
        <dependency>
            <groupId>org.slf4j</groupId>
            <artifactId>slf4j-log4j12</artifactId>
            <version>1.7.12</version>
        </dependency>
        <dependency>
            <groupId>log4j</groupId>
            <artifactId>log4j</artifactId>
            <version>1.2.17</version>
        </dependency> 

  步驟2.准備數據源db.properties並配置mybatis.xml文件

mysql.driver=com.mysql.jdbc.Driver
mysql.url=jdbc:mysql://localhost:3306/aa
mysql.username=root
mysql.password=123456
<?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="db.properties">
    </properties>
    
    <!-- 設置實體類的類型別名 -->
    <typeAliases>
        <typeAlias type="com.jyk.mybatis.Student" alias="student"/>
    </typeAliases>

    <!-- 設置一個默認的連接環境信息,支持多數據源 -->
    <environments default="mysql_env">
        <!-- 連接環境信息,取一個唯一的編號 -->
        <environment id="mysql_env">
            <!-- mybatis使用的jdbc事務管理方式 -->
            <transactionManager type="jdbc">
            </transactionManager>
            
            <!-- mybatis使用連接池方式來獲取鏈接 -->
            <dataSource type="pooled">
                <!-- 配置與數據庫交互的四個屬性 -->
                <property name="driver" value="${mysql.driver}"/>
                <property name="url" value="${mysql.url}"/>
                <property name="username" value="${mysql.username}"/>
                <property name="password" value="${mysql.password}"/>
            </dataSource>
        </environment>
    </environments>
    
<mappers> <mapper resource="com/jyk/mybatis/StudentMapper.xml"/> </mappers> </configuration>

  步驟3.編寫需要操作的實體類com.jyk.mybatis.Student記錄學生信息

package com.jyk.mybatis;

public class Student {

    private String id;
    private String name;
    private String age;
    private String sex;
    
    public String getId() {
        return id;
    }
    public void setId(String id) {
        this.id = id;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public String getAge() {
        return age;
    }
    public void setAge(String age) {
        this.age = age;
    }
    public String getSex() {
        return sex;
    }
    public void setSex(String sex) {
        this.sex = sex;
    }
    
    public Student(String id, String name, String age, String sex) {
        super();
        this.id = id;
        this.name = name;
        this.age = age;
        this.sex = sex;
    }
    
    public Student() {
        super();
    }
}

  步驟4.配置StudentMapper.xml,配置namespace,需要唯一,一般以需要操作的實體類全路徑為准,也可為其他值。然后是配置實體類與實際表的映射關系resultMap,type屬性:實體全路徑名,可在mybatis.xml文件中統一配置,如在上述mybatis.xml中已配置<typeAlias type="com.jyk.mybatis.Student" alias="student"/>,則此處實體類全路徑可用student代替

  注:當實體屬性名與表字段名不一樣時,此處信息必配,若一致,則此處配置可選。

<?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">

<!-- 名稱空間namespace必須唯一 -->
<mapper namespace="studentNamespace">
    
    <!-- 
        resultMap標簽:映射實體與表,非主鍵屬性標簽
        type屬性:實體全路徑名,可在mybatis.xml文件中統一配置
        id屬性:為實體與表的映射取一個唯一的編號
     -->
    <resultMap type="student" id="studentMap">
        <!-- 
        id標簽:映射主鍵屬性
        result標簽:映射非主鍵屬性
        property屬性:實體屬性名
        column屬性:表的字段名
         -->
        <id property="id" column="id"/>
        <result property="name" column="name"/>
        <result property="age" column="age"/>
        <result property="sex" column="sex"/>
    </resultMap>
    
</mapper>

  步驟5.編寫Mybatis通用工具類,通過Reader對象讀取src目錄下的mybatis.xml配置文件,並測試連接

package com.jyk.mybatis.util;

import java.io.IOException;
import java.io.Reader;
import java.sql.Connection;

import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;

/*
 * MyBatis工具類
 */
public class MyBatisUtil {

    private static ThreadLocal<SqlSession> threadLocal = new
            ThreadLocal<SqlSession>();
    private static SqlSessionFactory sqlSessionFactory;
    
    //靜態塊加載src目錄下的mybatis配置文件
    static{
        try {
            Reader reader = Resources.getResourceAsReader("mybatis.xml");
            sqlSessionFactory = new SqlSessionFactoryBuilder().build(reader);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    
    /*
     * 禁止外界通過new方法創建
     */
    private MyBatisUtil(){}
    
    /*
     * 獲取sqlsession
     */
    public static SqlSession getSqlSession()
    {
        //從當前線程中獲取sqlSession對象
        SqlSession sqlSession = threadLocal.get();
        
        //判斷SqlSession對象是否為空
        if(sqlSession==null)
        {
            //在SqlSessionFactory對象非空的情況下,獲取SqlSession對象
            sqlSession = sqlSessionFactory.openSession();
            //將SqlSession對象與當前線程綁定在一起
            threadLocal.set(sqlSession);
        }
        
        return sqlSession;
    }
    
    /*
     * 關閉sqlsession與當前線程分開
     */
    public static void closeSqlSession()
    {
        //從當前線程中獲取SqlSession對象
        SqlSession sqlSession = threadLocal.get();
        
        if(sqlSession != null)
        {
            //關閉SqlSession對象
            sqlSession.close();
            //分開當前線程與SqlSession對象的關系,目的是盡早進行垃圾回收
            threadLocal.remove();
        }        
    }
    
    /*
     * 測試方法
     */
    public static void main(String[] args) {
        Connection conn = MyBatisUtil.getSqlSession().getConnection();
        if(conn==null)
        {
            System.out.println("連接為空");
        }
        else
        {
            System.out.println("連接不為空");
        }
    }
}

  步驟6.編寫CRUD語句,在mapper文件中編寫,此處編寫在上述已經配置好實體類映射的StudentMapper.xml文件中

<?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">

<!-- 名稱空間namespace必須唯一 -->
<mapper namespace="studentNamespace">
    
    <!-- 
        resultMap標簽:映射實體與表
        type屬性:實體全路徑名
        id屬性:為實體與表的映射取一個唯一的編號
     -->
    <resultMap type="student" id="studentMap">
        <!-- 
        id標簽:映射主鍵屬性
        result標簽:映射非主鍵屬性
        property屬性:實體屬性名
        column屬性:表的字段名
         -->
        <id property="id" column="id"/>
        <result property="name" column="name"/>
        <result property="age" column="age"/>
        <result property="sex" column="sex"/>
    </resultMap>
    
    <!-- 
    insert標簽:sql插入語句
    id屬性:該sql語句的唯一標簽
    parameterType:要執行的dao中的方法的參數,如果是類的話,必須使用全路徑名
    #{xx}:mybatis特有語法,用來替代jdbc中的?占位符
     -->
    <insert id="add1">
    insert into student(id,name,age,sex) values("1","admin","22","男")
    </insert>
    
    <insert id="add2" parameterType="student">
    insert into student(id,name,age,sex) values(#{id},#{name},#{age},#{sex})
    </insert>
    
    <!-- <insert id="add3" parameterType="student">
    insert into student(id,name,age,sex) values(#{id},#{name},#{age},#{sex})
    </insert> -->
</mapper>

  步驟7.編寫DAO,利用上述配置完成的文件和寫好的通用工具類MyBatisUtil對學生信息進行增刪該查

package com.jyk.mybatis;

import org.apache.ibatis.session.SqlSession;

import com.jyk.mybatis.util.MyBatisUtil;

public class StudentDao {

    /*
     * 增加的方法1
     */
    public void add1()
    {
        SqlSession sqlSession = null;
        try{
            sqlSession = MyBatisUtil.getSqlSession();
            //事務開始(默認)
            
            //讀取StudentMapper.xml配置文件中的sql語句,對應的sql語句由{名稱空間.sql的id指定}
            int i = sqlSession.insert("studentNamespace.add1");
            System.out.println("本次操作影響了"+i+"行數據");
            
            //事務提交
            sqlSession.commit();
        }catch(Exception e){
            e.printStackTrace();
            //事務回滾
            sqlSession.rollback();
            throw e;
        }finally{
            MyBatisUtil.closeSqlSession();
        }
    }
    
    /*
     * 增加的方法2
     */
    public void add2(Student stu)
    {
        SqlSession sqlSession = null;
        try{
            sqlSession = MyBatisUtil.getSqlSession();
            //事務開始(默認)
            
            //讀取StudentMapper.xml配置文件中的sql語句
            int i = sqlSession.insert("studentNamespace.add2",stu);
            System.out.println("本次操作影響了"+i+"行數據");
            
            //事務提交
            sqlSession.commit();
        }catch(Exception e){
            e.printStackTrace();
            //事務回滾
            sqlSession.rollback();
            throw e;
        }finally{
            MyBatisUtil.closeSqlSession();
        }
    }
    
    /*
     * 增加的方法3
     * 往數據庫添加記錄必須要添加事務,沒有事務添加不進去
     */
    public void add3(Student stu)
    {
        SqlSession sqlSession = null;
        try{
            sqlSession = MyBatisUtil.getSqlSession();
            //事務開始(默認)
            
            //讀取StudentMapper.xml配置文件中的sql語句
            int i = sqlSession.insert("studentNamespace.add3",stu);
            System.out.println("本次操作影響了"+i+"行數據");
            sqlSession.commit();
        }catch(Exception e){
            e.printStackTrace();
            //事務回滾
            sqlSession.rollback();
            throw e;
        }finally{
            MyBatisUtil.closeSqlSession();
        }
    }
    
    public static void main(String[] args) {
        StudentDao sd = new StudentDao();
        sd.add1();
        sd.add2(new Student("64","kaiye","23","男"));
    }
}


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM