Skip to content

Commit

Permalink
Overhauled linting (agronholm#409)
Browse files Browse the repository at this point in the history
* Enforced the same pre-commit checks for everyone
* Switched most linting checks to be performed by pre-commit.ci
* Added a tox environment for pre-commit
  • Loading branch information
agronholm committed Jan 8, 2022
1 parent 780f60e commit 59ae376
Show file tree
Hide file tree
Showing 20 changed files with 139 additions and 130 deletions.
21 changes: 6 additions & 15 deletions .github/workflows/codeqa-test.yml → .github/workflows/test.yml
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
name: Python codeqa/test
name: Run the test suite

on:
push:
branches: [master]
pull_request:

jobs:
lint:
pyright:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
Expand All @@ -17,22 +17,13 @@ jobs:
- uses: actions/cache@v2
with:
path: ~/.cache/pip
key: pip-lint
key: pip-pyright
- name: Install dependencies
run: pip install pyproject-flake8 isort mypy pyright
- name: Run flake8
run: pflake8 src tests
- name: Run isort
run: isort -c --diff src tests
- name: Check types with Mypy
run: mypy src tests
- name: Check type completeness with pyright
run: |
pip install --no-deps -e . pytest
pyright --verifytypes anyio
run: pip install -e . pyright pytest
- name: Run pyright
run: pyright --verifytypes anyio

test:
needs: [lint]
strategy:
fail-fast: false
matrix:
Expand Down
1 change: 0 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -14,4 +14,3 @@ __pycache__
.idea
.cache
.local
.pre-commit-config.yaml
53 changes: 53 additions & 0 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
# This is the configuration file for pre-commit (https://pre-commit.com/).
# To use:
# * Install pre-commit (https://pre-commit.com/#installation)
# * Copy this file as ".pre-commit-config.yaml"
# * Run "pre-commit install".
repos:
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.1.0
hooks:
- id: check-toml
- id: check-yaml
- id: debug-statements
- id: end-of-file-fixer
- id: mixed-line-ending
args: [ "--fix=lf" ]
- id: trailing-whitespace

- repo: https://github.com/asottile/pyupgrade
rev: v2.30.1
hooks:
- id: pyupgrade
args: [ "--py36-plus", "--keep-mock" ]

- repo: https://github.com/pre-commit/mirrors-autopep8
rev: v1.6.0
hooks:
- id: autopep8

- repo: https://github.com/pycqa/isort
rev: 5.10.1
hooks:
- id: isort

- repo: https://github.com/csachs/pyproject-flake8
rev: v0.0.1a2.post1
hooks:
- id: pyproject-flake8

- repo: https://github.com/pre-commit/mirrors-mypy
rev: v0.931
hooks:
- id: mypy
additional_dependencies: [ "pytest", "trio-typing", "packaging" ]

- repo: https://github.com/pre-commit/pygrep-hooks
rev: v1.9.0
hooks:
- id: python-check-blanket-noqa
- id: python-check-blanket-type-ignore
- id: python-no-eval
- id: rst-backticks
- id: rst-directive-colons
- id: rst-inline-touching-normal
6 changes: 4 additions & 2 deletions docs/conf.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
#!/usr/bin/env python3
import pkg_resources
from importlib.metadata import version as get_version

from packaging.version import parse

extensions = [
'sphinx.ext.autodoc',
Expand All @@ -14,7 +16,7 @@
author = 'Alex Grönholm'
copyright = '2018, ' + author

v = pkg_resources.get_distribution('anyio').parsed_version
v = parse(get_version('anyio'))
version = v.base_version
release = v.public

Expand Down
5 changes: 3 additions & 2 deletions docs/contributing.rst
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,9 @@ code style fixing tools and then the actual test suite. To only run the code sty
To build the documentation, run ``tox -e docs`` which will generate a directory named ``build``
in which you may view the formatted HTML documentation.

The use of pre-commit_ is also highly recommended. You can find a sample configuration file at the
root of the repository.
AnyIO uses pre-commit_ to perform several code style/quality checks. It is recommended to activate
pre-commit_ on your local clone of the repository (using ``pre-commit install``) to ensure that
your changes will pass the same checks on GitHub.

.. _tox: https://tox.readthedocs.io/en/latest/install.html
.. _pre-commit: https://pre-commit.com/#installation
Expand Down
28 changes: 0 additions & 28 deletions pre-commit-config.sample.yaml

This file was deleted.

1 change: 1 addition & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ disallow_any_generics = false
warn_return_any = false
disallow_untyped_decorators = false
disallow_subclassing_any = false
show_error_codes = true

[tool.pytest.ini_options]
addopts = "-rsx --tb=short --strict-config --strict-markers -p anyio -p no:asyncio"
Expand Down
1 change: 1 addition & 0 deletions setup.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ test =
uvloop >= 0.15; python_version >= '3.7' and (platform_python_implementation == 'CPython' and platform_system != 'Windows')
trio = trio >= 0.16
doc =
packaging
sphinx_rtd_theme
sphinx-autodoc-typehints >= 1.2.0

Expand Down
26 changes: 13 additions & 13 deletions src/anyio/_backends/_asyncio.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
import math
import socket
import sys
from asyncio.base_events import _run_until_complete_cb # type: ignore
from asyncio.base_events import _run_until_complete_cb # type: ignore[attr-defined]
from collections import OrderedDict, deque
from concurrent.futures import Future
from contextvars import Context, copy_context
Expand Down Expand Up @@ -43,15 +43,15 @@
if sys.version_info >= (3, 8):
get_coro = asyncio.Task.get_coro
else:
def get_coro(task: asyncio.Task) -> Union[Coroutine, Generator]:
def get_coro(task: asyncio.Task) -> Union[Generator, Awaitable[Any]]:
return task._coro

if sys.version_info >= (3, 7):
from asyncio import all_tasks, create_task, current_task, get_running_loop
from asyncio import run as native_run

def _get_task_callbacks(task: asyncio.Task) -> Iterable[Callable]:
return [cb for cb, context in task._callbacks] # type: ignore
return [cb for cb, context in task._callbacks] # type: ignore[attr-defined]
else:
_T = TypeVar('_T')

Expand Down Expand Up @@ -88,7 +88,7 @@ def _cancel_all_tasks(loop):
"asyncio.run() cannot be called from a running event loop")

if not coroutines.iscoroutine(main):
raise ValueError("a coroutine was expected, got {!r}".format(main))
raise ValueError(f"a coroutine was expected, got {main!r}")

loop = events.new_event_loop()
try:
Expand Down Expand Up @@ -188,7 +188,7 @@ def _task_started(task: asyncio.Task) -> bool:
return getcoroutinestate(coro) in (CORO_RUNNING, CORO_SUSPENDED)
except AttributeError:
try:
return getgeneratorstate(coro) in (GEN_RUNNING, GEN_SUSPENDED)
return getgeneratorstate(cast(Generator, coro)) in (GEN_RUNNING, GEN_SUSPENDED)
except AttributeError:
# task coro is async_genenerator_asend https://bugs.python.org/issue37771
raise Exception(f"Cannot determine if task {task} has started or not")
Expand Down Expand Up @@ -345,7 +345,7 @@ def _deliver_cancellation(self) -> None:
should_retry = False
current = current_task()
for task in self._tasks:
if task._must_cancel: # type: ignore
if task._must_cancel: # type: ignore[attr-defined]
continue

# The task is eligible for cancellation if it has started and is not in a cancel
Expand Down Expand Up @@ -512,7 +512,7 @@ def __init__(self, parent_id: Optional[int], name: Optional[str],
#

class ExceptionGroup(BaseExceptionGroup):
def __init__(self, exceptions: Sequence[BaseException]):
def __init__(self, exceptions: List[BaseException]):
super().__init__()
self.exceptions = exceptions

Expand Down Expand Up @@ -977,9 +977,9 @@ def _forcibly_shutdown_process_pool_on_exit(workers: Set[Process], _task: object
if process.returncode is None:
continue

process._stdin._stream._transport.close() # type: ignore
process._stdout._stream._transport.close() # type: ignore
process._stderr._stream._transport.close() # type: ignore
process._stdin._stream._transport.close() # type: ignore[union-attr]
process._stdout._stream._transport.close() # type: ignore[union-attr]
process._stderr._stream._transport.close() # type: ignore[union-attr]
process.kill()
if child_watcher:
child_watcher.remove_child_handler(process.pid)
Expand Down Expand Up @@ -1299,7 +1299,7 @@ async def send_fds(self, message: bytes, fds: Collection[Union[int, IOBase]]) ->
# https://github.com/python/typeshed/pull/5545
self.__raw_socket.sendmsg(
[message],
[(socket.SOL_SOCKET, socket.SCM_RIGHTS, fdarray)] # type: ignore
[(socket.SOL_SOCKET, socket.SCM_RIGHTS, fdarray)]
)
break
except BlockingIOError:
Expand Down Expand Up @@ -1845,7 +1845,7 @@ def _create_task_info(task: asyncio.Task) -> TaskInfo:


def get_current_task() -> TaskInfo:
return _create_task_info(current_task()) # type: ignore
return _create_task_info(current_task()) # type: ignore[arg-type]


def get_running_tasks() -> List[TaskInfo]:
Expand Down Expand Up @@ -1904,7 +1904,7 @@ def call(self, func: Callable[..., Awaitable[T_Retval]],
def exception_handler(loop: asyncio.AbstractEventLoop, context: Dict[str, Any]) -> None:
exceptions.append(context['exception'])

exceptions: List[Exception] = []
exceptions: List[BaseException] = []
self._loop.set_exception_handler(exception_handler)
try:
retval: T_Retval = self._loop.run_until_complete(func(*args, **kwargs))
Expand Down
Loading

0 comments on commit 59ae376

Please sign in to comment.