您的位置:軟件測(cè)試 > 開(kāi)源軟件測(cè)試 > 開(kāi)源單元測(cè)試工具 >
EasyMock使用方法與原理剖析
作者:網(wǎng)絡(luò)轉(zhuǎn)載 發(fā)布時(shí)間:[ 2013/2/21 13:32:40 ] 推薦標(biāo)簽:

下面是示例代碼中的一個(gè)接口 SalesOrder,它的實(shí)現(xiàn)類(lèi) SalesOrderImpl 的主要功能是從數(shù)據(jù)庫(kù)中讀取一個(gè) Sales Order 的 Region 和 Total Price,并根據(jù)讀取的數(shù)據(jù)計(jì)算該 Sales Order 的 Price Level(完整的實(shí)現(xiàn)代碼都可以在 src.zip 中找到):

清單2:SalesOrder 接口

               
public interface SalesOrder
{
  ……
  public void loadDataFromDB(ResultSet resultSet) throws SQLException; 
  public String getPriceLevel();
}


其實(shí)現(xiàn)類(lèi) SalesOrderImpl 中對(duì) loadDataFromDB 的實(shí)現(xiàn)如下:

清單3:SalesOrderImpl 實(shí)現(xiàn)

               
public class SalesOrderImpl implements SalesOrder
{
  ......
  public void loadDataFromDB(ResultSet resultSet) throws SQLException
  {
    orderNumber = resultSet.getString(1);
    region = resultSet.getString(2);
    totalPrice = resultSet.getDouble(3);
  }
  ......
}


方法 loadDataFromDB 讀取了 ResultSet 對(duì)象包含的數(shù)據(jù)。當(dāng)我們將之前定義的 Mock 對(duì)象調(diào)整為 Replay 狀態(tài),并將該對(duì)象作為參數(shù)傳入,那么 Mock 對(duì)象的方法將會(huì)返回預(yù)先定義的預(yù)期返回值。完整的 TestCase 如下:

清單4:完整的TestCase

               
public class SalesOrderTestCase extends TestCase {
  public void testSalesOrder() {
    IMocksControl control = EasyMock.createControl();
    ......
    ResultSet mockResultSet = control.createMock(ResultSet.class);
    try {
      ......
      mockResultSet.next();
      expectLastCall().andReturn(true).times(3);
      expectLastCall().andReturn(false).times(1);
      mockResultSet.getString(1);
      expectLastCall().andReturn("DEMO_ORDER_001").times(1);
      expectLastCall().andReturn("DEMO_ORDER_002").times(1);
      expectLastCall().andReturn("DEMO_ORDER_003").times(1);
      mockResultSet.getString(2);
      expectLastCall().andReturn("Asia Pacific").times(1);
      expectLastCall().andReturn("Europe").times(1);
      expectLastCall().andReturn("America").times(1);
      mockResultSet.getDouble(3);
      expectLastCall().andReturn(350.0).times(1);
      expectLastCall().andReturn(1350.0).times(1);
      expectLastCall().andReturn(5350.0).times(1);
      control.replay();
      ......
      int i = 0;
      String[] priceLevels = { "Level_A", "Level_C", "Level_E" };
      while (mockResultSet.next()) {
        SalesOrder order = new SalesOrderImpl();
        order.loadDataFromDB(mockResultSet);
        assertEquals(order.getPriceLevel(), priceLevels[i]);
        i++;
      }
      control.verify();
    } catch (Exception e) {
      e.printStackTrace();
    }
  }
}


在這個(gè)示例中,我們首先創(chuàng)建了 ResultSet 的 Mock 對(duì)象 moResultSet,并記錄該 Mock 對(duì)象的預(yù)期行為。之后我們調(diào)用了 control.replay(),將 Mock 對(duì)象的狀態(tài)置為 Replay 狀態(tài)。 在實(shí)際的測(cè)試階段,Sales Order 對(duì)象的 loadDataFromDB 方法調(diào)用了 mockResultSet 對(duì)象的 getString 和 getDouble 方法讀取 mockResultSet 中的數(shù)據(jù)。Sales Order 對(duì)象根據(jù)讀取的數(shù)據(jù)計(jì)算出 Price Level,并和預(yù)期輸出進(jìn)行比較。

對(duì) Mock 對(duì)象的行為進(jìn)行驗(yàn)證

在利用 Mock 對(duì)象進(jìn)行實(shí)際的測(cè)試過(guò)程之后,我們還有一件事情沒(méi)有做:對(duì) Mock 對(duì)象的方法調(diào)用的次數(shù)進(jìn)行驗(yàn)證。

為了驗(yàn)證指定的方法調(diào)用真的完成了,我們需要調(diào)用 verify 方法進(jìn)行驗(yàn)證。和 replay 方法類(lèi)似,您需要根據(jù) Mock 對(duì)象的生成方式來(lái)選用不同的驗(yàn)證方式。如果 Mock 對(duì)象是由 org.easymock.EasyMock 類(lèi)提供的 createMock 靜態(tài)方法生成的,那么我們同樣采用 EasyMock 類(lèi)的靜態(tài)方法 verify 進(jìn)行驗(yàn)證:

verify(mockResultSet);


如果Mock對(duì)象是有 IMocksControl 接口所提供的 createMock 方法生成的,那么采用該接口提供的 verify 方法,例如第1節(jié)中的 IMocksControl 實(shí)例 control:

control.verify();


將對(duì) control 實(shí)例所生成的 Mock 對(duì)象 mockConnection、mockStatement 和 mockResultSet 等進(jìn)行驗(yàn)證。如果將上例中 expectLastCall().andReturn(false).times(1) 的預(yù)期次數(shù)修改為2,在 Eclipse 中將可以看到:

圖3:Mock對(duì)象驗(yàn)證失敗

Mock 對(duì)象的重用

為了避免生成過(guò)多的 Mock 對(duì)象,EasyMock 允許對(duì)原有 Mock 對(duì)象進(jìn)行重用。要對(duì) Mock 對(duì)象重新初始化,我們可以采用 reset 方法。和 replay 和 verify 方法類(lèi)似,EasyMock 提供了兩種 reset 方式:(1)如果 Mock 對(duì)象是由 org.easymock.EasyMock 類(lèi)中的靜態(tài)方法 createMock 生成的,那么該 Mock 對(duì)象的可以用 EasyMock 類(lèi)的靜態(tài)方法 reset 重新初始化;(2)如果 Mock 方法是由 IMocksControl 實(shí)例的 createMock 方法生成的,那么該 IMocksControl 實(shí)例方法 reset 的調(diào)用將會(huì)把所有該實(shí)例創(chuàng)建的 Mock 對(duì)象重新初始化。

上一頁(yè)12345下一頁(yè)
軟件測(cè)試工具 | 聯(lián)系我們 | 投訴建議 | 誠(chéng)聘英才 | 申請(qǐng)使用列表 | 網(wǎng)站地圖
滬ICP備07036474 2003-2017 版權(quán)所有 上海澤眾軟件科技有限公司 Shanghai ZeZhong Software Co.,Ltd