Pytest中如何解決測試用例的依賴執行問題


需求場景:  如果A用例執行失敗, 那么B用例直接跳過不執行
遇到問題:  如果pytest默認先執行B用例,再執行A用例, 那么在使用pytest-dependency插件后, B用例永遠都不會被執行
解決思路:  pytest-ordering插件來強制指定用例執行順序; 用pytest-dependency插件設置用例依賴關系

一. 安裝pytest插件

# 改變測試用例的執行順序
pip install pytest-ordering
# 管理測試用例的依賴關系 pip install pytest
-dependency

二. pytest-ordering插件的使用

2.1 代碼示例: 

# test_1.py文件
import pytest

class Test1():
   @pytest.mark.run(order
=5) def test_1(self): pass @pytest.mark.run(order=0) def test_2(self): pass @pytest.mark.run(order=1) def test_3(self): pass @pytest.mark.run(order=-1) def test_4(self): pass @pytest.mark.run(order=-5) def test_5(self): pass def test_6(self): pass if __name__ == '__main__': pytest.main(["-v", "-s", "test_1.py"])

2.2 執行結果:  

      order為非負整數(值越小優先級越高) > 無排序裝飾器 > order為負整數(負的值越大優先級越高)

          0(test_2) > 1(test_3) > 5(test_1)   > 無(test_6)   >    -5(test_5) > -1(test_4)                                         

collected 6 items

test_1.py::Test1::test_2 PASSED
test_1.py::Test1::test_3 PASSED
test_1.py::Test1::test_1 PASSED
test_1.py::Test1::test_6 PASSED
test_1.py::Test1::test_5 PASSED
test_1.py::Test1::test_4 PASSED

============================== 6 passed in 0.04s ==============================

2.3 分析小結:

1) 排序裝飾器@pytest.mark.run(order=1)既可以裝飾函數,也可以裝飾類
2) 用例優先級: order為負整數 < 無排序裝飾器 < order為非負整數
3) order為負整數時,值越小(負的值越大),優先級越高
4) order為非負整數時,值越小, 優先級越高

三. pytest-dependency插件的使用

3.1 test_1用例 先執行, test_2用例 后執行

3.1.1 代碼示例:

# test_21
import pytest

class Test1():

    @pytest.mark.dependency(name="a")
    def test_1(self):
        assert True

    @pytest.mark.dependency(depends=['a'])   # 明確指出test_2用例依賴於test_1用例
    def test_2(self):
        assert True

if __name__ == '__main__':
    pytest.main(["-v", "-s", "test_21.py"])

3.1.2 執行結果:

test_1.py::Test1::test_1 PASSED
test_1.py::Test1::test_2 PASSED

============================== 2 passed in 0.04s ==============================

3.1.3 分析小結

1) 如果test_1用例執行失敗,則test_2用例會直接跳過執行
2) 通過name="a"來給test_1用例定義一個別名,方便其他用例來指定依賴

3.2 test_2用例 先執行, test_1用例 后執行

3.2.1 代碼示例

import pytest

class Test1():

    @pytest.mark.dependency(depends=['b'])
    def test_1(self):
        assert True

    @pytest.mark.dependency(name="b")
    def test_2(self):
        assert True

if __name__ == '__main__':
    pytest.main(["-v", "-s", "test_1.py"])

3.2.2 執行結果:

test_1.py::Test1::test_1 SKIPPED
test_1.py::Test1::test_2 PASSED

======================== 1 passed, 1 skipped in 0.05s =========================

3.2.3 問題分析:

1) pytest默認會先執行test_1用例, 然后執行test_2用例
2) 上述代碼的意圖是想讓test_2用例作為test_1用例的前置用例, 但是在pytest默認情況下,先執行了test_1用例,最后導致test_1用例跳過
3) 若想解決上述問題,需要使用pytest-ordering來指定用例的執行順序, 讓test_2先執行

3.2.4 改進代碼:

import pytest

class Test1():

    @pytest.mark.dependency(depends=['b'])
    def test_1(self):
        assert True

    @pytest.mark.run(order=0)
    @pytest.mark.dependency(name="b")
    def test_2(self):
        assert True

if __name__ == '__main__':
    pytest.main(["-v", "-s", "test_1.py"])

3.4.5 分析小結:

1) 通過@pytest.mark.run(order=0)裝飾器, 讓test_2用例優先於test_1用例執行
2) 通過@pytest.mark.dependency裝飾器來定義用例的依賴關系

3.3 跨模塊或文件來指定用例依賴

3.3.1 代碼示例:

# test_31.py文件
import pytest
@pytest.mark.run(order=-5)
@pytest.mark.dependency(depends=["test_32.py::test_32"], scope='session')
def test_31():
    assert True

# test_32.py文件
import pytest
@pytest.mark.run(order=-10)
@pytest.mark.dependency()
def test_32():
    assert True

# run.py文件
import pytest
pytest.main(["-v", "-s", "."])

3.3.2 執行結果:

test_32.py::test_32 PASSED
test_31.py::test_31 PASSED

============================== 2 passed in 0.04s ==============================

3.3.3 分析小結:

1) 被@pytest.mark.run(order=-10)修飾的用例執行優先級高於被@pytest.mark.run(order=-5)修飾的用例 2) @pytest.mark.dependency裝飾器的depends值為一個nodeid列表. e.g:形如test_32.py::test_32就是一個nodeid
3) 如果需要跨文件來指定依賴用例, 可以設置@pytest.mark.dependency的scope參數為"session"

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM