前言
pytest 運行用例的時候,一般用命令行去執行,可能是之前深受 unittest 框架的影響,習慣在項目的根目錄下寫一個 run_all.py 的文件。【使用pytest測試框架一般使用pytest.ini主文件指定運行測試用例;詳細查看:https://www.cnblogs.com/hls-code/p/14983585.html】
運行的時候,使用 python 運行 run_all.py 來執行測試用例。
pytest.main()
先看看 pytest.main() 的源碼,main 函數 的內容:
- args 傳一個list對象,list 里面是多個命令行的參數。【包括運行的測試用例(例如:test_a.py);運行測試用例的命令行參數(例如:-vs)】
- plugins 傳一個list對象,list 里面是初始化的時候需注冊的插件。
def main(args=None, plugins=None): """ return exit code, after performing an in-process test run. :arg args: list of command line arguments. :arg plugins: list of plugin objects to be auto-registered during initialization. """ from _pytest.main import EXIT_USAGEERROR try: try: config = _prepareconfig(args, plugins) except ConftestImportFailure as e: exc_info = ExceptionInfo(e.excinfo) tw = py.io.TerminalWriter(sys.stderr) tw.line( "ImportError while loading conftest '{e.path}'.".format(e=e), red=True ) exc_info.traceback = exc_info.traceback.filter(filter_traceback) exc_repr = ( exc_info.getrepr(style="short", chain=False) if exc_info.traceback else exc_info.exconly() ) formatted_tb = safe_str(exc_repr) for line in formatted_tb.splitlines(): tw.line(line.rstrip(), red=True) return 4 else: try: return config.hook.pytest_cmdline_main(config=config) finally: config._ensure_unconfigure() except UsageError as e: tw = py.io.TerminalWriter(sys.stderr) for msg in e.args: tw.line("ERROR: {}\n".format(msg), red=True) return EXIT_USAGEERROR
main() 函數如果不帶任何參數,那么執行的效果跟我們在 cmd 直接運行 pytest 命令一樣,默認運行的是當前目錄及子目錄的所有文件夾的測試用例。
run_all.py/main.py
在項目的根目錄,新建一個 run_all.py 的文件。
只需寫簡單的2行代碼:
import pytest # 默認運行的是當前目錄及子目錄的所有文件夾的測試用例 pytest.main()
這樣就能在 pycharm 里面右鍵運行,不帶參數默認運行當前目錄及子目錄的所有文件夾的測試用例。
例如:
帶參數運行
在運行的時候,也可以指定參數運行:
-s:顯示程序中的 print/logging 輸出。 -v:豐富信息模式, 輸出更詳細的用例執行信息。 -k:運行包含某個字符串的測試用例。如:pytest -k add XX.py 表示運行 XX.py 中包含 add 的測試用例。 -q:簡單輸出模式, 不輸出環境信息。 -x:出現一條測試用例失敗就退出測試。在調試階段非常有用,當測試用例失敗時,應該先調試通過,而不是繼續執行測試用例。
1、在命令行運行帶上 -s 參數: pytest -s
那么在 pytest.main() 里面等價於:
import pytest # 帶上-s參數 pytest.main(["-s"])
2、在命令行運行帶上多個參數時: pytest -s -x
那么在 pytest.main() 里面等價於:
import pytest # 帶上-s -x參數 pytest.main(["-s", "-x"])
指定運行某個用例
1、指定運行 cases/module1 文件夾下的全部用例, 在命令行運行時, 先 cd 到項目的根目錄: pytest cases/module1
那么在 pytest.main() 里面等價於:
import pytest # 運行指定文件夾目錄 pytest.main(["cases/module1"])
2、運行指定的 cases/module1/test_x1.py 下的全部用例,在命令行運行時, 先cd到項目的根目錄: pytest cases/module1/test_x1.py
那么在 pytest.main() 里面等價於:
import pytest # 運行指定py文件 pytest.main(["cases/module1/test_x1.py"])
3、運行指定的 cases/module1/test_x1.py 下的某一個用例 test_x, 在命令行運行時, 先cd到項目的根目錄: pytest cases/module1/test_x1.py::test_x
那么在 pytest.main() 里面等價於:
import pytest # 運行指定py文件下的test_x pytest.main(["cases/module1/test_x1.py::test_x"])
plugins參數的使用
一般我們寫插件的代碼放到 conftest.py 會被pytest查找到;
如果不是寫到 conftest.py 的插件內容,可以通過 plugins 參數指定加載:【默認級別相當於fixture函數中的session級別:在所有目錄以及子目錄的用例執行之前首先執行一次僅執行一次plugins指定的函數】
# run_all.py import pytest # 在run_all.py下自定義插件 class MyPlugin(object): def pytest_sessionstart(self): print("*** test run start blog地址 https://www.cnblogs.com/yoyoketang/") # plugins指定加載插件 pytest.main(["cases/module1"], plugins=[MyPlugin()])
運行后會看到在測試用例開始執行之前打印上面的內容:
*** test run start blog地址 https://www.cnblogs.com/yoyoketang/ ============================= test session starts ============================= platform win32 -- Python 3.6.6, pytest-4.5.0, py-1.9.0, pluggy-0.13.1 Test order randomisation NOT enabled. Enable with --random-order or --random-order-bucket=<bucket_type> rootdir: D:\wangyiyun\web plugins: repeat-0.8.0, rerunfailures-9.1, xdist-2.1.0 collected 5 items cases\module1\test_x1.py . [ 20%] cases\module1\test_x2.py .... [100%] ========================== 5 passed in 0.05 seconds ===========================
plugins參數的作用就是指定需加載的插件,也可以指定多個。