1. 程式人生 > >四、spring集成ibatis進行項目中dao層基類封裝

四、spring集成ibatis進行項目中dao層基類封裝

access cbc seda gets cat resultset 源碼 -- 錯誤

  Apache iBatis(現已遷至Google Code下發展,更名為MyBatis)是當前IT項目中使用很廣泛的一個半自動ORM框架,區別於Hibernate之類的全自動框架,iBatis對數據庫的操作擁有更加靈活的控制,對於那些經常需要調用本地數據庫函數自定義SQL語句,或是喜歡自己優化SQL執行效率的開發者來說,iBatis是一個非常不錯的選擇。而得到廣泛應用的開源企業架構SpringFramework,也很好的將其進行了集成,使得iBatis在 SpringFramework中的使用更加便利、快捷。開發者所要做的就是繼承SpringFramework中提供的SqlMapClientDaoSupport類即可。下面將簡單介紹使用spring中集成的ibatis進行項目中dao層基類封裝,以方便開發。

1、SqlMapClientFactoryBean 的裝配

  SqlMapClientFactoryBean是SqlMapClientTemplate使用的基礎,如果在SpringFramework應用中沒有裝配SqlMapClientFactoryBean,那麽SqlMapClientTemplate將不可用,報空指針錯誤。其配置信息如下:(關於數據源、事務管理、url攔截器等更多配置請參看博文https://www.cnblogs.com/jiarui-zjb/p/8710361.html

技術分享圖片
<bean id="sqlMapClient"
    class="org.springframework.orm.ibatis.SqlMapClientFactoryBean">
    <!-- iBatis sqlmap config 文件位置 -->
    <property name="configLocation">
        <value>
            /WEB-INF/classes/org/bussiness/config/ibatis/SqlMapConfig.xml
        
</value> </property> <!-- 在SpringFramework配置文件中使用的數據源 --> <property name="dataSource"> <ref local="dataSource" /> </property> <!-- 如果需要讀寫Lob字段,需要註入在SpringFramework配置文件中配置好的Handler,這裏是Oracle的數據庫 --> <property name="lobHandler" ref="oracleLobHandler"/> </bean>
View Code

2、繼承使用SqlMapClientDaoSupport類

2.1)首先定義一個IBaseDao接口提供各種場景的查詢、修改、刪除、分頁查詢的各種抽象功能方法

技術分享圖片
package org.biframework.dao.ibatis;
import com.ibatis.common.util.PaginatedList;
import java.util.List;
import org.biframework.exception.DaoException;
public abstract interface IBaseDao
{
  public abstract Object getObject(String paramString, Object paramObject)
    throws DaoException;

  @SuppressWarnings("unchecked")
  public abstract List getList(String paramString, Object paramObject)
    throws DaoException;

  public abstract PaginatedList getPgntList(String paramString1, Object paramObject, String paramString2)
    throws DaoException;

  public abstract PaginatedList getPgntList(String paramString1, Object paramObject, String paramString2, int paramInt)
    throws DaoException;

  @SuppressWarnings("unchecked")
  public abstract List getListUseSameStmt(String paramString, Object[] paramArrayOfObject)
    throws DaoException;

  public abstract int update(String paramString, Object paramObject)
    throws DaoException;

  public abstract int transUpdateSameOpt(String paramString, Object[] paramArrayOfObject)
    throws DaoException;

  public abstract int transUpdate(Object[][] paramArrayOfObject)
    throws DaoException;
  
  @SuppressWarnings("unchecked")
  public List getList(String statementName, Object parameterObject,
            int skipResults, int maxResults) throws DaoException;
}
View Code

備註:該層也可以不寫

2.2)繼承使用SqlMapClientDaoSupport類並實現IBaseDao接口

技術分享圖片
package org.biframework.dao.ibatis;
import java.util.ArrayList;
import java.util.List;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.biframework.exception.DaoException;
import org.springframework.orm.ibatis.support.SqlMapClientDaoSupport;

import com.ibatis.common.util.PaginatedList;

public class BaseDao extends SqlMapClientDaoSupport implements IBaseDao {

    @SuppressWarnings("unused")
    private static Log log;
    protected static final int PAGE_SIZE = 15;
    @SuppressWarnings("unchecked")
    static Class class$0; /* synthetic field */

    public BaseDao() {
    }
    /*
    使用spring中集成的ibatis實現數據的查詢、修改、刪除
    1)當請求參數被封裝為一個普通對象,查詢結果為List集合:
    使用queryForList返回List 源碼方法如下:getSqlMapClientTemplate(),獲取SqlMapClientTemplate對象,
    參數說明:a、statementName sql聲明;b、parameterObject請求參數對象 queryForList方法源碼如下
    public List queryForList(String statementName, Object parameterObject)
      throws DataAccessException
      {
        executeWithListResult(new SqlMapClientCallback()
        {
          private final String val$statementName;
          private final Object val$parameterObject;
          public Object doInSqlMapClient(SqlMapExecutor executor)
            throws SQLException
          {
            return executor.queryForList(this.val$statementName, this.val$parameterObject);
          }
        });
      }
    */
    @SuppressWarnings("unchecked")
    public List getList(String statementName, Object parameterObject)
            throws DaoException {
        List list = getSqlMapClientTemplate().queryForList(statementName,
                parameterObject);
        return list;
    }
    
    /*
    2)當請求參數被封裝為一個數組對象時:
        即使用數組存放多個傳參對象(obj1、obj2...)而後使用相同sql,進行多次查詢,將多次查詢的結果list1、list2...放到結果集List中)
    使用queryForList返回List 封裝的方法如下:
    */
    @SuppressWarnings("unchecked")
    public List getListUseSameStmt(String statementName, Object objectParam[])
            throws DaoException {
        List list = null;
        List temp = null;
        if (statementName == null || objectParam == null|| objectParam.length == 0){
            return list;
        }else{
            for (int i = 0; i < objectParam.length; i++) {
                if (list == null){
                    list = new ArrayList();
                    temp = getSqlMapClientTemplate().queryForList(statementName,objectParam[i]);
                }    
                if (temp != null){
                    list.addAll(temp);
                }    
            }
        }
        return list;
    }

    /*
    3)當請求參數被封裝為一個普通對象,查詢結果為Object對象
    */
    @SuppressWarnings("unchecked")
    public Object getObject(String statementName, Object parameterObject)
            throws DaoException {
        Object result = null;
        List list = getSqlMapClientTemplate().queryForList(statementName,parameterObject);
        if (list != null && list.size() > 0){
            result = list.get(0);
        }
        return result;
    }
    
    /*
    4)ibatis-common-2.jar、使用ibatis自身封裝的PaginatedList工具類進行分頁查詢,每頁15條數據。
    public PaginatedList queryForPaginatedList(String statementName, Object parameterObject, int pageSize)
    throws DataAccessException
      {
        if (((this.sqlMapClient instanceof ExtendedSqlMapClient)) && (((ExtendedSqlMapClient)this.sqlMapClient).getDelegate().getTxManager() == null)) {
          throw new InvalidDataAccessApiUsageException("SqlMapClient needs to have DataSource to allow for lazy loading - specify SqlMapClientFactoryBean‘s ‘dataSource‘ property");
        }
        (PaginatedList)execute(new SqlMapClientCallback()
        {
          private final String val$statementName;
          private final Object val$parameterObject;
          private final int val$pageSize;
          
          public Object doInSqlMapClient(SqlMapExecutor executor)
            throws SQLException
          {
            return executor.queryForPaginatedList(this.val$statementName, this.val$parameterObject, this.val$pageSize);
          }
        });
      }
    */
    public PaginatedList getPgntList(String statementName,
            Object parameterObject, String pageDirection) throws DaoException {
        PaginatedList list = getSqlMapClientTemplate().queryForPaginatedList(
                statementName, parameterObject, 15);
        if ("next".equals(pageDirection))
            list.nextPage();
        else if ("previous".equals(pageDirection))
            list.previousPage();
        else if ("first".equals(pageDirection))
            list.isFirstPage();
        else if ("last".equals(pageDirection))
            list.isLastPage();
        return list;
    }

    /*
    4)自己指定分頁查詢的數量
    */
    public PaginatedList getPgntList(String statementName,
            Object parameterObject, String pageDirection, int pageSize)
            throws DaoException {
        PaginatedList list = getSqlMapClientTemplate().queryForPaginatedList(
                statementName, parameterObject, pageSize);
        if ("next".equals(pageDirection)) {
            System.out.println("下一頁");
            list.nextPage();
        } else if ("previous".equals(pageDirection)) {
            System.out.println("上一頁");
            list.previousPage();
        } else if ("first".equals(pageDirection)) {
            System.out.println("首頁");
            list.isFirstPage();
        } else if ("last".equals(pageDirection)) {
            System.out.println("末頁");
            list.isLastPage();
        }
        return list;
    }
    
    /*
    5)該方法暫時未理解其主要是處於何種場景使用
    */
    public int update(String statementName, Object parameterObject)
    throws DataAccessException
      {
        Integer result = (Integer)execute(new SqlMapClientCallback()
        {
          private final String val$statementName;
          private final Object val$parameterObject;
          public Object doInSqlMapClient(SqlMapExecutor executor)
            throws SQLException
          {
            return new Integer(executor.update(this.val$statementName, this.val$parameterObject));
          }
        });
        return result.intValue();
      }    
    */
    public int transUpdate(Object statementAndparameter[][])
            throws DaoException {
        Object statements[] = statementAndparameter[0];
        Object parameters[] = statementAndparameter[1];
        int result = 0;
        for (int i = 0; i < statements.length; i++) {
            String name = (String) statements[i];
            Object param = parameters[i];
            result += getSqlMapClientTemplate().update(name, param);
        }
        return result;
    }

    /*
    6)請求參數被封裝為一個數組對象,返回結果為成功更新的記錄數使用spring封裝的update方法進行更新操作
    */
    public int transUpdateSameOpt(String statementName, Object objectParam[])
            throws DaoException {
        int result = 0;
        if (statementName == null || objectParam == null
                || objectParam.length == 0)
            return result;
        for (int i = 0; i < objectParam.length; i++)
            result += getSqlMapClientTemplate().update(statementName,
                    objectParam[i]);
        return result;
    }
    /*
    7)請求參數被封裝為一個普通對象,返回結果為成功更新的記錄數
    */
    public int update(String statementName, Object parameterObject)
            throws DaoException {
        int result = getSqlMapClientTemplate().update(statementName,
                parameterObject);
        return result;
    }

    static {
        log = LogFactory.getLog(org.biframework.dao.ibatis.BaseDao.class);
    }
    
    /*
    8)請求參數被封裝為一個普通對象,並對查詢的結果記錄指定跳躍數和最大結果集
    */
    @SuppressWarnings("unchecked")
    public List getList(String statementName, Object parameterObject,
            int skipResults, int maxResults) throws DaoException {
        return getSqlMapClientTemplate().queryForList(statementName,
                parameterObject, skipResults, maxResults);
    }
}
View Code

3、進行dao層配置,並進行查詢等操作

3.1)所有的dao層都繼承BaseDao類

技術分享圖片
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.List;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.biframework.dao.ibatis.BaseDao;
import org.biframework.exception.DaoException;
import org.bussiness.product.detailquery.bo.StPolicyBean;

public class StPolicyDao extends BaseDao {
    protected static Log log = LogFactory.getLog(StPolicyDao.class);
    
    @SuppressWarnings("unchecked")
    public List getStPerm(StPBean param) throws DaoException{
        return super.getList("getShortPrem", param);
    }

    public Object getStPermCount(StPBean param) throws DaoException{
        return super.getObject("getShortPremCount", param);
    }
    }
}
View Code

3.2)進行dao裝配 detailQuery-applicationContext.xml

技術分享圖片
<bean id="nstpDao" class="org.bussiness.product.detailquery.dao.NstPolicyDao">
    <property name="dataSource">
        <ref bean="dataSource" />
    </property>
    <property name="sqlMapClient">
        <ref bean="sqlMapClient" />
    </property>
</bean>
View Code

參看博文:http://sharkl.iteye.com/blog/745615

四、spring集成ibatis進行項目中dao層基類封裝