摘要:在世界級的安卓測試開發流第一部分,作者開始了安卓測試開發流的討論。這個測試用例的測試對象是,部分指令集僅涉及執行的指令和。測試的粒度則應當和測試范圍相當。一旦我們能夠測試產品需求是否正確實現,我們必須繼續測試開發流。
在「世界級的安卓測試開發流?—?第一部分」,作者開始了安卓測試開發流的討論。我們探討了一個軟件工程師開始編寫測試,到發現測試開發中的相關問題的不斷變化。 最后,得到了以下結論:
測試自動化對于軟件開發的成功是至關重要的
可測試性代碼對編寫某些特定類型的測試是必須的
有些開發者在不確定測試內容和測試方法的情況下,就開始編寫測試
測試的質量和可靠度通常達不到我們的期望
一個測試開發流對于定義測試內容和方法是必要的
因此,任何應用程序中測試的關鍵部分是:
業務邏輯的測試要獨立于框架或庫
測試服務器端的API集成
從用戶的角度,使用黑盒測試驗收標準
在本文中,我們將探討涉及這幾個部分的幾種測試方案,以確保一個穩固的測試開發流。
業務邏輯的測試要獨立于框架或庫:首先,檢查業務邏輯是不是真的實現預定的產品需求,是必不可少的。我們需要將想要測試的代碼隔離出來,然后模擬出不同的初始場景,以配置某些組件在運行時的行為。然后,我們選擇想要執行的代碼部分進行測試。之后,我們需要在執行完測試對象后檢查軟件的狀態是否正確。
這個測試方案的關鍵在于依賴反轉原則。通過編寫只依賴于抽象的代碼,我們就可以把軟件分離成不同的層級。為了獲得依賴的實例,我們只需要向某個對象發出請求。 或者,一旦實例生成,我們也能獲得之。 我們的軟件有很多部分需要創建代碼來獲得合作者的實例。這時,我們會使用測試替身來模擬初始場景,或編寫不同的行為程序來設計我們的測試。通過使用測試替身,我們能同時模擬產品代碼的行為和狀態。 同時,它幫助我們選擇測試的范圍,也即需要測試的代碼量。沒有依賴反轉,所有的類需要獨自獲取自己的依賴。結果會導致類實現和依賴實現相耦合,這樣就沒有辦法借用測試替身來切割產品代碼的執行流程。
通常,在構造時傳遞類依賴是使用依賴反轉的最有效機制。這個機制對采用測試替身已經足夠。在構造時傳遞類依賴將幫助我們創建相應的測試替身來替換依賴的實例。要謹記,使用服務定位器或依賴反轉框架將有助于減少在應用依賴反轉時所需要的樣板, 雖然這并不是強制的。
我們將用一個具體例子(該測試和筆者幾個月前開始開發的 Android GameBoy 模擬器有關)來演示如何測試我們的業務需求。
以下測試是關于 GameBoy 內存管理單元(MMU)和 GameBoy BIOS 執行單元的。 我們將檢查產品需求(硬件模擬)是否正確實現。
public class MMUTest { private static final int MMU_SIZE = 65536; private static final int ANY_ADDRESS = 11; private static final byte ANY_BYTE_VALUE = 0x11; @Test public void shouldInitializeMMUFullOfZeros() { MMU mmu = givenAMMU(); assertMMUIsFullOfZeros(mmu); } @Test public void shouldFillMMUWithZerosOnReset() { MMU mmu = givenAMMU(); mmu.writeByte(ANY_ADDRESS, ANY_BYTE_VALUE); mmu.reset(); assertMMUIsFullOfZeros(mmu); } @Test public void shouldWriteBigBytesValuesAndRecoverThemAsOneWord() { MMU mmu = givenAMMU(); mmu.writeByte(ANY_ADDRESS, (byte) 0xFA); mmu.writeByte(ANY_ADDRESS +1, (byte) 0xFB); assertEquals(0xFBFA, mmu.readWord(ANY_ADDRESS)); } }
前三個測試是檢查 GameBoy 的 MMU 實現是否正確。 成功的關鍵是總在測試執行完成后,檢查 MMU 的狀態是否正確。 所有測試都會檢查 MMU 是否正確初始化。如果重置后MMU 是整潔的,寫入2個字節后讀出的是一個字符,那么最終讀取就是正確的。為了測試模擬器軟件的這個部分,我們將測試范圍縮小為一個類。
public class GameBoyBIOSExecutionTest { @Test public void shouldIndicateTheBIOSHasBeenLoadedUnlockingTheRomMapping() { GameBoy gameBoy = givenAGameBoy(); tickUntilBIOSLoaded(gameBoy); assertEquals(1, mmu.readByte(UNLOCK_ROM_ADDRESS) & 0xFF); } @Test public void shouldPutTheNintendoLogoIntoMemoryDuringTheBIOSThirdStage() { GameBoy gameBoy = givenAGameBoy(); tickUntilThirdStageFinished(gameBoy); assertNintendoLogoIsInVRAM(); } private GameBoy givenAGameBoy() { z80 = new GBZ80(); mmu = new MMU(); gpu = new GPU(mmu); GameLoader gameLoader = new GameLoader(new FakeGameReader()); GameBoy gameBoy = new Gameboy(z80, mmu, gpu, gameLoader); return gameboy; } }
在這兩個測試中,我們檢查 BIOS 是否在不同階段都正確執行。BIOS執行結束后,在具體內存位置的一個字節必須被初始化為一個具體的值。然后,在第三階段的最后,任天堂的logo必須已經加載到 VRAM。由于全套的BIOS執行是任何模擬器開發的關鍵部分,我們決定采用更大的測試范圍。這個測試用例的測試對象是 CPU,部分 CPU 指令集(僅涉及 BIOS執行的指令)和 MMU。 要檢查執行的狀態是否正確,我們必須對 MMU的狀態使用斷言(assert)。要想顯著的提升測試質量,一個關鍵就是檢查軟件執行后的最終狀態,同時避免驗證和其他組件之間的交互。因為即使和其他組件之間的交互都是正確的,最終狀態依然可能是錯的。還要明確,這些測試的某些部分同樣可以獨立進行,如 CPU指令。
這些測試的另一個主要亮點是使用測試替身來模擬和 Android SDK 相關的部分代碼。在執行 BIOS 前,GameBoy 游戲必須加載進 GameBoy 的 MMU。然而,在測試期間,沒有 Android SDK 可用,因而就不得不將其替換,轉而從測試環境中加載 GameBoy的 rom。我們使用依賴反轉原則不僅用于隱藏實現細節,或者定義邊界,還用測試替身 FakeGameReader 來替代 AndroidGameReader 的產品代碼,這意味著完全不依賴框架和庫進行代碼測試。通過這樣做,我們創建了隔離的測試環境,同時調整了測試范圍。
范圍:調整測試的范圍是非常重要的。 開始編寫測試前,我們應當牢記測試范圍可以幫助識別代碼錯誤(取決于測試的規模)。縮小測試規模能帶給我們更豐富的錯誤反饋,而放大規模的測試則不能提供錯誤位置的精確信息。測試的粒度則應當和測試范圍相當。
基礎設施:編寫這些測試的基礎設施相當明了。 我們必須在依賴反轉原則下編寫可測試代碼,并結合使用一個測試框架和一個模擬庫。 模擬庫用來生成模擬場景中需要的測試替身,或者用于替代部分產品代碼的測試替身。請注意,這些框架和庫不是強制使用的,但是非常推薦。
結果:這個方案的結果很有趣。 當遵循依賴反轉原則時,我們能獨立于框架和庫測試我們產品代碼中的業務邏輯。通過可重復的,易于編寫和設計的測試,我們可以創建隔離的測試環境。此外,我們能夠方便選擇要測試的產品代碼數量,并使用測試替身代替這部分代碼,來模擬行為和不同的場景。
一旦我們能夠測試產品需求是否正確實現,我們必須繼續測試開發流。接下來要測試的,就是在前一階段使用測試替身替換的外部組件集成后是否執行正確。我們將在下一篇博文中討論,敬請期待!
原文地址:http://blog.karumi.com/world-class-testing-development-pipeline-for-android-part-2/
OneAPM Mobile Insight ,監控網絡請求及網絡錯誤,提升用戶留存。訪問 OneAPM 官方網站感受更多應用性能優化體驗,想閱讀更多技術文章,請訪問 OneAPM 官方技術博客。
本文轉自 OneAPM 官方博客
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/8709.html
摘要:不過細想想,我郵只有前端的選修課啥的,課程也不是那么就業導向。至少目前,很少有大公司完全把作為前后端通用的技術棧。不能把簡單看做是在服務端的延展。編譯這個思想在前端領域很重要不改變現有的語言環境同時進行最佳的工程實踐。 P.S. 噴神請繞道,大神勿噴,不引戰,不攻擊,不鉆牛角尖。 大二時第一次接觸前端。許多同學估計都想過要做一個網站,大部分又是從PHP開始的(誰讓它是世界上最好的語言呢...
閱讀 1963·2021-10-25 09:48
閱讀 2780·2021-09-22 14:59
閱讀 1755·2019-08-29 16:52
閱讀 854·2019-08-29 16:07
閱讀 2297·2019-08-29 12:38
閱讀 1751·2019-08-26 13:23
閱讀 875·2019-08-26 11:49
閱讀 3264·2019-08-26 10:56