譯者 | 晶顏
審校 | 重樓
摘要:Python是測試自動化的最佳編程語言之一,掌握以下7點技巧與最佳實踐可以進一步提升測試自動化的性能。
如果你曾使用過JavaScript、Node或其他編程語言執行自動化測試,便會發現使用Python進行自動化測試要容易得多。Python的易用性、高普及率及其提供的大量庫都使其成為測試自動化的最佳編程語言之一。
本人長期從事Python測試自動化項目工作,積累了一些獲取最佳測試效果的技巧。下文將分享7個技巧和最佳實踐,借助這些內容,你將能夠實現高效的Python測試自動化。
1.根據項目規格選擇合適的測試自動化框架
Python自帶測試自動化框架Unittest,但它最適合小項目。如果你期望使用一個能在小型到大型項目中均適用的測試自動化框架,那么Pytest會是更好的選擇。
Pytest提供了一種結構化且高效的方式來編寫測試用例,以實現更易于管理和可擴展的測試自動化。它還擁有最簡單的語法和最全面的插件生態系統。例如,你可以使用pytest-xdist進行并行測試執行。此外,還可以在Pytest上運行用Unittest或Nose 2編寫的測試用例。
如果你需要進行更多的機器人過程自動化(RPA)工作,那么機器人框架將是更好的選擇。該框架的語法主要采用人類語言,使用起來較為簡便。對于Web測試,你還可以將其與其他Python測試框架(如Selenium)集成。
如果你所在的團隊采用行為驅動開發(BDD)模式,那么Behave則是最好的框架。在Behave中,編寫非技術受眾可以理解的測試用例是非常容易的。
總之,建議你選擇一個與團隊使用的技術棧相匹配的框架,以避免可能出現的溝通障礙。但若你是獨立開展工作,Pytest則是最通用且最常用的框架。
2.在Selenium中使用WebDriverWait來解決計時問題
前文提及可將Pytest與Selenium集成以進行Web測試。Pytest在功能測試方面表現出色,而Selenium則將Web自動化提升到了全新高度,尤其是其強大的WebDriver庫,具備卓越的瀏覽器自動化能力。
在Selenium上運行測試時,由于系統需定位元素,必須設置一段預設的等待時間。一旦預設時間(如10秒)結束,驅動程序便會退出。然而,隱式等待存在一定問題,因為不同的元素所需的等待時間各不相同。
因此,相較于依賴隱式等待,更建議將WebDriverWait與expected_conditions結合使用,通過創建某些條件,確保在與元素進行交互之前,這些條件已得到滿足。
from selenium import Webdriver
from Selenium.Webdriver.common.by import By
from Selenium.Webdriver.support.ui import WebDriverWait
from Selenium.Webdriver.support import expected_conditions as EC
driver = Webdriver.Chrome()
driver.get("https://example.com")
# Wait for the element to be clickable
wait = WebDriverWait(driver, 10)
element = wait.until(EC.element_to_be_clickable((By.ID, "clickableElementId")))
element.click() # Perform action after the element is ready
driver.quit()
若測試頻繁失敗,并不一定意味著Web應用程序存在問題,有可能是應用程序的代碼或用戶界面發生了某些變化。為避免因測試失敗而進行過多的調試工作,務必使用唯一的ID來準確識別Web元素。
3.使用Pytest參數化測試以避免重復測試函數
Pytest的參數化測試特性在節省時間方面的作用不容小覷。在測試自動化過程中,有時需要使用不同的數據集對應用程序中的相同功能進行測試。此時,你無需重復編寫測試函數,僅需使用pytest.mark.parametrize,便可使單個測試函數使用不同的參數多次運行。示例代碼如下:
import pytest
@pytest.mark.parametrize("input, expected", [(2, 4), (3, 9), (4, 16)])
def test_square(input, expected):
assert input ** 2 == expected
如果你想了解是否可以使用Python內置的測試自動化框架運行參數化測試,那么在某些條件下,答案是肯定的。Unittest本身不支持參數化測試,但是你可以為此添加一個模塊。具體方法如下所示:
import unittest
from parameterized import parameterized
class TestMathOperations(unittest.TestCase):
@parameterized.expand([
("square of 2", 2, 4),
("square of 3", 3, 9),
("square of 4", 4, 16),
])
def test_square(self, name, input, expected):
self.assertEqual(input ** 2, expected)
4.通過并行測試加速測試執行
測試套件中的API、測試用例、數據庫和第三方系統越多,執行過程中產生的延遲就會越多,這無疑會拖慢開發速度。值得慶幸的是,有一種方法可以在不篡改測試套件的情況下解決這個問題。Python允許使用Pytest等框架進行并行測試,借助此功能,你可以使用多個CPU并行運行多個測試。
下面將展示如何使用Pytest執行并行測試:
pip install pytest-xdist
pytest -n 4 # Run tests on 4 CPUs
你還可以增加處理負載的CPU數量,但是能夠處理負載的本地基礎設施有限。如果你的CPU不足以處理你的測試套件,那么建議使用像Lambda這樣的云平臺來測試應用程序在不同瀏覽器和操作系統上的表現。
5.將測試自動化融入CI/CD管道中
請相信,如果處于快節奏的開發周期中,手動調整代碼的工作將接連不斷,每次軟件發生變更時,都得手動對代碼進行調整,幾乎沒有喘息的機會。
而將Python測試自動化整合到CI/CD管道中,就能夠在代碼發生更改時自動執行測試。如此一來,便能快速發現漏洞,并及時發布改進后的應用版本供用戶使用。
具體操作是把Python測試自動化集成至CI/CD管道里。在項目中添加 Pytest -cov ,通過Pytest命令自動執行測試并標記出任何問題。具體步驟如下:
- name: Install dependencies
run: pip install pytest pytest-cov
- name: Run tests
run: pytest --cov=my_project
如果你需要處理更大規模的測試套件,就需要向諸如Jenkins之類的CI工具添加機器人框架。對于Unittest而言,coverage功能可使測試集成到類似的管道中,示例如下:
script:
- Python -m coverage run -m unittest discover
- Python -m coverage report
6.獨立運行測試
Python測試自動化可能遇到的一個常見問題是,由于測試之間存在相互依賴關系而導致測試中斷。簡單來說,就是因為某個測試依賴于其他測試的數據或環境條件,所以一旦其中一個測試被修改,其他測試就可能會因更改引發的連鎖反應而失敗。為解決這一問題,需要將所有測試進行隔離,使每個測試在開始運行時都不與其他測試產生關聯。這樣一來,在進行調試時,就無需顧慮其對其他測試造成的連鎖影響。
以下展示如何在Pytest中運用setup和teardown邏輯來確保測試隔離:
import pytest
@pytest.fixture
def clean_environment():
# Setup: Prepare a clean state
print("Setting up a clean environment.")
yield
# Teardown: Reset environment
print("Cleaning up after the test.")
def test_example(clean_environment):
assert 2 + 2 == 4
需要注意的是,Pytest fixture會確保在每次測試后清理你使用的資源,這使得在測試執行完畢后,環境能夠恢復到初始狀態。
7.堅持最佳測試自動化實踐原則
在此著重介紹幾個提高Python測試自動化效率的最佳實踐方法:
- 在開啟測試自動化工作之前,為測試套件設定測試指標。諸如代碼覆蓋率、執行的測試用例數量、通過或失敗情況以及測試執行時間等測試指標,有助于跟蹤測試過程并確定需要解決的瓶頸問題。
- 團隊中的每位成員在很大程度上都應掌握編寫端到端(E2E)測試的方法。如此一來,質量便不再是事后才考慮的因素,而是從開發伊始就融入到整個開發過程當中。
- 避免對第三方依賴進行測試,例如那些無法掌控的外部網站或服務器鏈接。對其進行測試可能會降低測試速度,而且可能會存在cookie橫幅或其他導致測試失敗的元素。
- 使用斷言來驗證測試結果是否與預期結果匹配。
- 及時更新測試自動化工具,以便在最新的瀏覽器版本上對應用進行測試,從而在應用向公眾發布之前捕獲潛在漏洞。
結語
自動化測試工作頗具挑戰性,尤其是在面對一系列看似難以解決的錯誤時。實踐發現,采用測試金字塔模式時,測試自動化出現的錯誤相對較少。在此模式下,重點關注單元測試和集成測試,而非端到端測試。運用上述所強調的技巧和實踐方法,便能夠在CI/CD環境中高效地運行持續回歸測試,并在代碼部署前及時獲取即時反饋信息。
原文標題:7 Best Tips and Practices for Efficient Python Test Automation,作者:Pradeesh Ashokan