在这里插入图片描述

前言

在断言一些代码块或者函数时会引发意料之中的异常或者其他失败的异常导致程序无法运行时,使用raises捕获匹配到的异常可以让代码继续运行。

Python的异常处理:try...except...else...finally...,示例如下:

try:
    print("正常的操作")
except TypeError:
    print("发生TypeError异常,执行这块代码")
    raise           # 并抛出这个异常
except:
    print("发生未知异常,执行这块代码")
else:
    print("如果没有异常执行这块代码有异常发生")
finally:
    print("退出try时总会执行")

Pytest的异常处理:pytest.raises

pytest.raiseswith语句一起使用,成功断言到期望异常则测试通过,未断言到期望异常则测试失败,如下代码中, with语句范围断言到期望异常TypeError - 测试通过示例代码如下:

import pytest


def test_01():
    with pytest.raises(TypeError) as e:
        raise TypeError
    print("2+2=4")


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

----------
执行结果如下:
============================= test session starts =============================
collecting ... collected 1 item

test_a.py::test_01 PASSED                                                [100%]2+2=4


============================== 1 passed in 0.02s ==============================

如下代码中, with语句范围未断言到期望TypeError - 测试失败

import pytest


def test_02():
    with pytest.raises(TypeError) as e:
        print("4-2=2")
    print("1+2=3")

if __name__ == '__main__':
    pytest.main(["test_a.py", "-s"])
-----------------
运行结果如下:
============================= test session starts =============================
collecting ... collected 1 item

test_a.py::test_02 FAILED                                                [100%]4-2=2

test_a.py:29 (test_02)
def test_02():
        with pytest.raises(TypeError) as e:
>           print("4-2=2")
E           Failed: DID NOT RAISE <class 'TypeError'>

test_a.py:32: Failed


============================== 1 failed in 0.05s ==============================

如果我们不知道预期异常的是什么,我们可以使用match和raise进行自定义异常,如下:

import pytest
 
def exc(x):
    if x == 0:
        raise ValueError("value not 0 or None")
    return 2 / x
 
def test_raises():
    with pytest.raises(ValueError, match="value not 0 or None"):
        exc(0)
    assert eval("1 + 2") == 3
 
if __name__ == '__main__':
    pytest.main(["test_a.py", "-s"])

match还可以使用正则表达式进行匹配异常,如下:

with pytest.raises(ValueError, match=r"value not \d+$"):
    raise ValueError("value not 0")

使用assert语句进行断言

assert是Python中用于检查条件是否满足的关键字。在pytest中,assert语句是异常断言的基础。当条件不满足时,assert会引发AssertionError异常,这有助于检测程序中的错误。例如:

def test_something():
    assert 2 + 2 == 4, "计算错误"

使用try...except块捕获异常

除了asserttry...except是另一种处理异常的重要方式。在测试中,try...except可以用来捕获并处理预期的异常。例如:

def test_exception_handling():
    try:
        # 可能引发异常的代码
        result = 10 / 0
    except ZeroDivisionError:
        # 异常处理代码
        assert True, "除数不能为零"

使用pytest.raises检查异常

pytest.raises是pytest提供的一个工具,用于检查是否引发了预期的异常。它可以方便地验证函数是否抛出了特定类型的异常。例如:

import pytest

def test_exception():
    with pytest.raises(ValueError):
        raise ValueError

结合使用异常处理和断言进行测试

在实际的测试中,通常需要结合使用异常处理和断言来确保代码在异常情况下的行为符合预期。以下是一个结合使用try...exceptassert的示例:

def divide(x, y):
    try:
        result = x / y
    except ZeroDivisionError:
        return None
    return result

def test_divide_by_zero():
    assert divide(10, 0) is None, "除数不能为零时应返回None"

在这个例子中,test_divide_by_zero测试函数使用assert来验证divide函数在除数为零时是否返回了None。

总结

pytest提供了多种方法来处理异常和断言,确保代码的正确性和稳定性。通过结合使用assert语句、try...except块和pytest.raises工具,你可以更有效地测试你的Python代码,并且在出现异常时能够进行适当的处理。


霍格沃兹测试学院
44 声望27 粉丝