refactor runner terminal summary and add more durations coverage
This commit is contained in:
parent
537215a16c
commit
afe28d0f32
|
@ -2,6 +2,7 @@
|
|||
import bdb
|
||||
import os
|
||||
import sys
|
||||
from operator import attrgetter
|
||||
from typing import Callable
|
||||
from typing import cast
|
||||
from typing import Dict
|
||||
|
@ -64,35 +65,43 @@ def pytest_addoption(parser: Parser) -> None:
|
|||
|
||||
|
||||
def pytest_terminal_summary(terminalreporter: "TerminalReporter") -> None:
|
||||
durations = terminalreporter.config.option.durations
|
||||
durations_min = terminalreporter.config.option.durations_min
|
||||
verbose = terminalreporter.config.getvalue("verbose")
|
||||
durations = terminalreporter.config.getoption("durations")
|
||||
if durations is None:
|
||||
return
|
||||
tr = terminalreporter
|
||||
dlist = []
|
||||
for replist in tr.stats.values():
|
||||
for rep in replist:
|
||||
if hasattr(rep, "duration"):
|
||||
dlist.append(rep)
|
||||
if not dlist:
|
||||
return
|
||||
dlist.sort(key=lambda x: x.duration, reverse=True) # type: ignore[no-any-return]
|
||||
if not durations:
|
||||
tr.write_sep("=", "slowest durations")
|
||||
else:
|
||||
tr.write_sep("=", "slowest %s durations" % durations)
|
||||
dlist = dlist[:durations]
|
||||
|
||||
for i, rep in enumerate(dlist):
|
||||
if verbose < 2 and rep.duration < durations_min:
|
||||
tr.write_line("")
|
||||
tr.write_line(
|
||||
"(%s durations < %gs hidden. Use -vv to show these durations.)"
|
||||
% (len(dlist) - i, durations_min)
|
||||
durations_min = terminalreporter.config.getoption("durations_min")
|
||||
verbose = terminalreporter.config.getvalue("verbose")
|
||||
reporter = terminalreporter
|
||||
durations_list = []
|
||||
for report_list in reporter.stats.values():
|
||||
for report in report_list:
|
||||
if hasattr(report, "duration"):
|
||||
durations_list.append(report)
|
||||
if not durations_list:
|
||||
return
|
||||
|
||||
durations_list.sort(key=attrgetter("duration"), reverse=True)
|
||||
|
||||
if not durations:
|
||||
reporter.write_sep("=", "slowest durations")
|
||||
else:
|
||||
reporter.write_sep("=", "slowest %s durations" % durations)
|
||||
durations_list = durations_list[:durations]
|
||||
|
||||
for index, test_report in enumerate(durations_list):
|
||||
if verbose < 2 and test_report.duration < durations_min:
|
||||
total = len(durations_list) - index
|
||||
pronoun, dur = (
|
||||
("this", "duration") if total == 1 else ("these", "durations")
|
||||
)
|
||||
reporter.write_line("")
|
||||
reporter.write_line(
|
||||
f"({total} {dur} slower than {durations_min:02.3f}s hidden. Use -vv to show {pronoun} {dur}.)"
|
||||
)
|
||||
break
|
||||
tr.write_line(f"{rep.duration:02.2f}s {rep.when:<8} {rep.nodeid}")
|
||||
reporter.write_line(
|
||||
f"{test_report.duration:02.2f}s {test_report.when:<8} {test_report.nodeid}"
|
||||
)
|
||||
|
||||
|
||||
def pytest_sessionstart(session: "Session") -> None:
|
||||
|
|
|
@ -867,7 +867,9 @@ class TestDurations:
|
|||
)
|
||||
|
||||
result.stdout.fnmatch_lines(
|
||||
["(8 durations < 0.005s hidden. Use -vv to show these durations.)"]
|
||||
[
|
||||
"(8 durations slower than 0.005s hidden. Use -vv to show these durations.)"
|
||||
]
|
||||
)
|
||||
|
||||
def test_calls_show_2(self, testdir, mock_timing):
|
||||
|
@ -1288,3 +1290,62 @@ def test_no_brokenpipeerror_message(pytester: Pytester) -> None:
|
|||
ret = popen.wait()
|
||||
assert popen.stderr.read() == b""
|
||||
assert ret == 1
|
||||
|
||||
|
||||
def test_multiple_durations_pluralized_tr_summary(pytester: Pytester) -> None:
|
||||
pytester.makepyfile(
|
||||
"""
|
||||
import pytest
|
||||
|
||||
def test_delays():
|
||||
assert True
|
||||
"""
|
||||
)
|
||||
result = pytester.runpytest("--durations=5", "--durations-min=10")
|
||||
assert result.ret == ExitCode.OK
|
||||
result.stdout.fnmatch_lines(
|
||||
["(3 durations slower than 10.000s hidden. Use -vv to show these durations.)"]
|
||||
)
|
||||
|
||||
|
||||
def test_single_duration_pluralized_tr_summary(pytester: Pytester) -> None:
|
||||
pytester.makepyfile(
|
||||
"""
|
||||
import pytest
|
||||
import time
|
||||
|
||||
def _sleep(delay):
|
||||
time.sleep(delay)
|
||||
|
||||
def test_one():
|
||||
_sleep(0.05)
|
||||
def test_two():
|
||||
_sleep(0.25)
|
||||
"""
|
||||
)
|
||||
result = pytester.runpytest("--durations=2", "--durations-min=0.1")
|
||||
assert result.ret == ExitCode.OK
|
||||
result.stdout.fnmatch_lines(
|
||||
["(1 duration slower than 0.100s hidden. Use -vv to show this duration.)"]
|
||||
)
|
||||
|
||||
|
||||
def test_durations_zero_lists_all(pytester: Pytester) -> None:
|
||||
pytester.makepyfile(
|
||||
"""
|
||||
import pytest
|
||||
import time
|
||||
@pytest.mark.parametrize('_', range(6))
|
||||
def test_this(_):
|
||||
time.sleep(0.1)
|
||||
"""
|
||||
)
|
||||
result = pytester.runpytest("--durations=0")
|
||||
assert result.ret == ExitCode.OK
|
||||
# Check 6x setup & 6x teardown are hidden, but 6x call are shown
|
||||
insertable_line = "*test_durations_zero_lists_all.py::test_this*{}*"
|
||||
lines = [insertable_line.format(x) for x in range(6)]
|
||||
lines.append(
|
||||
"(12 durations slower than 0.005s hidden. Use -vv to show these durations.)"
|
||||
)
|
||||
result.stdout.fnmatch_lines_random(lines)
|
||||
|
|
Loading…
Reference in New Issue