使用DbUnit進行資料庫操作的單元測試
1.DbUnit是junit的擴充套件,主要針對Dao層對資料庫操作的單元測試,可以在不改變資料庫原始資料的情況下,進行測試。
好了,廢話不多說了,其它內容麻煩自己去科普,直接上程式碼:
2.直接繼承 DatabaseTestCase 或 DBTestCase 進行測試,注意在專案中不建議這麼做,因為它會把測試用例插入到資料庫中並把真實資料給刪除掉(可能是我的原因,有空了再研究),這隻做入門測試使用。
執行後資料庫中的記錄://使用DBUnit進行資料庫測試,可以繼承自 DBTestCase或DatabaseTestCase(帶資料庫連結的) public class UserDaoTest extends DatabaseTestCase{ private IUserDao userDao = new UserDao(); @Override //處理資料鏈接的,如果是繼承自DBTestCase則可以不用實現此方法,資料庫的連結可以在建構函式中進行設定 protected IDatabaseConnection getConnection() throws Exception { Class driverClass = Class.forName("com.mysql.jdbc.Driver"); String url = "jdbc:mysql://localhost:3306/swh_hibernate4" ; Connection jdbcConnect = DriverManager.getConnection(url,"root", "root"); IDatabaseConnection databaseConnection = new DatabaseConnection(jdbcConnect); //也可以直接指定資料庫進行連結 // IDatabaseConnection databaseConnection = new MySqlConnection(jdbcConnect, "swh_hibernate4"); System.out.println("----->1. 進入 getConnection <----------"); return databaseConnection; } // @Override //從XML資料集中讀取資料和結構,例項化為IDataSet物件, //返回的Idataset代表資料表裡面將要存放的資料。 //該方法會在getSetUpOperation和getTearDownOperation方法執行之後分別執行一次。 //注意:在getSetUpOperation之後執行 是 填充測試資料,在getTearDownOperation之後執行是為 恢復真實資料 (這兩步操作需要自己控制) protected IDataSet getDataSet() throws Exception { System.out.println("----->3/5. 進入 getDataSet <----------"); //讀取xml檔案中的預存資料 InputStream is = new FileInputStream("src/test/resources/com/swh/user/dao/t_user.xml"); Assert.assertNotNull("dbunit的基本資料檔案不存在",is); //從2.4.7之後DBUnit就不推薦使用FlatXmlDataSet()方法了 。 // IDataSet dataSet = new FlatXmlDataSet(is); IDataSet dataSet = new FlatXmlDataSetBuilder().build(is); return dataSet; } @Override //可選的覆蓋,該方法代表執行該測試用例之前,要作的操作。預設就是CLEAN_INSERT //通過覆蓋DatabaseTestCase中的getSetUpOperation()方法來實現自己的動作 protected DatabaseOperation getSetUpOperation() throws Exception { System.out.println("----->2. 進入 getSetUpOperation <----------"); //先清空資料表裡的資料,再插入 getDataSet 返回的資料到資料表中, // DatabaseOperation.INSERT :是預設操作(也是我們常用的操作) (它首先會將目標資料庫中與我們提供的種子檔案一致的資料刪除,然後將我們提供的資料插入到資料庫中。這個實施順序保證了我們對資料庫的精確控制 ) 。 //DatabaseOperation.NONE: 不做任何事情。 //DatabaseOperation.REFRESH:通過這個操作,我們可以用種子檔案中的資料去更新目標資料庫裡的資料 //還有 DatabaseOperation.UPDATE 、 DatabaseOperation.DELETE 、 DatabaseOperation.DELETE_ALL 、 DatabaseOperation.TRUNCATE 、 CompositeOperation 、 TransactionOperation 和 IdentityInsertOperation 等幾個狀態 return DatabaseOperation.CLEAN_INSERT ; }; @Override // 可選的覆蓋,該方法代表執行完該測試,要做的操作。預設就是NONE protected DatabaseOperation getTearDownOperation() throws Exception { System.out.println("----->4. 進入 getTearDownOperation <----------"); return DatabaseOperation.NONE; } @Test public void testAdd(){ System.out.println("----->進入 testAdd <----------"); User user = new User(); user.setUsername("testAdd"); user.setPassword("456"); user.setNickname("測試4"); userDao.add(user); User user_ = userDao.loadByUserName(user.getUsername()); assertEquals("testAdd",user_.getUsername()); } @Test public void testLoadByUserName(){ System.out.println("----->進入 testLoadByUserName <----------"); User user = userDao.loadByUserName("test2"); assertEquals("測試員2", user.getNickname()); } }
3.封裝自己的DBUnit測試類或抽象測試類(使用dbunit中提供的方法),主要思路是 備份資料庫中真實資料-->清除真實資料並插入測試用例資料-->執行測試用例-->清除測試資料並恢復真實資料;另外,該類也可以繼承 DatabaseTestCase 或 DBTestCase 實現其中的方法按照上面的思路進行封裝。
/** * DBUnit Dao資料庫 測試 的抽象類, * Dao層方法的測試只需繼承此類, * 並呼叫相應的方法即可完成隔離真實資料層的資料測試 * @author * 2015.08.11 * */ public abstract class AbstractDbUnitTestCase { //資料庫連結 public static IDatabaseConnection dbunitCon ; //備份真實資料的檔案 private File tempFile ; @BeforeClass //在類執行之前執行,初始化資料庫連結 public static void init() throws DatabaseUnitException{ dbunitCon = new DatabaseConnection(DbUtil.getConnection()); } /** * 構建初始 測試 資料集 * @param tname 要構建的資料集的資料檔名 tname.xml * @return * @throws DataSetException */ protected IDataSet createDataSet(String tname) { //獲取預置資料集 InputStream is = AbstractDbUnitTestCase.class.getResourceAsStream("/com/swh/user/dao/"+tname+".xml"); Assert.assertNotNull("dbunit的基本檔案 "+tname+".xml 不存在",is); //構建資料集 IDataSet dataSet = null; try { dataSet = new FlatXmlDataSetBuilder().build(is); } catch (DataSetException e) { e.printStackTrace(); } return dataSet ; } //===========備份真實資料的公共方法==========================================================// /** * 備份資料表 * @param tname * @throws DataSetException * @throws IOException */ protected void backUpOneTable(String tname) { backUpCustomTable(new String[]{tname}); } /** * 同時備份多張表 * @param tname * @throws DataSetException * @throws IOException */ protected void backUpCustomTable(String[] tname) { try { QueryDataSet queryDataSet = new QueryDataSet(dbunitCon); for(String str : tname){ queryDataSet.addTable(str); } writeBackUpFile(queryDataSet); } catch (Exception e) { e.printStackTrace(); } } /** * 備份全部的真實資料表 * @author sangwenhao * 2015.08.10 */ protected void backUpAllTable(){ try { IDataSet dataSet = dbunitCon.createDataSet(); //儲存到物理檔案 writeBackUpFile(dataSet); } catch (Exception e) { e.printStackTrace(); } } /** * 儲存臨時檔案(資料庫中真實資料)操作 * @param dataSet * @author sangwenhao * 2015.08.11 */ protected void writeBackUpFile(IDataSet dataSet) { try { tempFile = File.createTempFile("back", "xml"); FlatXmlDataSet.write(dataSet, new FileWriter(tempFile) ); } catch (IOException e) { e.printStackTrace(); } catch (DataSetException e) { e.printStackTrace(); } } /** * 恢復資料表中的原始資料 * @author sangwenhao * 2015.08.10 */ protected void resumeTable() { try { //讀取 備份的真實資料集 IDataSet ds = new FlatXmlDataSet(new FlatXmlProducer(new InputSource(new FileInputStream(tempFile)))); //執行 插入資料 操作 DatabaseOperation.CLEAN_INSERT.execute(dbunitCon, ds); } catch (Exception e) { e.printStackTrace(); } } /** * 銷燬連結 * @author sangwenhao * 2015.08.10 */ protected void destory() { try { if(dbunitCon != null) dbunitCon.close(); } catch (Exception e) { e.printStackTrace(); } } }
測試用例的實現方法(注意:測試方法是倒著執行的):
//使用DBUnit進行資料庫測試,可以繼承自 DBTestCase或DatabaseTestCase(帶資料庫連結的) public class UserDaoTest extends DatabaseTestCase{ private IUserDao userDao = new UserDao(); @Override //處理資料鏈接的,如果是繼承自DBTestCase則可以不用實現此方法,資料庫的連結可以在建構函式中進行設定 protected IDatabaseConnection getConnection() throws Exception { Class driverClass = Class.forName("com.mysql.jdbc.Driver"); String url = "jdbc:mysql://localhost:3306/swh_hibernate4" ; Connection jdbcConnect = DriverManager.getConnection(url,"root", "root"); IDatabaseConnection databaseConnection = new DatabaseConnection(jdbcConnect); //也可以直接指定資料庫進行連結 // IDatabaseConnection databaseConnection = new MySqlConnection(jdbcConnect, "swh_hibernate4"); System.out.println("----->1. 進入 getConnection <----------"); return databaseConnection; } // @Override //從XML資料集中讀取資料和結構,例項化為IDataSet物件, //返回的Idataset代表資料表裡面將要存放的資料。 //該方法會在getSetUpOperation和getTearDownOperation方法執行之後分別執行一次。 //注意:在getSetUpOperation之後執行 是 填充測試資料,在getTearDownOperation之後執行是為 恢復真實資料 (這兩步操作需要自己控制) protected IDataSet getDataSet() throws Exception { System.out.println("----->3/5. 進入 getDataSet <----------"); //讀取xml檔案中的預存資料 InputStream is = new FileInputStream("src/test/resources/com/swh/user/dao/t_user.xml"); Assert.assertNotNull("dbunit的基本資料檔案不存在",is); //從2.4.7之後DBUnit就不推薦使用FlatXmlDataSet()方法了 。 // IDataSet dataSet = new FlatXmlDataSet(is); IDataSet dataSet = new FlatXmlDataSetBuilder().build(is); return dataSet; } @Override //可選的覆蓋,該方法代表執行該測試用例之前,要作的操作。預設就是CLEAN_INSERT //通過覆蓋DatabaseTestCase中的getSetUpOperation()方法來實現自己的動作 protected DatabaseOperation getSetUpOperation() throws Exception { System.out.println("----->2. 進入 getSetUpOperation <----------"); //先清空資料表裡的資料,再插入 getDataSet 返回的資料到資料表中, // DatabaseOperation.INSERT :是預設操作(也是我們常用的操作) (它首先會將目標資料庫中與我們提供的種子檔案一致的資料刪除,然後將我們提供的資料插入到資料庫中。這個實施順序保證了我們對資料庫的精確控制 ) 。 //DatabaseOperation.NONE: 不做任何事情。 //DatabaseOperation.REFRESH:通過這個操作,我們可以用種子檔案中的資料去更新目標資料庫裡的資料 //還有 DatabaseOperation.UPDATE 、 DatabaseOperation.DELETE 、 DatabaseOperation.DELETE_ALL 、 DatabaseOperation.TRUNCATE 、 CompositeOperation 、 TransactionOperation 和 IdentityInsertOperation 等幾個狀態 return DatabaseOperation.CLEAN_INSERT ; }; @Override // 可選的覆蓋,該方法代表執行完該測試,要做的操作。預設就是NONE protected DatabaseOperation getTearDownOperation() throws Exception { System.out.println("----->4. 進入 getTearDownOperation <----------"); return DatabaseOperation.NONE; } @Test public void testAdd(){ System.out.println("----->進入 testAdd <----------"); User user = new User(); user.setUsername("testAdd"); user.setPassword("456"); user.setNickname("測試4"); userDao.add(user); User user_ = userDao.loadByUserName(user.getUsername()); assertEquals("testAdd",user_.getUsername()); } @Test public void testLoadByUserName(){ System.out.println("----->進入 testLoadByUserName <----------"); User user = userDao.loadByUserName("test2"); assertEquals("測試員2", user.getNickname()); } }
4.xml 資料集檔案
<?xml version="1.0" encoding="UTF-8"?>
<!-- 使用DBUnit進行測試的 測試資料 -->
<dataset>
<!-- 標籤名應和資料庫中表的名稱對應;下面標籤與資料庫中表名:user對應
屬性名應和資料庫中表的欄位名稱對應。
-->
<t_user id="1" username="admin" password="123456" nickname="管理員" />
<t_user id="2" username="test2" password="123456" nickname="測試員2" />
<t_user id="3" username="test3" password="123" nickname="測試員3" />
</dataset>
不喜勿噴,有不對的地方請指出,以便及時更正。
相關推薦
使用DbUnit進行資料庫操作的單元測試
1.DbUnit是junit的擴充套件,主要針對Dao層對資料庫操作的單元測試,可以在不改變資料庫原始資料的情況下,進行測試。 好了,廢話不多說了,其它內容麻煩自己去科普,直接上程式碼: 2.直接繼承 DatabaseTestCase 或 DBTestCase 進行測試
Codeigniter 如何在自己的類中進行資料庫操作
自己寫了一個類,放在 libraries 下,但是類裡面不能使用 new mysqli()。因此,使用下面的方法來操作資料庫: 在 application/config/autoload.php 中增加: $autoload['libraries'] = array('datab
採用ADO+ACCESS進行資料庫操作
第一接觸資料庫是2年前在研究生院上課的時候,北京理工大學的一個老太太講的。不是太好!選課失敗!今天做的東西中有根資料庫相關的部分,於是便學了一下,最終決定採用ADO方式防衛ACCESS。 感謝W.C.Y, Z.W.J, W.S.F在這個過程中給與的指導和討論! (1) 動態建立資料庫 boo
python 64式: 第20式、sqlalchemy進行資料庫操作與alembic進行資料庫升級
文章目錄編排如下: 1 引言 2 使用sqlalchemy實現資料庫增刪改查 3 使用alembic進行資料庫升級 4 總結 1 引言 sqlalchemy是python專案採用的ORM(物件關係對映),主要用於資料庫相關的操作。 而alembic是與sqlalchemy搭配使用的資料庫升
框架學習(1)——service層,dao層和service實現類進行資料庫操作
最近也是比較忙,也只能忙裡偷閒地抓緊時間接著學習一下技術,自從上次學習了maven之後,越來越對框架產生了興趣,下了好多的spring視屏,聽著老師的建議,最近也萌生了看別人的程式碼進行學習的想法,然後就上了知乎搜了搜優秀的java框架,發現了一個比較感興趣的,
JAVA類獲取mybatis的mapper進行資料庫操作
- 0x00 前言 最近在做專案的專案, 有個功能是從資料庫中讀取一些引數, 專案用的是spring mvc + spring + mybatis, 也就是需要在java類中通過spring獲取mapper. - 0x01
React-如何進行元件的單元測試
什麼是單元測試 一般測試分成幾個型別:單元測試、整合測試、功能測試。整合測試和功能測試不贅述。單元測試是用來對一個模組、一個函式或者一個類來進行正確性檢驗的測試工作,這裡的單元是程式工作的最小工作單位。單元測試應該僅僅依賴輸入,不依賴多餘的環境,如果你的單元測
從零學springboot——使用jdbcTemplate的方式自定義sql進行資料庫操作
引入jdbcTemplate依賴 <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-sta
Spring Boot快速入門(五):使用MyBatis(註解形式)進行資料庫操作
新增依賴 新建專案選擇web,MyBatis,MySQL三個依賴 對於已存在的專案可以在bulid.gradle加入,spring boot將會幫你自動配置好 compile('org.springframework.boot:spring-boot-sta
描述使用Mybatis來進行資料庫操作的過程
什麼是Mybatis?維基百科是這樣定義的:Mybatis是一個Java持久化框架,它通過XML描述符或註解把物件與儲存過程或SQL語句關聯起來。通俗點說就是Mybatis是對JPA(Java持久化API,一個Java應用程式介面規範)的實現,是為了簡化資料庫操作過程而衍生出來的產品。 --
dbUtils進行資料庫操作
package cn.itcast.test; import java.sql.SQLException; import java.util.List; import java.util.Map; import org.apache.commons.dbutils.QueryRunner
Spring Boot快速入門(四):使用jpa進行資料庫操作
新增依賴 新建專案選擇web,JPA,MySQL三個依賴 對於已存在的專案可以在bulid.gradle加入,spring boot將會幫你自動配置好 compile('org.springframework.boot:spring-boot-starter
Struts2 攔截器中實現對資料進行資料庫操作
功能需求說明: 用攔截器的方式,攔截以.action結尾的類,同時記錄訪問的action名稱、action的包路徑、action後面帶的引數、操作者的ID、操作者的姓名、等其他資料。 吐槽點: 1.
Spring4託管Hibernate5並利用HibernateTemplate進行資料庫操作
時隔半年,再次釋出配置類的相關Blog,因為左手受傷原因先做一個簡述。 首先利用idea建立一個Spring+SpringMVC+Hibernate專案,注意的是因為我們要完全放棄Hibernate以及SessionFactory配置檔案,所以Hibernate不需勾選配置檔
Xshell5的簡單使用,結合Xftp 4匯入.sql檔案 進行資料庫操作
第一次寫部落格,好緊張。。。。。。 Xshell下載地址 http://rj.baidu.com/soft/detail/15201.html?ald 安裝什麼的就不用多說了吧,網上有教程,很簡單。 我也是第一次使用Xshell,弄了半天,整的有點明白了,只是初
Hibernate使用配置檔案進行資料庫操作
package com.hibtest;import net.sf.hibernate.HibernateException;import net.sf.hibernate.Session;import net.sf.hibernate.SessionFactory;import net.sf.hiberna
簡單的通過shell指令碼接收引數進行資料庫操作
建表sql語句: SET FOREIGN_KEY_CHECKS=0; -- ---------------------------- -- Table structure for `cent_su
java使用jUnit,jMockit,dbunit做DAO層單元測試方法
第一步:準備資料 先在MySQL資料庫中填寫測試資料和期望資料,然後匯出到xml檔案中。 全表匯出:DBUnitHelper.exportTable("t_dp_content_02001", TEST_DATA_FILE); 條件查詢匯出:DBUnitHelper
一個簡單的進行資料庫操作的類,呼叫內部sqlzz函式並加入sql語句即可
import pymysql #簡單封裝一個可以執行sql語句的類 class Mysql_text(object): #定義一個初始化函式用來開啟資料庫連線和建立遊標物件 def __init__(self): self.db
在eclipse中連線資料庫並進行資料庫操作時出現空指標異常類java.lang.NullPointerException
java.lang.NullPointerException載入驅動成功!連線資料庫成功!at com.dao.BookDAO.create(BookDAO.java:24)at servlets.Insert_Book_Servlet.doPost(Insert_Book_