mbox series

[libgpiod,v2,00/23] bindings: python: conform to mypy and ruff linter recommendations

Message ID 20241114145116.2123714-1-vfazio@xes-inc.com
Headers show
Series bindings: python: conform to mypy and ruff linter recommendations | expand

Message

Vincent Fazio Nov. 14, 2024, 2:50 p.m. UTC
This patch series employs mypy [0] and ruff [1] to ensure the gpiod
library has correctly typed public interfaces, is performing proper type
checking internally, is consistently formatted in a standard code style
that targets Python 3.9 syntax, and passes a subset of linting checks.

Patches 1 and 2 remove unused imports, sort and guard the remainder, and
ensure the publicly usable classes are available from the gpiod module.

Patches 3-5 fix and add type hints to callable interfaces.

Patches 6-14 fix type and lint errors internal to the bindings.

Patch 15 fixes a duplicate test name identified by the linter.

Patch 16 and 17 remove unused imports, sort the remainder, and fix lint
errors related to a shadowed export.

Patches 18 and 19 fix and add type hints to callable interfaces within
the tests.

Patches 20-22 fix type and lint errors internal to the tests.

Patch 23 adds mypy and ruff configuration to pyproject.toml and adds
documentation to the readme so future patches can be evaluated against a
standard set of rules.

There should be no functional changes that impact existing code as part
of this series.

All unit tests continue to pass without changes and code coverage has
not changed.

After this series is applied, the public type annotations will reflect
the argument expectations of the class methods so consumers can type
check their code against the gpiod type annotations.

v2 changes (mostly feedback from Bartosz):
- Added/expanded commit messages
- Commit to raise exception classes has been dropped
- A few changes have been split to separate commits
- Line objects are no longer directly exported from the gpiod module
- A couple of public APIs now have loosened type requirements
- casting has been reworked for Chip and LineRequest classes
- additional strings are now f-strings
- imports used only for type checking are behind a type check guard
- tests: type hints have been reworked to be less noisy

[0]: https://mypy.readthedocs.io/en/stable/
[1]: https://docs.astral.sh/ruff/

Vincent Fazio (23):
  bindings: python: clean up imports and exports
  bindings: python: make internal a private submodule
  bindings: python: loosen type requirements in public API
  bindings: python: explicitly type gpiod.request_lines
  bindings: python: add type stub for the _ext module
  bindings: python: add missing method type hints
  bindings: python: add type hint for the sec variable in poll_fd
  bindings: python: add type hints for Chip's internal members
  bindings: python: fix Chip union-attr type errors
  bindings: python: add type hints for LineRequest's internal members
  bindings: python: fix LineRequest union-attr type errors
  bindings: python: convert lines to offsets in LineRequest
  bindings: python: cast return value of LineRequest.get_values
  bindings: python: selectively use f-strings
  bindings: python: tests: fix duplicate test name
  bindings: python: tests: clean up imports and exports
  bindings: python: tests: make EventType private to prevent export
  bindings: python: tests: add type stubs for external modules
  bindings: python: tests: add missing method type hints
  bindings: python: tests: add type hints to internal members
  bindings: python: tests: ignore purposeful type errors
  bindings: python: tests: selectively use f-strings
  bindings: python: configure and document dev dependencies

 bindings/python/README.md                     |  17 ++
 bindings/python/gpiod/__init__.py             |  83 ++++++-
 bindings/python/gpiod/_ext.pyi                |  93 ++++++++
 .../gpiod/{internal.py => _internal.py}       |   3 +-
 bindings/python/gpiod/chip.py                 |  80 ++++---
 bindings/python/gpiod/chip_info.py            |   8 +-
 bindings/python/gpiod/edge_event.py           |   9 +-
 bindings/python/gpiod/exception.py            |   4 +-
 bindings/python/gpiod/info_event.py           |  13 +-
 bindings/python/gpiod/line.py                 |   5 +-
 bindings/python/gpiod/line_info.py            |  10 +-
 bindings/python/gpiod/line_request.py         |  90 ++++----
 bindings/python/gpiod/line_settings.py        |  15 +-
 bindings/python/pyproject.toml                |  36 +++
 bindings/python/setup.py                      |   2 +-
 bindings/python/tests/__init__.py             |   6 +-
 bindings/python/tests/__main__.py             |   5 +-
 bindings/python/tests/gpiosim/__init__.py     |   2 +
 bindings/python/tests/gpiosim/_ext.pyi        |  21 ++
 bindings/python/tests/gpiosim/chip.py         |   3 +-
 bindings/python/tests/helpers.py              |  17 +-
 bindings/python/tests/procname/__init__.py    |   2 +
 bindings/python/tests/procname/_ext.pyi       |   1 +
 bindings/python/tests/tests_chip.py           |  99 +++++----
 bindings/python/tests/tests_chip_info.py      |  31 +--
 bindings/python/tests/tests_edge_event.py     |  60 ++---
 bindings/python/tests/tests_info_event.py     |  81 +++----
 bindings/python/tests/tests_line.py           |   5 +-
 bindings/python/tests/tests_line_info.py      |  40 ++--
 bindings/python/tests/tests_line_request.py   | 210 +++++++++---------
 bindings/python/tests/tests_line_settings.py  |  19 +-
 bindings/python/tests/tests_module.py         |  37 ++-
 32 files changed, 691 insertions(+), 416 deletions(-)
 create mode 100644 bindings/python/gpiod/_ext.pyi
 rename bindings/python/gpiod/{internal.py => _internal.py} (90%)
 create mode 100644 bindings/python/tests/gpiosim/_ext.pyi
 create mode 100644 bindings/python/tests/procname/_ext.pyi

Comments

Bartosz Golaszewski Nov. 19, 2024, 1:51 p.m. UTC | #1
On Thu, Nov 14, 2024 at 3:58 PM Vincent Fazio <vfazio@xes-inc.com> wrote:
>
> This patch series employs mypy [0] and ruff [1] to ensure the gpiod
> library has correctly typed public interfaces, is performing proper type
> checking internally, is consistently formatted in a standard code style
> that targets Python 3.9 syntax, and passes a subset of linting checks.
>
> Patches 1 and 2 remove unused imports, sort and guard the remainder, and
> ensure the publicly usable classes are available from the gpiod module.
>
> Patches 3-5 fix and add type hints to callable interfaces.
>
> Patches 6-14 fix type and lint errors internal to the bindings.
>
> Patch 15 fixes a duplicate test name identified by the linter.
>
> Patch 16 and 17 remove unused imports, sort the remainder, and fix lint
> errors related to a shadowed export.
>
> Patches 18 and 19 fix and add type hints to callable interfaces within
> the tests.
>
> Patches 20-22 fix type and lint errors internal to the tests.
>
> Patch 23 adds mypy and ruff configuration to pyproject.toml and adds
> documentation to the readme so future patches can be evaluated against a
> standard set of rules.
>
> There should be no functional changes that impact existing code as part
> of this series.
>
> All unit tests continue to pass without changes and code coverage has
> not changed.
>
> After this series is applied, the public type annotations will reflect
> the argument expectations of the class methods so consumers can type
> check their code against the gpiod type annotations.
>

Thanks for your work, this really improves the bindings.

On a related note: we still have some uses of deprecated distutils in
the code. Do you know how we should replace LooseVersion to not use it
anymore?

Bart
Vincent Fazio Nov. 19, 2024, 1:56 p.m. UTC | #2
On Tue, Nov 19, 2024 at 7:51 AM Bartosz Golaszewski <brgl@bgdev.pl> wrote:
>
> Thanks for your work, this really improves the bindings.

My pleasure!

>
> On a related note: we still have some uses of deprecated distutils in
> the code. Do you know how we should replace LooseVersion to not use it
> anymore?
>

I can look into this. Should we create an issue in the GH repo to track this?
Bartosz Golaszewski Nov. 19, 2024, 2:03 p.m. UTC | #3
On Tue, Nov 19, 2024 at 2:57 PM Vincent Fazio <vfazio@gmail.com> wrote:
>
> On Tue, Nov 19, 2024 at 7:51 AM Bartosz Golaszewski <brgl@bgdev.pl> wrote:
> >
> > Thanks for your work, this really improves the bindings.
>
> My pleasure!
>
> >
> > On a related note: we still have some uses of deprecated distutils in
> > the code. Do you know how we should replace LooseVersion to not use it
> > anymore?
> >
>
> I can look into this. Should we create an issue in the GH repo to track this?

Sure! I will apply this series shortly.

Bart
Bartosz Golaszewski Nov. 19, 2024, 2:41 p.m. UTC | #4
From: Bartosz Golaszewski <bartosz.golaszewski@linaro.org>


On Thu, 14 Nov 2024 08:50:53 -0600, Vincent Fazio wrote:
> This patch series employs mypy [0] and ruff [1] to ensure the gpiod
> library has correctly typed public interfaces, is performing proper type
> checking internally, is consistently formatted in a standard code style
> that targets Python 3.9 syntax, and passes a subset of linting checks.
> 
> Patches 1 and 2 remove unused imports, sort and guard the remainder, and
> ensure the publicly usable classes are available from the gpiod module.
> 
> [...]

Applied, thanks!

[01/23] bindings: python: clean up imports and exports
        commit: 7fde8a47f5845b20ef4774416b28bf063848dc0e
[02/23] bindings: python: make internal a private submodule
        commit: b306ce694ab1acf75502ae1cedf8ab6d8d9e7647
[03/23] bindings: python: loosen type requirements in public API
        commit: 8f62e6c45355588621ca5916cfab6d1d8e787a77
[04/23] bindings: python: explicitly type gpiod.request_lines
        commit: f5c70ec993497d92e62e0660f12d2bd22deb4a7b
[05/23] bindings: python: add type stub for the _ext module
        commit: 30e23df2ef9ffcb8f488383bcfceb03e07c31db3
[06/23] bindings: python: add missing method type hints
        commit: 498ec6df34cd103a532e33fa1a7edf47339f88de
[07/23] bindings: python: add type hint for the sec variable in poll_fd
        commit: 2a2904082fd1bbbf5863dccd4184873c5826ae72
[08/23] bindings: python: add type hints for Chip's internal members
        commit: 1cc8bedab60e9c72c215076424dceba0ecba5ff4
[09/23] bindings: python: fix Chip union-attr type errors
        commit: 72e51c8a94f508c472c855331ba680bb1d0b95e2
[10/23] bindings: python: add type hints for LineRequest's internal members
        commit: 01efd10160bfcf09566992522aa70319241d3db7
[11/23] bindings: python: fix LineRequest union-attr type errors
        commit: fcb520f9fe5cc6e550646daee224c6e3d0c3bfb6
[12/23] bindings: python: convert lines to offsets in LineRequest
        commit: fcddb71b45e7bf7dde3eb0c6849acba7bc609462
[13/23] bindings: python: cast return value of LineRequest.get_values
        commit: f3444341f4964b47f8e72f4ef697fad535d9dcc6
[14/23] bindings: python: selectively use f-strings
        commit: 42308c2df11a6ec30661ba7d90a8afe368bb378b
[15/23] bindings: python: tests: fix duplicate test name
        commit: 0f40c01a09c2aec7319fedf82eb171a37663912b
[16/23] bindings: python: tests: clean up imports and exports
        commit: 171577eb41f916b77772346c6fe12defea626793
[17/23] bindings: python: tests: make EventType private to prevent export
        commit: 66c12b72ebf21170eff96f2f3f3a864b41237c65
[18/23] bindings: python: tests: add type stubs for external modules
        commit: 72f2eede085905d2f55d6a1aabddcebb21ca264c
[19/23] bindings: python: tests: add missing method type hints
        commit: d9313c18a06432ec10732b94885f915bdbc722bf
[20/23] bindings: python: tests: add type hints to internal members
        commit: f04f58ae1d548542134a31f48a1285b59a2915fc
[21/23] bindings: python: tests: ignore purposeful type errors
        commit: 632ea4df4b3ec9c3721623b150c5f6964447db54
[22/23] bindings: python: tests: selectively use f-strings
        commit: 3bb5368ba2a399b975ea552b2ea86cf5079739fa
[23/23] bindings: python: configure and document dev dependencies
        commit: 0505dc36435b6d87523f530192d6025fc94222f3

Best regards,
Bartosz Golaszewski Nov. 20, 2024, 1:59 p.m. UTC | #5
On Thu, Nov 14, 2024 at 3:51 PM Vincent Fazio <vfazio@xes-inc.com> wrote:
>
> The internal submodule shouldn't be exposed as part of the public
> interface, so mark it private following PEP 8 convention [0].
>
> [0]: https://peps.python.org/pep-0008/#public-and-internal-interfaces
> Signed-off-by: Vincent Fazio <vfazio@xes-inc.com>
> ---

FYI this broke `make dist` because the Makefile still tries to package
internal.py (without the '_' prefix). I fixed it in tree.

Bart