Narrow `Generator[T, None, None] types to Iterator[T]` (#12241)

This commit is contained in:
Adam Turner 2024-04-09 03:26:44 +01:00 committed by GitHub
parent 413e740dca
commit 3421e5382a
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
20 changed files with 61 additions and 54 deletions

View File

@ -27,7 +27,7 @@ from sphinx.util.template import SphinxRenderer
if TYPE_CHECKING:
import os
from collections.abc import Generator, Iterable
from collections.abc import Iterable, Iterator
from docutils.nodes import Element
@ -69,7 +69,7 @@ class Catalog:
line = -1
self.metadata[msg].append((origin.source, line, origin.uid)) # type: ignore[arg-type]
def __iter__(self) -> Generator[Message, None, None]:
def __iter__(self) -> Iterator[Message]:
for message in self.messages:
positions = sorted({(source, line) for source, line, uuid
in self.metadata[message]})

View File

@ -29,7 +29,7 @@ from sphinx.util.http_date import rfc1123_to_epoch
from sphinx.util.nodes import get_node_line
if TYPE_CHECKING:
from collections.abc import Generator, Iterator
from collections.abc import Iterator
from typing import Any, Callable
from requests import Response
@ -224,7 +224,7 @@ class HyperlinkAvailabilityChecker:
self.to_ignore: list[re.Pattern[str]] = list(map(re.compile,
self.config.linkcheck_ignore))
def check(self, hyperlinks: dict[str, Hyperlink]) -> Generator[CheckResult, None, None]:
def check(self, hyperlinks: dict[str, Hyperlink]) -> Iterator[CheckResult]:
self.invoke_threads()
total_links = 0

View File

@ -11,7 +11,7 @@ from sphinx.locale import __
from sphinx.util import logging
if TYPE_CHECKING:
from collections.abc import Generator, Iterator
from collections.abc import Iterator
from typing_extensions import Self
@ -248,7 +248,7 @@ class Symbol:
Symbol.debug_print("recurseInAnon: ", recurseInAnon)
Symbol.debug_print("searchInSiblings: ", searchInSiblings)
def candidates() -> Generator[Symbol, None, None]:
def candidates() -> Iterator[Symbol]:
s = self
if Symbol.debug_lookup:
Symbol.debug_print("searching in self:")

View File

@ -17,7 +17,7 @@ from sphinx.locale import __
from sphinx.util import logging
if TYPE_CHECKING:
from collections.abc import Generator, Iterator
from collections.abc import Iterator
from sphinx.environment import BuildEnvironment
@ -237,7 +237,7 @@ class Symbol:
yield from sChild.get_all_symbols()
@property
def children_recurse_anon(self) -> Generator[Symbol, None, None]:
def children_recurse_anon(self) -> Iterator[Symbol]:
for c in self._children:
yield c
if not c.identOrOp.is_anon():
@ -347,7 +347,7 @@ class Symbol:
return False
return True
def candidates() -> Generator[Symbol, None, None]:
def candidates() -> Iterator[Symbol]:
s = self
if Symbol.debug_lookup:
Symbol.debug_print("searching in self:")

View File

@ -23,7 +23,7 @@ from sphinx.util.nodes import is_translatable
from sphinx.util.osutil import canon_path, os_path
if TYPE_CHECKING:
from collections.abc import Generator, Iterator
from collections.abc import Iterator
from pathlib import Path
from docutils import nodes
@ -524,7 +524,7 @@ class BuildEnvironment:
return added, changed, removed
def check_dependents(self, app: Sphinx, already: set[str]) -> Generator[str, None, None]:
def check_dependents(self, app: Sphinx, already: set[str]) -> Iterator[str]:
to_rewrite: list[str] = []
for docnames in self.events.emit('env-get-updated', self):
to_rewrite.extend(docnames)

View File

@ -32,7 +32,7 @@ from sphinx.util.osutil import FileAvoidWrite, ensuredir
from sphinx.util.template import ReSTRenderer
if TYPE_CHECKING:
from collections.abc import Generator, Sequence
from collections.abc import Iterator, Sequence
logger = logging.getLogger(__name__)
@ -214,7 +214,7 @@ def is_skipped_module(filename: str, opts: Any, _excludes: Sequence[re.Pattern[s
def walk(rootpath: str, excludes: Sequence[re.Pattern[str]], opts: Any,
) -> Generator[tuple[str, list[str], list[str]], None, None]:
) -> Iterator[tuple[str, list[str], list[str]]]:
"""Walk through the directory and list files and subdirectories up."""
followlinks = getattr(opts, 'followlinks', False)
includeprivate = getattr(opts, 'includeprivate', False)

View File

@ -25,7 +25,7 @@ from sphinx.util.inspect import (
)
if TYPE_CHECKING:
from collections.abc import Callable, Generator, Mapping
from collections.abc import Callable, Iterator, Mapping
from types import ModuleType
from typing import Any
@ -38,7 +38,7 @@ def _filter_enum_dict(
enum_class: type[Enum],
attrgetter: Callable[[Any, str, Any], Any],
enum_class_dict: Mapping[str, object],
) -> Generator[tuple[str, type, Any], None, None]:
) -> Iterator[tuple[str, type, Any]]:
"""Find the attributes to document of an enumeration class.
The output consists of triplets ``(attribute name, defining class, value)``

View File

@ -14,7 +14,7 @@ from sphinx.util import logging
from sphinx.util.inspect import isboundmethod, safe_getattr
if TYPE_CHECKING:
from collections.abc import Generator, Iterator, Sequence
from collections.abc import Iterator, Sequence
logger = logging.getLogger(__name__)
@ -137,7 +137,7 @@ class MockFinder(MetaPathFinder):
@contextlib.contextmanager
def mock(modnames: list[str]) -> Generator[None, None, None]:
def mock(modnames: list[str]) -> Iterator[None]:
"""Insert mock modules during context::
with mock(['target.module.name']):

View File

@ -22,7 +22,7 @@ from sphinx.util.display import status_iterator
from sphinx.util.nodes import make_refnode
if TYPE_CHECKING:
from collections.abc import Generator, Iterable
from collections.abc import Iterable, Iterator
from sphinx.application import Sphinx
from sphinx.builders import Builder
@ -239,7 +239,7 @@ def should_generate_module_page(app: Sphinx, modname: str) -> bool:
return True
def collect_pages(app: Sphinx) -> Generator[tuple[str, dict[str, Any], str], None, None]:
def collect_pages(app: Sphinx) -> Iterator[tuple[str, dict[str, Any], str]]:
env = app.builder.env
if not hasattr(env, '_viewcode_modules'):
return

View File

@ -14,7 +14,7 @@ import pytest
from sphinx.testing.util import SphinxTestApp, SphinxTestAppWrapperForSkipBuilding
if TYPE_CHECKING:
from collections.abc import Callable, Generator
from collections.abc import Callable, Iterator
from pathlib import Path
from typing import Any
@ -147,7 +147,7 @@ def app(
app_params: tuple[dict, dict],
make_app: Callable,
shared_result: SharedResult,
) -> Generator[SphinxTestApp, None, None]:
) -> Iterator[SphinxTestApp]:
"""
Provides the 'sphinx.application.Sphinx' object
"""
@ -183,7 +183,7 @@ def warning(app: SphinxTestApp) -> StringIO:
@pytest.fixture()
def make_app(test_params: dict, monkeypatch: Any) -> Generator[Callable, None, None]:
def make_app(test_params: dict, monkeypatch: Any) -> Iterator[Callable]:
"""
Provides make_app function to initialize SphinxTestApp instance.
if you want to initialize 'app' in your test function. please use this
@ -289,7 +289,7 @@ def sphinx_test_tempdir(tmp_path_factory: Any) -> Path:
@pytest.fixture()
def rollback_sysmodules() -> Generator[None, None, None]: # NoQA: PT004
def rollback_sysmodules() -> Iterator[None]: # NoQA: PT004
"""
Rollback sys.modules to its value before testing to unload modules
during tests.

View File

@ -21,7 +21,7 @@ from sphinx.util.i18n import format_date
from sphinx.util.nodes import apply_source_workaround, is_smartquotable
if TYPE_CHECKING:
from collections.abc import Generator
from collections.abc import Iterator
from docutils.nodes import Node, Text
@ -376,7 +376,7 @@ class SphinxSmartQuotes(SmartQuotes, SphinxTransform):
for tag in normalize_language_tag(language)
)
def get_tokens(self, txtnodes: list[Text]) -> Generator[tuple[str, str], None, None]:
def get_tokens(self, txtnodes: list[Text]) -> Iterator[tuple[str, str]]:
# A generator that yields ``(texttype, nodetext)`` tuples for a list
# of "Text" nodes (interface to ``smartquotes.educate_tokens()``).
for txtnode in txtnodes:

View File

@ -27,7 +27,7 @@ logger = logging.getLogger(__name__)
report_re = re.compile('^(.+?:(?:\\d+)?): \\((DEBUG|INFO|WARNING|ERROR|SEVERE)/(\\d+)?\\) ')
if TYPE_CHECKING:
from collections.abc import Generator
from collections.abc import Iterator
from types import ModuleType
from docutils.frontend import Values
@ -43,7 +43,7 @@ additional_nodes: set[type[Element]] = set()
@contextmanager
def docutils_namespace() -> Generator[None, None, None]:
def docutils_namespace() -> Iterator[None]:
"""Create namespace for reST parsers."""
try:
_directives = copy(directives._directives) # type: ignore[attr-defined]
@ -121,7 +121,7 @@ def unregister_node(node: type[Element]) -> None:
@contextmanager
def patched_get_language() -> Generator[None, None, None]:
def patched_get_language() -> Iterator[None]:
"""Patch docutils.languages.get_language() temporarily.
This ignores the second argument ``reporter`` to suppress warnings.
@ -141,7 +141,7 @@ def patched_get_language() -> Generator[None, None, None]:
@contextmanager
def patched_rst_get_language() -> Generator[None, None, None]:
def patched_rst_get_language() -> Iterator[None]:
"""Patch docutils.parsers.rst.languages.get_language().
Starting from docutils 0.17, get_language() in ``rst.languages``
also has a reporter, which needs to be disabled temporarily.
@ -165,7 +165,7 @@ def patched_rst_get_language() -> Generator[None, None, None]:
@contextmanager
def using_user_docutils_conf(confdir: str | None) -> Generator[None, None, None]:
def using_user_docutils_conf(confdir: str | None) -> Iterator[None]:
"""Let docutils know the location of ``docutils.conf`` for Sphinx."""
try:
docutilsconfig = os.environ.get('DOCUTILSCONFIG', None)
@ -181,7 +181,7 @@ def using_user_docutils_conf(confdir: str | None) -> Generator[None, None, None]
@contextmanager
def du19_footnotes() -> Generator[None, None, None]:
def du19_footnotes() -> Iterator[None]:
def visit_footnote(self: HTMLTranslator, node: Element) -> None:
label_style = self.settings.footnote_references
if not isinstance(node.previous_sibling(), type(node)):
@ -214,7 +214,7 @@ def du19_footnotes() -> Generator[None, None, None]:
@contextmanager
def patch_docutils(confdir: str | None = None) -> Generator[None, None, None]:
def patch_docutils(confdir: str | None = None) -> Iterator[None]:
"""Patch to docutils temporarily."""
with patched_get_language(), \
patched_rst_get_language(), \
@ -359,7 +359,7 @@ class NullReporter(Reporter):
@contextmanager
def switch_source_input(state: State, content: StringList) -> Generator[None, None, None]:
def switch_source_input(state: State, content: StringList) -> Iterator[None]:
"""Switch current source input of state temporarily."""
try:
# remember the original ``get_source_and_line()`` method

View File

@ -19,7 +19,7 @@ from sphinx.util.osutil import SEP, canon_path, relpath
if TYPE_CHECKING:
import datetime as dt
from collections.abc import Generator
from collections.abc import Iterator
from typing import Protocol, Union
from babel.core import Locale
@ -112,7 +112,7 @@ class CatalogRepository:
self.encoding = encoding
@property
def locale_dirs(self) -> Generator[str, None, None]:
def locale_dirs(self) -> Iterator[str]:
if not self.language:
return
@ -125,7 +125,7 @@ class CatalogRepository:
logger.verbose(__('locale_dir %s does not exist'), locale_path)
@property
def pofiles(self) -> Generator[tuple[str, str], None, None]:
def pofiles(self) -> Iterator[tuple[str, str]]:
for locale_dir in self.locale_dirs:
basedir = path.join(locale_dir, self.language, 'LC_MESSAGES')
for root, dirnames, filenames in os.walk(basedir):
@ -139,7 +139,7 @@ class CatalogRepository:
yield basedir, relpath(fullpath, basedir)
@property
def catalogs(self) -> Generator[CatalogInfo, None, None]:
def catalogs(self) -> Iterator[CatalogInfo]:
for basedir, filename in self.pofiles:
domain = canon_path(path.splitext(filename)[0])
yield CatalogInfo(basedir, domain, self.encoding)

View File

@ -16,7 +16,7 @@ from sphinx.util.console import colorize
from sphinx.util.osutil import abspath
if TYPE_CHECKING:
from collections.abc import Generator
from collections.abc import Iterator
from docutils.nodes import Node
@ -246,7 +246,7 @@ class MemoryHandler(logging.handlers.BufferingHandler):
@contextmanager
def pending_warnings() -> Generator[logging.Handler, None, None]:
def pending_warnings() -> Iterator[logging.Handler]:
"""Context manager to postpone logging warnings temporarily.
Similar to :func:`pending_logging`.
@ -274,7 +274,7 @@ def pending_warnings() -> Generator[logging.Handler, None, None]:
@contextmanager
def suppress_logging() -> Generator[MemoryHandler, None, None]:
def suppress_logging() -> Iterator[MemoryHandler]:
"""Context manager to suppress logging all logs temporarily.
For example::
@ -303,7 +303,7 @@ def suppress_logging() -> Generator[MemoryHandler, None, None]:
@contextmanager
def pending_logging() -> Generator[MemoryHandler, None, None]:
def pending_logging() -> Iterator[MemoryHandler]:
"""Context manager to postpone logging all logs temporarily.
For example::
@ -323,7 +323,7 @@ def pending_logging() -> Generator[MemoryHandler, None, None]:
@contextmanager
def skip_warningiserror(skip: bool = True) -> Generator[None, None, None]:
def skip_warningiserror(skip: bool = True) -> Iterator[None]:
"""Context manager to skip WarningIsErrorFilter temporarily."""
logger = logging.getLogger(NAMESPACE)
@ -343,7 +343,7 @@ def skip_warningiserror(skip: bool = True) -> Generator[None, None, None]:
@contextmanager
def prefixed_warnings(prefix: str) -> Generator[None, None, None]:
def prefixed_warnings(prefix: str) -> Iterator[None]:
"""Context manager to prepend prefix to all warning log records temporarily.
For example::
@ -393,7 +393,7 @@ class LogCollector:
self.logs: list[logging.LogRecord] = []
@contextmanager
def collect(self) -> Generator[None, None, None]:
def collect(self) -> Iterator[None]:
with pending_logging() as memhandler:
yield

View File

@ -18,7 +18,7 @@ from sphinx.locale import __
from sphinx.util import docutils, logging
if TYPE_CHECKING:
from collections.abc import Generator
from collections.abc import Iterator
from docutils.statemachine import StringList
@ -61,7 +61,7 @@ def heading(env: Environment, text: str, level: int = 1) -> str:
@contextmanager
def default_role(docname: str, name: str) -> Generator[None, None, None]:
def default_role(docname: str, name: str) -> Iterator[None]:
if name:
dummy_reporter = Reporter('', 4, 4)
role_fn, _ = roles.role(name, english, 0, dummy_reporter)

View File

@ -5,7 +5,7 @@ import math
import os
import re
import textwrap
from collections.abc import Generator, Iterable, Sequence
from collections.abc import Iterable, Iterator, Sequence
from itertools import chain, groupby
from typing import TYPE_CHECKING, Any, cast
@ -166,7 +166,7 @@ class Table:
return width + (cell.colspan - 1) * 3
@property
def cells(self) -> Generator[Cell, None, None]:
def cells(self) -> Iterator[Cell]:
seen: set[Cell] = set()
for line in self.lines:
for cell in line:

View File

@ -14,7 +14,7 @@ import sphinx.pycode
from sphinx.testing.util import _clean_up_global_state
if TYPE_CHECKING:
from collections.abc import Generator
from collections.abc import Iterator
def _init_console(
@ -52,7 +52,7 @@ def pytest_report_header(config: pytest.Config) -> str:
@pytest.fixture(autouse=True)
def _cleanup_docutils() -> Generator[None, None, None]:
def _cleanup_docutils() -> Iterator[None]:
saved_path = sys.path
yield # run the test
sys.path[:] = saved_path

View File

@ -9,11 +9,11 @@ import pytest
from sphinx import addnodes
if TYPE_CHECKING:
from collections.abc import Generator
from collections.abc import Iterator
@pytest.fixture()
def sig_elements() -> Generator[set[type[addnodes.desc_sig_element]], None, None]:
def sig_elements() -> Iterator[set[type[addnodes.desc_sig_element]]]:
"""Fixture returning the current ``addnodes.SIG_ELEMENTS`` set."""
original = addnodes.SIG_ELEMENTS.copy() # safe copy of the current nodes
yield {*addnodes.SIG_ELEMENTS} # temporary value to use during tests

View File

@ -7,7 +7,7 @@ import pytest
from sphinx.testing.util import etree_parse
if TYPE_CHECKING:
from collections.abc import Callable, Generator
from collections.abc import Callable, Iterator
from pathlib import Path
from xml.etree.ElementTree import ElementTree
@ -23,6 +23,6 @@ def _parse(path: Path) -> ElementTree:
@pytest.fixture(scope='package')
def cached_etree_parse() -> Generator[Callable[[Path], ElementTree], None, None]:
def cached_etree_parse() -> Iterator[Callable[[Path], ElementTree]]:
yield _parse
_etree_cache.clear()

View File

@ -32,6 +32,7 @@ from typing import (
Callable,
Dict,
Generator,
Iterator,
List,
NewType,
Optional,
@ -175,6 +176,8 @@ def test_restify_type_hints_containers():
assert restify(Generator[None, None, None]) == (":py:class:`~typing.Generator`\\ "
"[:py:obj:`None`, :py:obj:`None`, "
":py:obj:`None`]")
assert restify(Iterator[None]) == (":py:class:`~typing.Iterator`\\ "
"[:py:obj:`None`]")
def test_restify_type_hints_Callable():
@ -389,6 +392,10 @@ def test_stringify_type_hints_containers():
assert stringify_annotation(Generator[None, None, None], "fully-qualified") == "typing.Generator[None, None, None]"
assert stringify_annotation(Generator[None, None, None], "smart") == "~typing.Generator[None, None, None]"
assert stringify_annotation(Iterator[None], 'fully-qualified-except-typing') == "Iterator[None]"
assert stringify_annotation(Iterator[None], "fully-qualified") == "typing.Iterator[None]"
assert stringify_annotation(Iterator[None], "smart") == "~typing.Iterator[None]"
def test_stringify_type_hints_pep_585():
assert stringify_annotation(list[int], 'fully-qualified-except-typing') == "list[int]"