Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update ci #202

Merged
merged 10 commits into from
Feb 19, 2024
40 changes: 20 additions & 20 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -11,11 +11,11 @@ jobs:
check:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Set up Python 3.11
uses: actions/setup-python@v3
- uses: actions/checkout@v4
- name: Set up Python 3.12
uses: actions/setup-python@v5
with:
python-version: '3.11'
python-version: '3.12'
- name: Install dependencies
run: |
python -m pip install --upgrade pip setuptools pre-commit
Expand All @@ -27,46 +27,46 @@ jobs:
runs-on: ubuntu-latest
strategy:
matrix:
python-version: ['3.9', '3.10', '3.11']
python-version: ['3.9', '3.10', '3.11', '3.12', 3.13-dev]
fail-fast: false
steps:
- uses: actions/checkout@v3
- uses: actions/checkout@v4
- name: Set up Python ${{ matrix.python-version }}
uses: actions/setup-python@v3
uses: actions/setup-python@v5
with:
python-version: ${{ matrix.python-version }}
- name: Install dependencies
run: |
python -m pip install --upgrade pip setuptools tox
python -m tox --notest --recreate -e flake8_5,flake8_6
- name: Run tests
run: python -m tox -e flake8_5,flake8_6
run: python -m pip install --upgrade pip setuptools tox
- name: Run tests with flake8_6
run: python -m tox -e flake8_6
- name: Run tests with flake8_7+
run: python -m tox -e flake8_7

slow_tests:
runs-on: ubuntu-latest
strategy:
fail-fast: false
steps:
- uses: actions/checkout@v3
- name: Set up Python 3.11
uses: actions/setup-python@v3
- uses: actions/checkout@v4
- name: Set up Python 3.12
uses: actions/setup-python@v5
with:
python-version: 3.11
python-version: 3.12
- name: Install dependencies
run: |
python -m pip install --upgrade pip setuptools tox
python -m tox --notest --recreate -e flake8_6
python -m tox --notest --recreate -e flake8_7
- name: Run tests
run: python -m tox -e flake8_6 -- --onlyfuzz --no-cov -n auto
run: python -m tox -e flake8_7 -- --onlyfuzz --no-cov -n auto

release:
runs-on: ubuntu-latest
needs: [check, test]
if: github.repository == 'Zac-HD/flake8-trio' && github.ref == 'refs/heads/main'
steps:
- uses: actions/checkout@v3
- uses: actions/checkout@v4
- name: Set up Python 3
uses: actions/setup-python@v3
uses: actions/setup-python@v5
- name: Install tools
run: python -m pip install --upgrade build pip setuptools wheel twine gitpython
- name: Upload new release
Expand Down
48 changes: 13 additions & 35 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
@@ -1,41 +1,42 @@
---
default_language_version:
python: python3.11
python: python3.12
# pyright requires internet connection to run, which the pre-commit ci app doesn't have.
# Not used in this repo.
ci:
skip: [pyright]

repos:
- repo: https://github.com/psf/black
rev: 23.1.0
rev: 24.2.0
hooks:
- id: black
args: [--preview]

- repo: https://github.com/PyCQA/autoflake
rev: v2.0.2
rev: v2.2.1
hooks:
- id: autoflake

- repo: https://github.com/asottile/pyupgrade
rev: v3.3.1
rev: v3.15.0
hooks:
- id: pyupgrade
args: [--py39-plus]
exclude: tests/eval_files/trio103.py

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

- repo: https://github.com/pre-commit/mirrors-mypy
rev: v1.1.1
rev: v1.8.0
hooks:
- id: mypy

- repo: https://github.com/RobertCraigie/pyright-python
rev: v1.1.299
rev: v1.1.350
hooks:
- id: pyright
# ignore warnings about new version being available, no other warnings
Expand All @@ -53,14 +54,14 @@ repos:
- trio

- repo: https://github.com/codespell-project/codespell
rev: v2.2.4
rev: v2.2.6
hooks:
- id: codespell
additional_dependencies:
- tomli

- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.4.0
rev: v4.5.0
hooks:
- id: check-merge-conflict
- id: check-toml
Expand All @@ -74,40 +75,17 @@ repos:
args: ['--markdown-linebreak-ext=md,markdown']

- repo: https://github.com/charliermarsh/ruff-pre-commit
rev: v0.0.269
rev: v0.2.1
hooks:
- id: ruff

- repo: https://github.com/PyCQA/flake8
rev: 6.0.0
hooks:
- id: flake8
# this doesn't seem to work, pyi files don't get checked with --all-files
types_or: [python, pyi]
language_version: python3
additional_dependencies:
- flake8-2020
- flake8-bugbear
- flake8-builtins
- flake8-comprehensions
- flake8-datetimez
- flake8-docstrings
- flake8-mutable # not official supported by ruff
- flake8-pie
- flake8-pyi
- flake8-pytest-style
- flake8-return
- flake8-simplify
- flake8-type-checking
# all other are

- repo: https://github.com/jumanjihouse/pre-commit-hook-yamlfmt
rev: 0.2.2
rev: 0.2.3
hooks:
- id: yamlfmt

- repo: https://github.com/macisamuele/language-formatters-pre-commit-hooks
rev: v2.8.0
rev: v2.12.0
hooks:
- id: pretty-format-toml
args: [--autofix]
1 change: 1 addition & 0 deletions flake8_trio/__main__.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
"""Entry file when executed with `python -m`."""

import sys

from . import main
Expand Down
12 changes: 7 additions & 5 deletions flake8_trio/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
from __future__ import annotations

from dataclasses import dataclass
from typing import TYPE_CHECKING, Any, NamedTuple
from typing import TYPE_CHECKING, NamedTuple

if TYPE_CHECKING:
from collections.abc import Collection
Expand All @@ -29,10 +29,12 @@ class Statement(NamedTuple):
lineno: int
col_offset: int = -1

def __eq__(self, other: Any) -> bool:
# pyright is unhappy about defining __eq__ but not __hash__ .. which it should
# but it works :tm: and needs changing in a couple places to avoid it.
def __eq__(self, other: object) -> bool:
return (
isinstance(other, Statement)
and self[:2] == other[:2] # type: ignore
and self[:2] == other[:2]
and (
self.col_offset == other.col_offset
or -1 in (self.col_offset, other.col_offset)
Expand Down Expand Up @@ -68,11 +70,11 @@ def cmp(self):
return self.line, self.code, self.args, self.col

# for sorting in tests
def __lt__(self, other: Any) -> bool:
def __lt__(self, other: Error) -> bool:
assert isinstance(other, Error)
return self.cmp() < other.cmp()

def __eq__(self, other: Any) -> bool:
def __eq__(self, other: object) -> bool:
return isinstance(other, Error) and self.cmp() == other.cmp()

def __repr__(self) -> str: # pragma: no cover
Expand Down
6 changes: 3 additions & 3 deletions flake8_trio/visitors/flake8triovisitor.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

import ast
from abc import ABC
from typing import TYPE_CHECKING, Any, Union
from typing import TYPE_CHECKING, Any, ClassVar, Union

import libcst as cst
from libcst.metadata import PositionProvider
Expand All @@ -23,7 +23,7 @@

class Flake8TrioVisitor(ast.NodeVisitor, ABC):
# abstract attribute by not providing a value
error_codes: dict[str, str] # pyright: ignore[reportUninitializedInstanceVariable]
error_codes: ClassVar[dict[str, str]]

def __init__(self, shared_state: SharedState):
super().__init__()
Expand Down Expand Up @@ -158,7 +158,7 @@ def add_library(self, name: str) -> None:

class Flake8TrioVisitor_cst(cst.CSTTransformer, ABC):
# abstract attribute by not providing a value
error_codes: dict[str, str] # pyright: ignore[reportUninitializedInstanceVariable]
error_codes: dict[str, str]
METADATA_DEPENDENCIES = (PositionProvider,)

def __init__(self, shared_state: SharedState):
Expand Down
6 changes: 4 additions & 2 deletions flake8_trio/visitors/helpers.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@

import ast
from fnmatch import fnmatch
from typing import TYPE_CHECKING, NamedTuple, TypeVar
from typing import TYPE_CHECKING, NamedTuple, TypeVar, Union

import libcst as cst
import libcst.matchers as m
Expand All @@ -29,7 +29,9 @@

T = TypeVar("T", bound=Flake8TrioVisitor)
T_CST = TypeVar("T_CST", bound=Flake8TrioVisitor_cst)
T_EITHER = TypeVar("T_EITHER", bound=Flake8TrioVisitor | Flake8TrioVisitor_cst)
T_EITHER = TypeVar(
"T_EITHER", bound=Union[Flake8TrioVisitor, Flake8TrioVisitor_cst]
)
Comment on lines +32 to +34

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why this change?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I didn't previously specify python_version in pyproject.toml for mypy, and now that I did it didn't like the old version which wouldn't work at runtime - and mypy doesn't seem to detect that we're inside an if TYPE_CHECKING block.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

although I never remember which tools want python_version to be set to max-version-you-support vs min-version-you-support, so maybe should set it to 3.12 instead of 3.9

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

mypy wants you to run separate runs of all of them in parallel x)
python/mypy#12286



def error_class(error_class: type[T]) -> type[T]:
Expand Down
3 changes: 2 additions & 1 deletion flake8_trio/visitors/visitor100.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,12 @@
the timeout can only be triggered by a checkpoint.
Checkpoints on Await, Async For and Async With
"""

from __future__ import annotations

from typing import Any

import libcst as cst # noqa: TCH002
import libcst as cst
import libcst.matchers as m

from .flake8triovisitor import Flake8TrioVisitor_cst
Expand Down
1 change: 1 addition & 0 deletions flake8_trio/visitors/visitor101.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
`yield` inside a nursery or cancel scope is only safe when implementing a context manager
- otherwise, it breaks exception handling.
"""

from __future__ import annotations

from typing import TYPE_CHECKING, Any
Expand Down
1 change: 0 additions & 1 deletion flake8_trio/visitors/visitor103_104.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,6 @@
an improper raise, or other flow control, is encountered.
"""


from __future__ import annotations

import ast
Expand Down
1 change: 0 additions & 1 deletion flake8_trio/visitors/visitor118.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@
that breaks linter checks and multi-backend programs.
"""


from __future__ import annotations

import ast
Expand Down
21 changes: 14 additions & 7 deletions flake8_trio/visitors/visitor91x.py
Original file line number Diff line number Diff line change
Expand Up @@ -35,10 +35,16 @@
def func_empty_body(node: cst.FunctionDef) -> bool:
"""Check if function body consist of `pass`, `...`, and/or (doc)string literals."""
empty_statement = m.Pass() | m.Expr(m.Ellipsis() | m.SimpleString())

return m.matches(
node.body,
m.IndentedBlock(
[m.ZeroOrMore(m.SimpleStatementLine([m.ZeroOrMore(empty_statement)]))]
m.OneOf(
# newline + indented statements
m.IndentedBlock(
[m.ZeroOrMore(m.SimpleStatementLine([m.ZeroOrMore(empty_statement)]))]
),
# same-line statement[s]
m.SimpleStatementSuite(body=[m.ZeroOrMore(empty_statement)]),
),
)

Expand Down Expand Up @@ -114,12 +120,10 @@ def __init__(self):

@property
@abstractmethod
def library(self) -> tuple[str, ...]:
...
def library(self) -> tuple[str, ...]: ...

@abstractmethod
def should_autofix(self, node: cst.CSTNode, code: str | None = None) -> bool:
...
def should_autofix(self, node: cst.CSTNode, code: str | None = None) -> bool: ...

# instead of trying to exclude yields found in all the weird places from
# setting self.add_statement, we instead clear it upon each new line.
Expand Down Expand Up @@ -587,7 +591,10 @@ def visit_While_body(self, node: cst.For | cst.While):
if getattr(node, "asynchronous", None):
self.uncheckpointed_statements = set()
else:
self.uncheckpointed_statements = {ARTIFICIAL_STATEMENT}
# pyright correctly dislikes Statement defining __eq__ but not __hash__
# but it works:tm:, and changing it touches on various bits of code, so
# leaving it for another time.
self.uncheckpointed_statements = {ARTIFICIAL_STATEMENT} # pyright: ignore

self.loop_state.uncheckpointed_before_continue = set()
self.loop_state.uncheckpointed_before_break = set()
Expand Down
8 changes: 6 additions & 2 deletions flake8_trio/visitors/visitor_utility.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
import ast
import functools
import re
from typing import TYPE_CHECKING, Any
from typing import TYPE_CHECKING, Any, cast

import libcst.matchers as m
from libcst.metadata import PositionProvider
Expand All @@ -17,6 +17,7 @@
from re import Match

import libcst as cst
from libcst._position import CodeRange


@utility_visitor
Expand Down Expand Up @@ -178,7 +179,10 @@ def visit_Comment(self, node: cst.Comment):
return False

codes_str = noqa_match.groupdict()["codes"]
pos = self.get_metadata(PositionProvider, node).start

# see https://github.com/Instagram/LibCST/issues/1107
metadata = cast("CodeRange", self.get_metadata(PositionProvider, node))
pos = metadata.start

codes: set[str]

Expand Down
Loading