2012-09-07 73 views
1

我一直在推動自己學習越來越多的單元測試技術,並且遇到了一些我無法想象的東西,即如何開始。我試圖用一種非常非常簡單的單一方法對工廠進行單元測試。我已經使用示例名稱爲您提供幫助的人簡化了它。難度單元測試帶接口的工廠

public class HandlerFactory extends SecondHandlerFactory 
{ 
    //To hold singleton of this class. 
    private static SecondHandler factoryInstance = null; 

    private HandlerFactory() throws HandlerCreationException 
    { 
      super(); 
    } 

    protected InterfaceExample createSomethingByThisKey(String key) throws HandlerCreationException 
    { 
     InterfaceExample myNewHandler = null; 

     if (StringFunctions.isEqualIgnoreCase(key, "Phone")) 
     { 
      myNewHandler = new PhoneHandler(); 
     } 
    } 
} 

我在設置這個測試甚至陷入createSomethingByKey()時遇到了很大的麻煩。即使如此,我甚至無法弄清楚如何正確地執行我的assertEquals()方法。

現在,我已經設置了一些東西來做一個createInstance();但對於我如何陷入困境似乎沒有任何意義。添加的變量和接口讓我感到困惑。測試看起來很簡單,而且是一個非常非常短的類,但沒有被暴露(Java甚至不是我的第一語言)對我來說是一道難以逾越的障礙)。

有關如何設置標準JUnit或Mockito(無所謂)如何設置所有這些的任何幫助?另外,被保護的事實讓我更加無能爲力,因爲正確的標準是在另一個軟件包中進行單元測試。

+3

我們是否真的對一家工廠進行單元測試?您應該測試工廠創建的對象。 – Jayan

+0

關於測試結構化:最好在同一個包中進行測試,以便在需要時調用包可見方法。儘管測試應該位於不同的文件夾(測試源樹)中。 – Jayan

+0

你說的對象應該被測試是正確的(我有,爲電話,電子郵件等創建了幾個處理程序),但是測試處理程序創建者本身以確保非特定鍵被丟棄並不重要嗎?例如,如果某個鍵值爲空或空值。在這個工廠中有一個無效的條件,我忽略了這個例子,但我覺得這是重要的測試,我只是不知道如何。 – notMordecai

回答

2

老實說,我不知道你有什麼困難。我只能猜測2:

  1. 你不知道在這樣的工廠測試什麼。
  2. 你有問題測試一個受保護的方法

爲1,這其實並不難,只是假設你正在測試的方法是公開的:

public class HandlerFactory extends SecondHandlerFactory 
{ 
    public InterfaceExample createSomethingByThisKey(String key) throws HandlerCreationException 
    { 
     InterfaceExample myNewHandler = null; 

     if (StringFunctions.isEqualIgnoreCase(key, "Phone")) 
     { 
      myNewHandler = new PhoneHandler(); 
     } 
    } 
} 

該方法的邏輯只需創建一個基於密鑰的處理程序實例。因此,您的測試應該根據您的密鑰來確定是否創建了正確類型的處理程序。因此,測試應該是這樣的:

@Test 
testCreateSomethingByThisKeyGivenKeyForPhoneKey { 
    InterfaceExample result = handelerFactory.createSomethingByThisKey("Phone"); 
    assertTrue("result is a PhoneHandler", result instanceof PhoneHandler); 
} 

@Test 
testCreateSomethingByThisKeyGivenKeyForUnknownKey { 
    InterfaceExample result = handelerFactory.createSomethingByThisKey("NONEXIST"); 
    assertNull("result", result); 
} 

對於問題2(限制訪問到受保護的方法),通常有2種選擇: 我們通常有測試坐在同一個包中被測系統(SUT)所以你應該能夠調用受保護的方法。

您也可以選擇創建一個特定於測試的子類(TSS),它公開一個直接委託給SUT中受保護方法的方法(或覆蓋以放寬方法的可見性),並根據TSS。當然,你應該確保你的SUT可以擴展。它可能看起來像這樣

public class Sut { 
    protected Foo methodToTest(Param param) { 
    //.... 
    } 
} 

這樣創建TSS:

​​

然後你就可以在該保護法自由測試(這是罕在Java中使用,我相信,怎麼我們可以隨時調用通過在與SUT相同的封裝下進行測試的保護方法)

+0

非常感謝。這是問題2我無法弄清楚的問題。爲了考慮「正確的指導方針」,我試圖將測試保存在不同的文件夾/軟件包中,但是這已將其清除了很多。我知道這是一個簡單的答案,但我真的不知道。謝謝! – notMordecai