pytest에서 예외가 발생한다고 올바르게 주장하는 방법은 무엇입니까?
코드:
# coding=utf-8
import pytest
def whatever():
return 9/0
def test_whatever():
try:
whatever()
except ZeroDivisionError as exc:
pytest.fail(exc, pytrace=True)
출력:
================================ test session starts =================================
platform linux2 -- Python 2.7.3 -- py-1.4.20 -- pytest-2.5.2
plugins: django, cov
collected 1 items
pytest_test.py F
====================================== FAILURES ======================================
___________________________________ test_whatever ____________________________________
def test_whatever():
try:
whatever()
except ZeroDivisionError as exc:
> pytest.fail(exc, pytrace=True)
E Failed: integer division or modulo by zero
pytest_test.py:12: Failed
============================== 1 failed in 1.16 seconds ==============================
pytest print traceback을 만드는 방법.그래서 pytest print traceback의 위치를 확인할 수 있습니다.whatever
함수에 예외가 발생했습니까?
pytest.raises(Exception)
그게 네게 필요한 거야
코드
import pytest
def test_passes():
with pytest.raises(Exception) as e_info:
x = 1 / 0
def test_passes_without_info():
with pytest.raises(Exception):
x = 1 / 0
def test_fails():
with pytest.raises(Exception) as e_info:
x = 1 / 1
def test_fails_without_info():
with pytest.raises(Exception):
x = 1 / 1
# Don't do this. Assertions are caught as exceptions.
def test_passes_but_should_not():
try:
x = 1 / 1
assert False
except Exception:
assert True
# Even if the appropriate exception is caught, it is bad style,
# because the test result is less informative
# than it would be with pytest.raises(e)
# (it just says pass or fail.)
def test_passes_but_bad_style():
try:
x = 1 / 0
assert False
except ZeroDivisionError:
assert True
def test_fails_but_bad_style():
try:
x = 1 / 1
assert False
except ZeroDivisionError:
assert True
산출량
============================================================================================= test session starts ==============================================================================================
platform linux2 -- Python 2.7.6 -- py-1.4.26 -- pytest-2.6.4
collected 7 items
test.py ..FF..F
=================================================================================================== FAILURES ===================================================================================================
__________________________________________________________________________________________________ test_fails __________________________________________________________________________________________________
def test_fails():
with pytest.raises(Exception) as e_info:
> x = 1 / 1
E Failed: DID NOT RAISE
test.py:13: Failed
___________________________________________________________________________________________ test_fails_without_info ____________________________________________________________________________________________
def test_fails_without_info():
with pytest.raises(Exception):
> x = 1 / 1
E Failed: DID NOT RAISE
test.py:17: Failed
___________________________________________________________________________________________ test_fails_but_bad_style ___________________________________________________________________________________________
def test_fails_but_bad_style():
try:
x = 1 / 1
> assert False
E assert False
test.py:43: AssertionError
====================================================================================== 3 failed, 4 passed in 0.02 seconds ======================================================================================
주의:e_info
는 예외 개체를 저장하므로 이 개체에서 세부 정보를 추출할 수 있습니다.예를 들어 예외 콜스택 또는 다른 네스트된 예외를 체크하는 경우입니다.
다음과 같은 것을 의미합니까?
def test_raises():
with pytest.raises(Exception) as exc_info:
raise Exception('some info')
# these asserts are identical; you can use either one
assert exc_info.value.args[0] == 'some info'
assert str(exc_info.value) == 'some info'
pytest는 지속적으로 진화하며 최근의 좋은 변화 중 하나로 현재 동시에 테스트 가능
- 예외 유형(예외 테스트)
- 에러 메시지(정규 표현을 사용한 체크 또는 느슨한 체크)
이 매뉴얼에서는 다음 두 가지 예를 제시하겠습니다.
with pytest.raises(ValueError, match='must be 0 or None'):
raise ValueError('value must be 0 or None')
with pytest.raises(ValueError, match=r'must be \d+$'):
raise ValueError('value must be 42')
저는 그 방법을 여러 프로젝트에서 사용해 왔고 매우 좋아합니다.
주의: ilya-rusin의 이 코멘트는 앞서 말한 접근법도 시사한다.
pytest에서 이러한 종류의 사례를 처리하는 방법은 두 가지가 있습니다.
사용.
pytest.raises
기능.사용.
pytest.mark.xfail
데코레이터
설명서에 기재되어 있는 바와 같이:
사용.
pytest.raises
자신의 코드가 의도적으로 발생하는 예외를 테스트하는 경우에는 더 나을 수 있습니다.@pytest.mark.xfail
체크 기능이 있는 경우는, 수정되지 않은 버그를 문서화하는 것(테스트에 의해서 「필요」가 설명되는 것)이나 의존 관계에 있는 버그를 문서화하는 것이 좋을지도 모릅니다.
사용방법pytest.raises
:
def whatever():
return 9/0
def test_whatever():
with pytest.raises(ZeroDivisionError):
whatever()
사용방법pytest.mark.xfail
:
@pytest.mark.xfail(raises=ZeroDivisionError)
def test_whatever():
whatever()
출력pytest.raises
:
============================= test session starts ============================
platform linux2 -- Python 2.7.10, pytest-3.2.3, py-1.4.34, pluggy-0.4.0 --
/usr/local/python_2.7_10/bin/python
cachedir: .cache
rootdir: /home/user, inifile:
collected 1 item
test_fun.py::test_whatever PASSED
======================== 1 passed in 0.01 seconds =============================
출력pytest.xfail
마커:
============================= test session starts ============================
platform linux2 -- Python 2.7.10, pytest-3.2.3, py-1.4.34, pluggy-0.4.0 --
/usr/local/python_2.7_10/bin/python
cachedir: .cache
rootdir: /home/user, inifile:
collected 1 item
test_fun.py::test_whatever xfail
======================== 1 xfailed in 0.03 seconds=============================
해 볼 수 있습니다
def test_exception():
with pytest.raises(Exception) as excinfo:
function_that_raises_exception()
assert str(excinfo.value) == 'some info'
에서는 두 가지 방법으로 예외를 처리할 수 있습니다.pytest
:
- 사용.
pytest.raises
제기된 예외에 대한 주장을 쓰다 - 사용.
@pytest.mark.xfail
1. 사용방법pytest.raises
문서에서:
발생한 예외에 대한 주장을 작성하려면 다음을 사용하여 작성할 수 있습니다.
pytest.raises
콘텍스트 매니저로서
예:
예외만을 주장하는 경우:
import pytest
def test_zero_division():
with pytest.raises(ZeroDivisionError):
1 / 0
with pytest.raises(ZeroDivisionError)
다음 코드 블록에 무엇이 있든 간에ZeroDivisionError
예외.예외가 발생하지 않으면 테스트는 실패합니다.테스트에서 다른 예외가 발생하면 실패합니다.
실제 예외 정보에 액세스할 필요가 있는 경우:
import pytest
def f():
f()
def test_recursion_depth():
with pytest.raises(RuntimeError) as excinfo:
f()
assert "maximum recursion" in str(excinfo.value)
excinfo
는 입니다.ExceptionInfo
instance: 실제로 발생한 예외를 둘러싼 래퍼입니다.주요 관심 속성은 다음과 같습니다..type
,.value
그리고..traceback
.
2. 사용방법@pytest.mark.xfail
또, 다음과 같이 지정할 수도 있습니다.raises
에 대한 의론.pytest.mark.xfail
.
import pytest
@pytest.mark.xfail(raises=IndexError)
def test_f():
l = [1, 2, 3]
l[10]
@pytest.mark.xfail(raises=IndexError)
다음 코드 블록에 무엇이 있든지 간에IndexError
. ㅇㅇㅇㅇ이면IndexError
하면 '이 올라가다'로 표시됩니다.xfailed (x)
하지 않을 는 "예외가 발생하지 않을 로 표시됩니다xpassed (X)
테스트에서 다른 예외가 발생하면 실패합니다.
주의:
「」를 사용합니다.
pytest.raises
에서는, 의 코드가 발생시키고 는, 「예외 」를 사용하는 것이 가능성이 .@pytest.mark.xfail
수정되지 않은 버그나 의존관계에 있는 버그를 문서화하는 등에는 체크 기능이 있는 것이 좋습니다.할 수 요.
match
context-manager ('pytest.raises
): 정규 표현이 예외 문자열 표현과 일치하는지 테스트합니다.(자세한 것은 이쪽)
은 바바용 right를 사용하는 것입니다.pytest.raises
하지만 나는 여기서 흥미로운 대체 방법을 발견했고, 이 질문을 나중에 독자들에게 남겨두고 싶다.
try:
thing_that_rasises_typeerror()
assert False
except TypeError:
assert True
이 솔루션을 사용하고 있습니다.
def test_date_invalidformat():
"""
Test if input incorrect data will raises ValueError exception
"""
date = "06/21/2018 00:00:00"
with pytest.raises(ValueError):
app.func(date) #my function to be tested
https://docs.pytest.org/en/latest/reference.html#pytest-raises 의 pytest 를 참조해 주세요.
특정 오류 유형을 테스트하려면 try, catch 및 raise 조합을 사용합니다.
#-- test for TypeError
try:
myList.append_number("a")
assert False
except TypeError: pass
except: assert False
여기에 제시된 상위 답변은 테스트 케이스에 대해 예외가 발생할 것으로 예상되는 경우에 유용합니다.테스트에서 예외가 발생할 수 있고 어느 시나리오에서도 우아하게 대처하고 싶은 경우에는 그다지 유용하지 않습니다.
예외가 발생할 수 있는 테스트 케이스가 있다면 이것이 더 나은 선택이라고 생각합니다.
@python.mark.parametrize("request_query, response_code", query_response_dataset)
def test_big_query_submission(request_query, response_code):
try:
stats = bigquery.Client().query(request_query)
except Exception as e:
assert False, f"Exception raised: {e}"
assert stats.errors is None
이렇게 하면 어떤 이유로든 발생한 예외로 인해 테스트를 중단하지 않고 정상적으로 불합격할 수 있습니다.
가장 좋은 방법은 끊임없이 계승되는 클래스를 사용하는 것입니다.TestCase 및 running self.assertRaises.
예를 들어 다음과 같습니다.
import unittest
def whatever():
return 9/0
class TestWhatEver(unittest.TestCase):
def test_whatever():
with self.assertRaises(ZeroDivisionError):
whatever()
그런 다음 다음을 실행하여 실행합니다.
pytest -vs test_path
난 그냥 모든 시험을 볼 때마다 갈고리를 썼을 뿐이야
훅:
@pytest.hookimpl(tryfirst=True, hookwrapper=True) def pytest_runtest_makereport(항목:항목, 호출: CallInfo):
outcome = yield # The result after the test is completed
result = outcome.get_result()
if result.when == "call":
if result.failed == True:
else:
테스트 결과로 문서를 업데이트하고 : result.longrepr.reprcrash.message를 사용하여 트레이스를 추가하는 기능이 있습니다.
이것이 최선의 방법인지는 모르겠지만 pytest만을 사용하여 트레이스 백을 인쇄하는 방법에 대한 질문에 대한 답은 됩니다.
@분명히 나는 다른 코드를 가지고 있다.
"pytrace=True"를 제거해 보셨습니까?
pytest.fail(exc, pytrace=True) # before
pytest.fail(exc) # after
'--fulltrace'로 달려본 적 있나요?
언급URL : https://stackoverflow.com/questions/23337471/how-to-properly-assert-that-an-exception-gets-raised-in-pytest
'programing' 카테고리의 다른 글
Java API는 왜 쇼트나 바이트 대신 int를 사용하는가? (0) | 2023.01.21 |
---|---|
수천 개의 SELECT 쿼리 속도 향상 (0) | 2023.01.21 |
MariaDB에서 윈도우 기능이 느립니까? (0) | 2023.01.21 |
JavaScript에 상수가 있나요? (0) | 2023.01.21 |
junit & java : 비공개 메서드 테스트 (0) | 2023.01.21 |