generator-return-from-iter-method (PYI058)#
Derived from the flake8-pyi linter.
Fix is sometimes available.
What it does#
Checks for simple __iter__ methods that return Generator, and for
simple __aiter__ methods that return AsyncGenerator.
Why is this bad?#
Using (Async)Iterator for these methods is simpler and more elegant. More
importantly, it also reflects the fact that the precise kind of iterator
returned from an __iter__ method is usually an implementation detail that
could change at any time. Type annotations help define a contract for a
function; implementation details should not leak into that contract.
For example:
from collections.abc import AsyncGenerator, Generator
from typing import Any
class CustomIterator:
def __iter__(self) -> Generator:
yield from range(42)
class CustomIterator2:
def __iter__(self) -> Generator[str, Any, None]:
yield from "abcdefg"
Use instead:
from collections.abc import Iterator
class CustomIterator:
def __iter__(self) -> Iterator:
yield from range(42)
class CustomIterator2:
def __iter__(self) -> Iterator[str]:
yield from "abdefg"
Fix safety#
This rule tries hard to avoid false-positive errors, and the rule's fix
should always be safe for .pyi stub files. However, there is a slightly
higher chance that a false positive might be emitted by this rule when
applied to runtime Python (.py files). As such, the fix is marked as
unsafe for any __iter__ or __aiter__ method in a .py file that has
more than two statements (including docstrings) in its body.