qileilove

          blog已經轉移至github,大家請訪問 http://qaseven.github.io/

          持續集成之路——數據訪問層的單元測試(續)

          在上一篇中,完成了對測試用數據源的配置。下面繼續構建可運行的測試。

            三、使用DBUnit管理數據

            測試的維護一直是我比較頭疼的問題,期望可以有一個比較易于維護和可復用的方法來管理這些數據。在沒有更好的方法之前,暫時選用DBUnit。(反思:其實我一直在為沒有發生的事情擔心,使得事情根本沒有進展。從已存在的、最簡單的地方入手,才是正確的處理方式。)

            在pom.xml中引入dbunit和springtestdbunit包,后者提供通過注解方式使用DBUnit:

          <dependency>
          <groupId>org.dbunit</groupId>
          <artifactId>dbunit</artifactId>
          <version>2.4.9</version>
          <scope>test</scope>
          </dependency>
          <dependency>
          <groupId>com.github.springtestdbunit</groupId>
          <artifactId>spring-test-dbunit</artifactId>
          <version>1.0.1</version>
          <scope>test</scope>
          </dependency>

            DBUnit使用xml文件管理數據集,通過使用第三方的庫也可以很方便的支持JSON格式。這里使用xml:

          <xml version="1.0" encoding="utf-8"?>
          <dataset>
              <building id="1" name="SOHO"/>
              <building id="2" name="New Gate Plaza"/>
              <floor id="1" floor_num="2" building="1"/>
              <floor id="2" floor_num="3" building="1"/>
              <floor id="3" floor_num="5" building="2"/>
          </dataset>

            這個數據文件放在了 /src/test/resources/中,與測試用例在同一個級別的目錄中。為了便于區分,我采用了:Dao類名-被測試的方法名-dataset.xml 的命名方式,例如:UserDao-findByname-dataxml.set。以后如果測試用例需要修改,就可以根據名字很方便地找到對應的數據集,并且不會影響其他測試用例。

            注意:

            1. 這里的Element及其Attribute名稱要和數據庫的結構一一對應,而不是實體類。

            2. 如果同一個數據對象初始化時,需要初始化的字段數目不一樣,比如:一條數據需要初始化的字段是8個,而另外一個是4個。那么一定要字段數多的放在前面。

            四、編寫測試用例

            在編寫用例前,還是看下被測試的代碼。用到的兩個實體類:

          package com.noyaxe.myapp.entity;

          import javax.persistence.Entity;
          import javax.persistence.Table;

          @Entity
          @Table(name = "building")
          public class Building extends IdEntity {
              private String name;


              public String getName() {
                  return name;
              }

              public void setName(String name) {
                  this.name = name;
              }
          }


          package com.noyaxe.myapp.entity;

          import javax.persistence.Column;
          import javax.persistence.Entity;
          import javax.persistence.JoinColumn;
          import javax.persistence.ManyToOne;
          import javax.persistence.Table;

          @Entity
          @Table(name = "floor")
          public class Floor extends IdEntity {
              private Integer floorNum;
              private Building building;

              @Column(name = "floor_num")
              public Integer getFloorNum() {
                  return floorNum;
              }

              public void setFloorNum(Integer floorNum) {
                  this.floorNum = floorNum;
              }

              @ManyToOne(optional = false)
              @JoinColumn(name = "building")
              public Building getBuilding() {
                  return building;
              }

              public void setBuilding(Building building) {
                  this.building = building;
              }
          }

            被測試的FloorDao:

          package com.noyaxe.myapp.repository;

          import com.noyaxe.myapp.entity.Floor;
          import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
          import org.springframework.data.repository.PagingAndSortingRepository;

          import java.util.List;

          public interface FloorDao extends JpaSpecificationExecutor<Floor>, PagingAndSortingRepository<Floor, Long> {
              public Floor findByBuildingNameAndFloorNum(String building, Integer floorNum);

              public List<Floor> findByBuildingName(String building);
          }



           測試用例也十分簡單:

          package com.noyaxe.myapp.repository;

          import com.github.springtestdbunit.annotation.DatabaseSetup;
          import com.noyaxe.myapp.entity.Floor;
          import org.junit.Test;
          import org.springframework.beans.factory.annotation.Autowired;
          import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
          import org.springframework.test.context.support.DependencyInjectionTestExecutionListener;
          import org.springframework.test.context.support.DirtiesContextTestExecutionListener;

          import java.util.List;

          import static junit.framework.Assert.assertNull;
          import static org.junit.Assert.assertEquals;
          import static org.junit.Assert.assertNotNull;

          @RunWith(SpringJUnit4ClassRunner.class)
          @ContextConfiguration("classpath:applicationContext-test.xml")
          @TestExecutionListeners({
          &nbsp; &nbsp; &nbsp; &nbsp; DependencyInjectionTestExecutionListener.class,
          &nbsp; &nbsp; &nbsp; &nbsp; DirtiesContextTestExecutionListener.class,
          &nbsp; &nbsp; &nbsp; &nbsp; TransactionDbUnitTestExecutionListener.class})
          public class FloorDaoTest {
              @Autowired
              private FloorDao floorDao;

              @Test
          <PRE class=java name="code">    @DatabaseSetup("FloorDao-findbByBuidlingName-dataset.xml")</PRE>    public void testFindByBuildingName(){        List<Floor> singleFloorList = floorDao.findByBuildingName("SOHO");        assertEquals(1, singleFloorList.size());        List<Floor> twoFloorList = floorDao.findByBuildingName("New Gate Plaza");        assertEquals(2, twoFloorList.size());        List<Floor> emptyFloorList = floorDao.findByBuildingName("Test");        assertEquals(0, emptyFloorList.size());    }    @Test<BR><PRE class=java name="code">    @DatabaseSetup("FloorDao-findbByBuidlingNameAndFloorNum-dataset.xml")</PRE>    public void testFindByBuildingNameAndFloorNum(){        Floor floor = floorDao.findByBuildingNameAndFloorNum("SOHO", 2);        assertNotNull(floor);        Floor empty = floorDao.findByBuildingNameAndFloorNum("New Gate Plaza", 7);        assertNull(empty);        empty = floorDao.findByBuildingNameAndFloorNum("No Building", 7);        assertNull(empty);    }}

            通過代碼,可以很清楚的看到通過DatabaseSetup完成了對測試數據的引入。這里在每個測試方法前引入不同的文件,如果所有的方法可以通過一個文件包括,那么也可以在類前面使用DatabaseSetup引入數據文件。

            至此,一個完整的數據層測試用例已經呈現,并且可以運行。可是實際的過程卻并沒有這么順利,接下來的文章就要總結一下遇到的問題。

          相關文章:

          持續集成之路——數據訪問層的單元測試

          posted on 2013-07-25 10:45 順其自然EVO 閱讀(263) 評論(0)  編輯  收藏 所屬分類: 測試學習專欄

          <2013年7月>
          30123456
          78910111213
          14151617181920
          21222324252627
          28293031123
          45678910

          導航

          統計

          常用鏈接

          留言簿(55)

          隨筆分類

          隨筆檔案

          文章分類

          文章檔案

          搜索

          最新評論

          閱讀排行榜

          評論排行榜

          主站蜘蛛池模板: 庐江县| 阳高县| 林西县| 白银市| 金华市| 凤冈县| 定襄县| 旌德县| 喜德县| 成都市| 漳浦县| 桐乡市| 宁海县| 邢台县| 屏南县| 闽侯县| 龙泉市| 鸡泽县| 库伦旗| 泾源县| 麟游县| 永城市| 扎鲁特旗| 收藏| 英山县| 新竹县| 崇州市| 大城县| 四川省| 伊宁县| 凉城县| 黄陵县| 亳州市| 德江县| 定结县| 麦盖提县| 阿拉善右旗| 富源县| 和田县| 镇雄县| 青神县|