單元測試理論(續):第 2 部分

單元測試理論(續):第 2 部分

在上一篇文章中,我們開始討論 WordPress 中的單元測試理論。具體來說,我們回顧了我們在單元測試主題和插件方面的工作,然后開始討論代碼單元,這如何影響我們的測試,并且我們回顧了更大的軟件開發世界中的單元測試。

我們將繼續討論 WordPress 中的單元測試理論,但會從它如何幫助識別問題、驅動架構、記錄項目等角度進行討論。


發現問題,節省時間

回想一下本系列前面的內容,進行單元測試的傳統方法是這樣的:

  • 編寫測試,運行它(知道它會失敗)
  • 編寫函數以使該方法通過。
  • 運行測試。如果測試失敗,則繼續處理該功能;否則,轉到下一個。

是的,第一步有點教條。為什么要浪費時間去運行一些你知道會失敗的東西,對吧?不過,你明白了。但是當您開始將這種特殊技術應用于開發時,您會發現編寫代碼時會形成一定的節奏,而這是整個目標的一部分。

但這只是其中的一半——單元測試實際上可以幫助您在開發早期發現問題。

為了理解這一點,最好回顧一下這個想法。

假設您正在為基于 WordPress 的項目開發一項功能,您將允許用戶在不實際登錄 WordPress 儀表板的情況下創建用戶帳戶。這假設您已經設置了一個頁面模板來處理注冊、必要的驗證以及用于生成密碼和電子郵件的代碼。

您在瀏覽器中加載頁面,嘗試創建一些用戶 – 一些具有相同的電子郵件地址,一些具有不正確的密碼,一些具有非法字符等。您明白了 – 有多種方法驗證通過和失敗。這太粗糙了!這意味著每次更改用戶注冊功能時,您都必須執行相同的 n 次注冊,以確保不會出現任何問題。

或者您可以編寫一套測試來處理它,并在每次代碼更改時運行它們。

所以,是的,編寫單元測試可能會花費大量時間,但看看每次修改代碼單元時節省的時間。這是非常值得的,這可以幫助盡早發現問題(即在發布到生產之前),這些問題可能會因為有人忘記模擬測試的一種排列而被錯過。


自我記錄

在編寫單元測試時,您不僅可以通過確保代碼實際工作來提高代碼質量,而且本質上還可以提供面向開發人員的文檔。

如果您正在對產品中構建的功能進行單元測試,您將提供有關功能如何工作、何時應該失敗以及何時應該通過的文檔。

隨之而來的是一些假設:具體來說,您正在邏輯地命名和分組您的函數及其相關測試,并且您正在正確測試每個函數。

通過 PHPUnit,WordPress 單元測試可以輕松執行易于閱讀的斷言。您只需聲明assertTrue、assertFalse 或組成項目的函數上可用的任何其他斷言。

按照上面的示例,這意味著您可以編寫一個函數來確保用戶注冊函數在嘗試使用空電子郵件地址注冊時失敗:

 $this->assertFalse( registerNewUser( '' ) ); 

也許是一個簡單的例子,但要點仍然是:您的代碼變得自文檔化,并且只需要您編寫清晰的單元測試。


架構

也許單元測試最被低估的優勢之一是它可以幫助驅動項目的架構。通常,主題或插件開發可以通過以下兩種方式之一開始:

  1. 列出函數,繪制用戶界面,然后編寫代碼
  2. 畫出文件如何協同工作的圖表,然后編寫代碼

這些本質上并不是壞事,但我認為它們很弱(我將是第一個承認我所做的事情比我想分享的要多的人!)。但是“編寫代碼”步驟需要承擔很多責任,不是嗎?

對于任何一個長時間編寫代碼的人來說,你都太熟悉了,以至于你最終會意識到,“哦……我沒有想到這一點。”

如果你幸運的話,這通常意味著你可以編寫一個輔助方法或另一個條件來處理你忽略的情況,但在最壞的情況下,這意味著你可能必須重新設計你的整個類或整個集合解決這個問題的函數。

單元測試雖然并不完美,但可以幫助緩解這種情況。

考慮一下這樣一個事實:從一開始,您就列出了您希望主題或插件提供的所有功能。您尚未編寫任何代碼,但也許您有某種類型的 ui 草圖和/或一組類圖。

接下來,您開始編寫要編寫的測試以測試您的項目。回想一下,單元測試的一部分是將代碼分解為盡可能的原子單元,因此您的任務是為每個單元編寫單元測試,咳咳

由于單元測試的性質,您本質上會以不同的方式思考您的代碼:您正在考慮“編寫測試”,而不是“編寫代碼”,并且因為您必須在更原子的級別上進行思考,您會情不自禁地考慮經常被歸入“編寫代碼”的邊緣案例。


代碼的語言

作為開發人員,我們非常習慣使用不斷強化我們編寫代碼的約定。我的意思是,我們傾向于提供縮寫的變量名稱、神秘的函數名稱和類名稱,這些名稱對于您自己或項目團隊之外的任何人來說可能沒有任何意義。

單元測試不一定是編寫更易于閱讀的代碼的關鍵,但它可以進一步幫助提供更清晰的函數名稱。

回想一下您讀過的第一本編程書、您參加的第一堂計算機科學課或者您看到的第一段開源代碼,方法名稱通常是動詞。為什么他們不應該這樣?方法是封裝代碼的方法,做一些事情。但隨著我們在項目上工作的時間越來越長,我們變得越來越懶,我們的代碼從“register_user_and_email_password()”變成“new_account()”。

顯然,前者比后者更清晰,但如果我們致力于高質量的單元測試,并且希望確保我們的單元測試易于閱讀,為了使它們易于閱讀,我們的函數名稱必須易于閱讀。

這不是更容易閱讀嗎:

 $this->assertFalse( register_user_and_email_password( '' ) ); 

而不是這個?

 $this->assertFalse( new_account( '' ) ); 

同樣,這也許是一個簡單的示例,但原則仍然是:編寫良好的單元測試,以幫助自我記錄驅動函數語言的代碼。


結論

我們已經討論了單元測試的基礎知識以及主要優點,但是我們還沒有討論單元測試帶來的缺點,我們甚至還沒有考慮如何將其合并到我們的項目中。工作流程。

因此,在下一篇文章中,我們將嘗試做到這一點。

? 版權聲明
THE END
喜歡就支持一下吧
點贊10 分享