Skip to content

Commit be354b3

Browse files
authored
Merge pull request #7604 from bluetech/typing-disallow-any-generics
typing: set disallow_any_generics
2 parents 1e9c638 + be656dd commit be354b3

23 files changed

+123
-104
lines changed

setup.cfg

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,7 @@ formats = sdist.tgz,bdist_wheel
9696
[mypy]
9797
mypy_path = src
9898
check_untyped_defs = True
99+
disallow_any_generics = True
99100
ignore_missing_imports = True
100101
no_implicit_optional = True
101102
show_error_codes = True

src/_pytest/_code/code.py

Lines changed: 15 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -613,7 +613,7 @@ def getrepr(
613613
)
614614
return fmt.repr_excinfo(self)
615615

616-
def match(self, regexp: "Union[str, Pattern]") -> "Literal[True]":
616+
def match(self, regexp: "Union[str, Pattern[str]]") -> "Literal[True]":
617617
"""Check whether the regular expression `regexp` matches the string
618618
representation of the exception using :func:`python:re.search`.
619619
@@ -678,7 +678,7 @@ def get_source(
678678
self,
679679
source: "Source",
680680
line_index: int = -1,
681-
excinfo: Optional[ExceptionInfo] = None,
681+
excinfo: Optional[ExceptionInfo[BaseException]] = None,
682682
short: bool = False,
683683
) -> List[str]:
684684
"""Return formatted and marked up source lines."""
@@ -703,7 +703,10 @@ def get_source(
703703
return lines
704704

705705
def get_exconly(
706-
self, excinfo: ExceptionInfo, indent: int = 4, markall: bool = False
706+
self,
707+
excinfo: ExceptionInfo[BaseException],
708+
indent: int = 4,
709+
markall: bool = False,
707710
) -> List[str]:
708711
lines = []
709712
indentstr = " " * indent
@@ -743,7 +746,9 @@ def repr_locals(self, locals: Mapping[str, object]) -> Optional["ReprLocals"]:
743746
return None
744747

745748
def repr_traceback_entry(
746-
self, entry: TracebackEntry, excinfo: Optional[ExceptionInfo] = None
749+
self,
750+
entry: TracebackEntry,
751+
excinfo: Optional[ExceptionInfo[BaseException]] = None,
747752
) -> "ReprEntry":
748753
lines = [] # type: List[str]
749754
style = entry._repr_style if entry._repr_style is not None else self.style
@@ -785,7 +790,7 @@ def _makepath(self, path):
785790
path = np
786791
return path
787792

788-
def repr_traceback(self, excinfo: ExceptionInfo) -> "ReprTraceback":
793+
def repr_traceback(self, excinfo: ExceptionInfo[BaseException]) -> "ReprTraceback":
789794
traceback = excinfo.traceback
790795
if self.tbfilter:
791796
traceback = traceback.filter()
@@ -850,12 +855,14 @@ def _truncate_recursive_traceback(
850855

851856
return traceback, extraline
852857

853-
def repr_excinfo(self, excinfo: ExceptionInfo) -> "ExceptionChainRepr":
858+
def repr_excinfo(
859+
self, excinfo: ExceptionInfo[BaseException]
860+
) -> "ExceptionChainRepr":
854861
repr_chain = (
855862
[]
856863
) # type: List[Tuple[ReprTraceback, Optional[ReprFileLocation], Optional[str]]]
857-
e = excinfo.value
858-
excinfo_ = excinfo # type: Optional[ExceptionInfo]
864+
e = excinfo.value # type: Optional[BaseException]
865+
excinfo_ = excinfo # type: Optional[ExceptionInfo[BaseException]]
859866
descr = None
860867
seen = set() # type: Set[int]
861868
while e is not None and id(e) not in seen:

src/_pytest/assertion/rewrite.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -710,7 +710,7 @@ def run(self, mod: ast.Module) -> None:
710710
node = nodes.pop()
711711
for name, field in ast.iter_fields(node):
712712
if isinstance(field, list):
713-
new = [] # type: List
713+
new = [] # type: List[ast.AST]
714714
for i, child in enumerate(field):
715715
if isinstance(child, ast.Assert):
716716
# Transform assert.

src/_pytest/cacheprovider.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -181,7 +181,7 @@ def __init__(self, lfplugin: "LFPlugin") -> None:
181181
self._collected_at_least_one_failure = False
182182

183183
@pytest.hookimpl(hookwrapper=True)
184-
def pytest_make_collect_report(self, collector: nodes.Collector) -> Generator:
184+
def pytest_make_collect_report(self, collector: nodes.Collector):
185185
if isinstance(collector, Session):
186186
out = yield
187187
res = out.get_result() # type: CollectReport

src/_pytest/debugging.py

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,10 @@
33
import functools
44
import sys
55
import types
6+
from typing import Any
7+
from typing import Callable
68
from typing import Generator
9+
from typing import List
710
from typing import Tuple
811
from typing import Union
912

@@ -91,7 +94,7 @@ class pytestPDB:
9194

9295
_pluginmanager = None # type: PytestPluginManager
9396
_config = None # type: Config
94-
_saved = [] # type: list
97+
_saved = [] # type: List[Tuple[Callable[..., None], PytestPluginManager, Config]]
9598
_recursive_debug = 0
9699
_wrapped_pdb_cls = None
97100

@@ -274,7 +277,7 @@ def set_trace(cls, *args, **kwargs) -> None:
274277

275278
class PdbInvoke:
276279
def pytest_exception_interact(
277-
self, node: Node, call: "CallInfo", report: BaseReport
280+
self, node: Node, call: "CallInfo[Any]", report: BaseReport
278281
) -> None:
279282
capman = node.config.pluginmanager.getplugin("capturemanager")
280283
if capman:

src/_pytest/fixtures.py

Lines changed: 20 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -94,8 +94,8 @@
9494

9595

9696
@attr.s(frozen=True)
97-
class PseudoFixtureDef:
98-
cached_result = attr.ib(type="_FixtureCachedResult")
97+
class PseudoFixtureDef(Generic[_FixtureValue]):
98+
cached_result = attr.ib(type="_FixtureCachedResult[_FixtureValue]")
9999
scope = attr.ib(type="_Scope")
100100

101101

@@ -141,7 +141,7 @@ def provide(self):
141141
return decoratescope
142142

143143

144-
def get_scope_package(node, fixturedef: "FixtureDef"):
144+
def get_scope_package(node, fixturedef: "FixtureDef[object]"):
145145
import pytest
146146

147147
cls = pytest.Package
@@ -397,7 +397,7 @@ class FuncFixtureInfo:
397397
# definitions.
398398
initialnames = attr.ib(type=Tuple[str, ...])
399399
names_closure = attr.ib(type=List[str])
400-
name2fixturedefs = attr.ib(type=Dict[str, Sequence["FixtureDef"]])
400+
name2fixturedefs = attr.ib(type=Dict[str, Sequence["FixtureDef[Any]"]])
401401

402402
def prune_dependency_tree(self) -> None:
403403
"""Recompute names_closure from initialnames and name2fixturedefs.
@@ -441,7 +441,7 @@ def __init__(self, pyfuncitem) -> None:
441441
self.fixturename = None # type: Optional[str]
442442
#: Scope string, one of "function", "class", "module", "session".
443443
self.scope = "function" # type: _Scope
444-
self._fixture_defs = {} # type: Dict[str, FixtureDef]
444+
self._fixture_defs = {} # type: Dict[str, FixtureDef[Any]]
445445
fixtureinfo = pyfuncitem._fixtureinfo # type: FuncFixtureInfo
446446
self._arg2fixturedefs = fixtureinfo.name2fixturedefs.copy()
447447
self._arg2index = {} # type: Dict[str, int]
@@ -467,7 +467,7 @@ def node(self):
467467
"""Underlying collection node (depends on current request scope)."""
468468
return self._getscopeitem(self.scope)
469469

470-
def _getnextfixturedef(self, argname: str) -> "FixtureDef":
470+
def _getnextfixturedef(self, argname: str) -> "FixtureDef[Any]":
471471
fixturedefs = self._arg2fixturedefs.get(argname, None)
472472
if fixturedefs is None:
473473
# We arrive here because of a dynamic call to
@@ -586,7 +586,7 @@ def getfixturevalue(self, argname: str) -> Any:
586586

587587
def _get_active_fixturedef(
588588
self, argname: str
589-
) -> Union["FixtureDef", PseudoFixtureDef]:
589+
) -> Union["FixtureDef[object]", PseudoFixtureDef[object]]:
590590
try:
591591
return self._fixture_defs[argname]
592592
except KeyError:
@@ -604,9 +604,9 @@ def _get_active_fixturedef(
604604
self._fixture_defs[argname] = fixturedef
605605
return fixturedef
606606

607-
def _get_fixturestack(self) -> List["FixtureDef"]:
607+
def _get_fixturestack(self) -> List["FixtureDef[Any]"]:
608608
current = self
609-
values = [] # type: List[FixtureDef]
609+
values = [] # type: List[FixtureDef[Any]]
610610
while 1:
611611
fixturedef = getattr(current, "_fixturedef", None)
612612
if fixturedef is None:
@@ -616,7 +616,7 @@ def _get_fixturestack(self) -> List["FixtureDef"]:
616616
assert isinstance(current, SubRequest)
617617
current = current._parent_request
618618

619-
def _compute_fixture_value(self, fixturedef: "FixtureDef") -> None:
619+
def _compute_fixture_value(self, fixturedef: "FixtureDef[object]") -> None:
620620
"""Create a SubRequest based on "self" and call the execute method
621621
of the given FixtureDef object.
622622
@@ -689,7 +689,7 @@ def _compute_fixture_value(self, fixturedef: "FixtureDef") -> None:
689689
self._schedule_finalizers(fixturedef, subrequest)
690690

691691
def _schedule_finalizers(
692-
self, fixturedef: "FixtureDef", subrequest: "SubRequest"
692+
self, fixturedef: "FixtureDef[object]", subrequest: "SubRequest"
693693
) -> None:
694694
# If fixture function failed it might have registered finalizers.
695695
self.session._setupstate.addfinalizer(
@@ -751,7 +751,7 @@ def __init__(
751751
scope: "_Scope",
752752
param,
753753
param_index: int,
754-
fixturedef: "FixtureDef",
754+
fixturedef: "FixtureDef[object]",
755755
) -> None:
756756
self._parent_request = request
757757
self.fixturename = fixturedef.argname
@@ -773,7 +773,7 @@ def addfinalizer(self, finalizer: Callable[[], object]) -> None:
773773
self._fixturedef.addfinalizer(finalizer)
774774

775775
def _schedule_finalizers(
776-
self, fixturedef: "FixtureDef", subrequest: "SubRequest"
776+
self, fixturedef: "FixtureDef[object]", subrequest: "SubRequest"
777777
) -> None:
778778
# If the executing fixturedef was not explicitly requested in the argument list (via
779779
# getfixturevalue inside the fixture call) then ensure this fixture def will be finished
@@ -1456,8 +1456,8 @@ class FixtureManager:
14561456
def __init__(self, session: "Session") -> None:
14571457
self.session = session
14581458
self.config = session.config # type: Config
1459-
self._arg2fixturedefs = {} # type: Dict[str, List[FixtureDef]]
1460-
self._holderobjseen = set() # type: Set
1459+
self._arg2fixturedefs = {} # type: Dict[str, List[FixtureDef[Any]]]
1460+
self._holderobjseen = set() # type: Set[object]
14611461
self._nodeid_and_autousenames = [
14621462
("", self.config.getini("usefixtures"))
14631463
] # type: List[Tuple[str, List[str]]]
@@ -1534,7 +1534,7 @@ def _getautousenames(self, nodeid: str) -> List[str]:
15341534

15351535
def getfixtureclosure(
15361536
self, fixturenames: Tuple[str, ...], parentnode, ignore_args: Sequence[str] = ()
1537-
) -> Tuple[Tuple[str, ...], List[str], Dict[str, Sequence[FixtureDef]]]:
1537+
) -> Tuple[Tuple[str, ...], List[str], Dict[str, Sequence[FixtureDef[Any]]]]:
15381538
# Collect the closure of all fixtures, starting with the given
15391539
# fixturenames as the initial set. As we have to visit all
15401540
# factory definitions anyway, we also return an arg2fixturedefs
@@ -1557,7 +1557,7 @@ def merge(otherlist: Iterable[str]) -> None:
15571557
# need to return it as well, so save this.
15581558
initialnames = tuple(fixturenames_closure)
15591559

1560-
arg2fixturedefs = {} # type: Dict[str, Sequence[FixtureDef]]
1560+
arg2fixturedefs = {} # type: Dict[str, Sequence[FixtureDef[Any]]]
15611561
lastlen = -1
15621562
while lastlen != len(fixturenames_closure):
15631563
lastlen = len(fixturenames_closure)
@@ -1677,7 +1677,7 @@ def parsefactories(
16771677

16781678
def getfixturedefs(
16791679
self, argname: str, nodeid: str
1680-
) -> Optional[Sequence[FixtureDef]]:
1680+
) -> Optional[Sequence[FixtureDef[Any]]]:
16811681
"""Get a list of fixtures which are applicable to the given node id.
16821682
16831683
:param str argname: Name of the fixture to search for.
@@ -1691,8 +1691,8 @@ def getfixturedefs(
16911691
return tuple(self._matchfactories(fixturedefs, nodeid))
16921692

16931693
def _matchfactories(
1694-
self, fixturedefs: Iterable[FixtureDef], nodeid: str
1695-
) -> Iterator[FixtureDef]:
1694+
self, fixturedefs: Iterable[FixtureDef[Any]], nodeid: str
1695+
) -> Iterator[FixtureDef[Any]]:
16961696
from _pytest import nodes
16971697

16981698
for fixturedef in fixturedefs:

src/_pytest/hookspec.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -533,7 +533,7 @@ def pytest_report_from_serializable(
533533

534534
@hookspec(firstresult=True)
535535
def pytest_fixture_setup(
536-
fixturedef: "FixtureDef", request: "SubRequest"
536+
fixturedef: "FixtureDef[Any]", request: "SubRequest"
537537
) -> Optional[object]:
538538
"""Perform fixture setup execution.
539539
@@ -549,7 +549,7 @@ def pytest_fixture_setup(
549549

550550

551551
def pytest_fixture_post_finalizer(
552-
fixturedef: "FixtureDef", request: "SubRequest"
552+
fixturedef: "FixtureDef[Any]", request: "SubRequest"
553553
) -> None:
554554
"""Called after fixture teardown, but before the cache is cleared, so
555555
the fixture result ``fixturedef.cached_result`` is still available (not
@@ -826,7 +826,7 @@ def pytest_keyboard_interrupt(
826826

827827
def pytest_exception_interact(
828828
node: Union["Item", "Collector"],
829-
call: "CallInfo[object]",
829+
call: "CallInfo[Any]",
830830
report: Union["CollectReport", "TestReport"],
831831
) -> None:
832832
"""Called when an exception was raised which can potentially be

src/_pytest/main.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -404,7 +404,7 @@ class Failed(Exception):
404404

405405

406406
@attr.s
407-
class _bestrelpath_cache(dict):
407+
class _bestrelpath_cache(Dict[py.path.local, str]):
408408
path = attr.ib(type=py.path.local)
409409

410410
def __missing__(self, path: py.path.local) -> str:

src/_pytest/mark/structures.py

Lines changed: 11 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
from typing import Any
66
from typing import Callable
77
from typing import Iterable
8+
from typing import Iterator
89
from typing import List
910
from typing import Mapping
1011
from typing import NamedTuple
@@ -30,6 +31,8 @@
3031
if TYPE_CHECKING:
3132
from typing import Type
3233

34+
from ..nodes import Node
35+
3336

3437
EMPTY_PARAMETERSET_OPTION = "empty_parameter_set_mark"
3538

@@ -521,31 +524,32 @@ def __getattr__(self, name: str) -> MarkDecorator:
521524
MARK_GEN = MarkGenerator()
522525

523526

524-
class NodeKeywords(collections.abc.MutableMapping):
525-
def __init__(self, node):
527+
# TODO(py36): inherit from typing.MutableMapping[str, Any].
528+
class NodeKeywords(collections.abc.MutableMapping): # type: ignore[type-arg]
529+
def __init__(self, node: "Node") -> None:
526530
self.node = node
527531
self.parent = node.parent
528532
self._markers = {node.name: True}
529533

530-
def __getitem__(self, key):
534+
def __getitem__(self, key: str) -> Any:
531535
try:
532536
return self._markers[key]
533537
except KeyError:
534538
if self.parent is None:
535539
raise
536540
return self.parent.keywords[key]
537541

538-
def __setitem__(self, key, value):
542+
def __setitem__(self, key: str, value: Any) -> None:
539543
self._markers[key] = value
540544

541-
def __delitem__(self, key):
545+
def __delitem__(self, key: str) -> None:
542546
raise ValueError("cannot delete key in keywords dict")
543547

544-
def __iter__(self):
548+
def __iter__(self) -> Iterator[str]:
545549
seen = self._seen()
546550
return iter(seen)
547551

548-
def _seen(self):
552+
def _seen(self) -> Set[str]:
549553
seen = set(self._markers)
550554
if self.parent is not None:
551555
seen.update(self.parent.keywords)

0 commit comments

Comments
 (0)