알고 있습니다. pytest-timeout
각 테스트 케이스에 대해 tiemout을 지정할 수 있지만 단일 실패는 전체 테스트 실행을 종료하고 대신 테스트 케이스가 느슨해집니다.pytest-timeout - 대신 전체 테스트 실행을 죽이는 테스트를 실패합니다
나는 이것에 대한 내 자신의 해결책을 강요 받았 는가, 아니면 그것을 제공 할 준비가 된 도구가 있는가?
알고 있습니다. pytest-timeout
각 테스트 케이스에 대해 tiemout을 지정할 수 있지만 단일 실패는 전체 테스트 실행을 종료하고 대신 테스트 케이스가 느슨해집니다.pytest-timeout - 대신 전체 테스트 실행을 죽이는 테스트를 실패합니다
나는 이것에 대한 내 자신의 해결책을 강요 받았 는가, 아니면 그것을 제공 할 준비가 된 도구가 있는가?
나는 오래 전에이 문제를 조사한 결과 자체 해결 된 솔루션이 더 좋을 것이라는 결론에 도달했습니다.
내 플러그인은 전체 pytest 프로세스를 종료했지만 단일 (현재) 테스트 만 쉽게 실패하도록 조정할 수 있습니다. 여기 조정 된 초안 :
당신이 kill -ALRM $pid
을
import pytest
import signal
class Termination(SystemExit):
pass
class TimeoutExit(BaseException):
pass
def _terminate(signum, frame):
raise Termination("Runner is terminated from outside.")
def _timeout(signum, frame):
raise TimeoutExit("Runner timeout is reached, runner is terminating.")
@pytest.hookimpl
def pytest_addoption(parser):
parser.addoption(
'--timeout', action='store', dest='timeout', type=int, default=None,
help="number of seconds before each test failure")
@pytest.hookimpl
def pytest_configure(config):
# Install the signal handlers that we want to process.
signal.signal(signal.SIGTERM, _terminate)
signal.signal(signal.SIGALRM, _timeout)
@pytest.hookimpl(hookwrapper=True)
def pytest_runtest_protocol(item, nextitem):
# Set the per-test timeout (an alarm signal).
if item.config.option.timeout is not None:
signal.alarm(item.config.option.timeout)
try:
# Run the setup, test body, and teardown stages.
yield
finally:
# Disable the alarm when the test passes or fails.
# I.e. when we get into the framework's body.
signal.alarm(0)
, 또는 각각의 테스트 시간이 초과 개별적으로 인해 사전 경보에, 오직 현재 테스트가 실패 할 때,하지만 다른 검사가 계속됩니다.
그리고이 TimeoutExit
은 에서 상속되기 때문에 except Exception: pass
인 라이브러리에 의해 표시되지 않습니다.
따라서이 부분은 모두 SystemExit
입니다. 그러나 SystemExit
또는 KeyboardInterruption
과 달리 pytest는이를 catch하지 않으며 이러한 예외가 발생하면 종료하지 않습니다.
time.sleep(...)
(모든 신호와 동일)이더라도 알람이 울릴 때마다 테스트가 수행되는 곳으로 예외가 주입됩니다.
프로세스 (OS 제한)에 대해 하나의 단일 알람 만 설정할 수 있음을 기억하십시오. 또한 같은 목적으로 ALRM 신호를 사용하기 때문에 pytest-timeout
과 호환되지 않습니다.
글로벌 단위로 테스트 시간 초과를 사용하려면 스마트 알람 관리자를 구현해야합니다 알람 신호가 수신됩니다. 경우
, 당신은 kill -TERM $pid
하거나 kill $pid
(우아한 종료를) 할, 그것은 즉시 종료됩니다 - 그것은 BaseException
이며 일반적으로 코드 또는 pytest에 의해 체포되지 SystemExit
, 상속 때문이다.
후자의 경우 대부분 다른 신호에 대해 다른 반응을 설정하는 방법을 보여줍니다. USR1 & USR2 및 기타 잡을 수있는 신호로 유사한 작업을 수행 할 수 있습니다. 빠른 테스트를 들면
conftest.py
파일 (의사 플러그인)에 위의 플러그인 코드를 삽입.
하면이 테스트 파일을 고려 : 시간 제한없이 pytest 실행
import time
def test_this():
try:
time.sleep(10)
except Exception:
pass
def test_that():
pass
은 아무것도하지 않으며, 두 테스트 통과 : 타임 아웃으로 실행
$ pytest -s -v
.........
collected 2 items
test_me.py::test_this PASSED
test_me.py::test_that PASSED
======= 2 passed in 10.02 seconds =======
는 첫 번째 테스트 실패,하지만 두 번째 통과 하나 :
$ pytest -s -v --timeout=5
.........
collected 2 items
test_me.py::test_this FAILED
test_me.py::test_that PASSED
============== FAILURES ==============
______________ test_this _____________
def test_this():
try:
> time.sleep(10)
test_me.py:5:
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
signum = 14, frame = <frame object at 0x106b3c428>
def _timeout(signum, frame):
> raise TimeoutExit("Runner timeout is reached, runner is terminating.")
E conftest.pytest_configure.<locals>.TimeoutExit: Runner timeout is reached, runner is terminating.
conftest.py:24: TimeoutExit
======= 1 failed, 1 passed in 5.11 seconds =======
구현 세부 정보를 너무 자세히 파고 들지는 않았지만이 경우 정말 계몽! 저는 이것을 참고 자료로 사용할 것입니다. – JCode