diff options
| -rw-r--r-- | .github/workflows/lint.yaml | 18 | ||||
| -rw-r--r-- | .pre-commit-config.yaml | 29 | ||||
| -rw-r--r-- | poetry.lock | 263 | ||||
| -rw-r--r-- | pyproject.toml | 29 | ||||
| -rw-r--r-- | tox.ini | 26 | 
5 files changed, 78 insertions, 287 deletions
diff --git a/.github/workflows/lint.yaml b/.github/workflows/lint.yaml index 58911758..68d35d82 100644 --- a/.github/workflows/lint.yaml +++ b/.github/workflows/lint.yaml @@ -46,22 +46,12 @@ jobs:            CLIENT_IN_CI: true            CLIENT_TOKEN: "" -      # We will not run `flake8` here, as we will use a separate flake8 -      # action.        - name: Run pre-commit hooks -        run: SKIP=flake8 pre-commit run --all-files +        run: SKIP=ruff pre-commit run --all-files -      # Run flake8 and have it format the linting errors in the format of -      # the GitHub Workflow command to register error annotations. This -      # means that our flake8 output is automatically added as an error -      # annotation to both the run result and in the "Files" tab of a -      # pull request. -      # -      # Format used: -      # ::error file={filename},line={line},col={col}::{message} -      - name: Run flake8 -        run: "flake8 \ -        --format='::error file=%(path)s,line=%(row)d,col=%(col)d::[flake8] %(code)s: %(text)s'" +      # Run `ruff` using github formatting to enable automatic inline annotations. +      - name: Run ruff +        run: "ruff check --format=github ."        # Prepare the Pull Request Payload artifact. If this fails, we        # we fail silently using the `continue-on-error` option. It's diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 7895d208..3fdd30bf 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -1,6 +1,6 @@  repos:    - repo: https://github.com/pre-commit/pre-commit-hooks -    rev: v2.5.0 +    rev: v4.4.0      hooks:        - id: check-merge-conflict        - id: check-toml @@ -8,21 +8,22 @@ repos:        - id: end-of-file-fixer        - id: trailing-whitespace          args: [--markdown-linebreak-ext=md] -  - repo: https://github.com/pre-commit/pygrep-hooks -    rev: v1.5.1 -    hooks: -      - id: python-check-blanket-noqa -  - repo: https://github.com/pycqa/isort -    rev: 5.12.0 -    hooks: -      - id: isort -        name: isort (python) +    - repo: local      hooks: -      - id: flake8 -        name: Flake8 -        description: This hook runs flake8 within our project's poetry environment. -        entry: poetry run flake8 +      - id: isort +        name: isort +        description: This hook runs isort within our project's environment. +        entry: poetry run isort          language: system          types: [python]          require_serial: true + +      - id: ruff +        name: ruff +        description: Run ruff linting +        entry: poetry run ruff check --force-exclude +        language: system +        'types_or': [python, pyi] +        require_serial: true +        args: [--fix, --exit-non-zero-on-fix] diff --git a/poetry.lock b/poetry.lock index fa74d15f..edd424af 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry and should not be changed by hand. +# This file is automatically @generated by Poetry 1.4.2 and should not be changed by hand.  [[package]]  name = "aiodns" @@ -225,14 +225,14 @@ lxml = ["lxml"]  [[package]]  name = "certifi" -version = "2022.12.7" +version = "2023.5.7"  description = "Python package for providing Mozilla's CA Bundle."  category = "main"  optional = false  python-versions = ">=3.6"  files = [ -    {file = "certifi-2022.12.7-py3-none-any.whl", hash = "sha256:4ad3232f5e926d6718ec31cfc1fcadfde020920e278684144551c91769c7bc18"}, -    {file = "certifi-2022.12.7.tar.gz", hash = "sha256:35824b4c3a97115964b408844d64aa14db1cc518f6562e8d7261699d1350a9e3"}, +    {file = "certifi-2023.5.7-py3-none-any.whl", hash = "sha256:c6c2e98f5c7869efca1f8916fed228dd91539f9f1b444c314c06eef02980c716"}, +    {file = "certifi-2023.5.7.tar.gz", hash = "sha256:0f0d56dc5a6ad56fd4ba36484d6cc34451e1c6548c61daad8c320169f91eddc7"},  ]  [[package]] @@ -500,14 +500,14 @@ files = [  [[package]]  name = "fakeredis" -version = "2.11.2" +version = "2.12.0"  description = "Fake implementation of redis API for testing purposes."  category = "main"  optional = false  python-versions = ">=3.7,<4.0"  files = [ -    {file = "fakeredis-2.11.2-py3-none-any.whl", hash = "sha256:69a504328a89e5e5f2d05a4236b570fb45244c96997c5002c8c6a0503b95f289"}, -    {file = "fakeredis-2.11.2.tar.gz", hash = "sha256:e0fef512b8ec49679d373456aa4698a4103005ecd7ca0b13170a2c1d3af949c5"}, +    {file = "fakeredis-2.12.0-py3-none-any.whl", hash = "sha256:13040c67c471edfa4aa941f023d04f0df05f092e81c9f42a7f91d8fe67612386"}, +    {file = "fakeredis-2.12.0.tar.gz", hash = "sha256:9c98be9f31d4b7d610e83ce3a8a3cb0434beedd16125f10475c618df4c52ed10"},  ]  [package.dependencies] @@ -536,137 +536,6 @@ docs = ["furo (>=2023.3.27)", "sphinx (>=6.1.3)", "sphinx-autodoc-typehints (>=1  testing = ["covdefaults (>=2.3)", "coverage (>=7.2.3)", "diff-cover (>=7.5)", "pytest (>=7.3.1)", "pytest-cov (>=4)", "pytest-mock (>=3.10)", "pytest-timeout (>=2.1)"]  [[package]] -name = "flake8" -version = "6.0.0" -description = "the modular source code checker: pep8 pyflakes and co" -category = "dev" -optional = false -python-versions = ">=3.8.1" -files = [ -    {file = "flake8-6.0.0-py2.py3-none-any.whl", hash = "sha256:3833794e27ff64ea4e9cf5d410082a8b97ff1a06c16aa3d2027339cd0f1195c7"}, -    {file = "flake8-6.0.0.tar.gz", hash = "sha256:c61007e76655af75e6785a931f452915b371dc48f56efd765247c8fe68f2b181"}, -] - -[package.dependencies] -mccabe = ">=0.7.0,<0.8.0" -pycodestyle = ">=2.10.0,<2.11.0" -pyflakes = ">=3.0.0,<3.1.0" - -[[package]] -name = "flake8-annotations" -version = "3.0.0" -description = "Flake8 Type Annotation Checks" -category = "dev" -optional = false -python-versions = ">=3.8.1,<4.0.0" -files = [ -    {file = "flake8_annotations-3.0.0-py3-none-any.whl", hash = "sha256:ea927d31016515e9aa6e256651d74baeeee6fa4ad3f8383715ec5c0460a4c225"}, -    {file = "flake8_annotations-3.0.0.tar.gz", hash = "sha256:88c8b35a0db10b9a92be69ed3f81494509a18db1c3162551e57bc0fc35fab065"}, -] - -[package.dependencies] -attrs = ">=21.4" -flake8 = ">=5.0" - -[[package]] -name = "flake8-bugbear" -version = "23.3.23" -description = "A plugin for flake8 finding likely bugs and design problems in your program. Contains warnings that don't belong in pyflakes and pycodestyle." -category = "dev" -optional = false -python-versions = ">=3.8.1" -files = [ -    {file = "flake8-bugbear-23.3.23.tar.gz", hash = "sha256:ea565bdb87b96b56dc499edd6cc3ba7f695373d902a5f56c989b74fad7c7719d"}, -    {file = "flake8_bugbear-23.3.23-py3-none-any.whl", hash = "sha256:8a218d13abd6904800970381057ce8e72cde8eea743240c4ef3ede4dd0bc9cfb"}, -] - -[package.dependencies] -attrs = ">=19.2.0" -flake8 = ">=6.0.0" - -[package.extras] -dev = ["coverage", "hypothesis", "hypothesmith (>=0.2)", "pre-commit", "pytest", "tox"] - -[[package]] -name = "flake8-docstrings" -version = "1.7.0" -description = "Extension for flake8 which uses pydocstyle to check docstrings" -category = "dev" -optional = false -python-versions = ">=3.7" -files = [ -    {file = "flake8_docstrings-1.7.0-py2.py3-none-any.whl", hash = "sha256:51f2344026da083fc084166a9353f5082b01f72901df422f74b4d953ae88ac75"}, -    {file = "flake8_docstrings-1.7.0.tar.gz", hash = "sha256:4c8cc748dc16e6869728699e5d0d685da9a10b0ea718e090b1ba088e67a941af"}, -] - -[package.dependencies] -flake8 = ">=3" -pydocstyle = ">=2.1" - -[[package]] -name = "flake8-isort" -version = "6.0.0" -description = "flake8 plugin that integrates isort ." -category = "dev" -optional = false -python-versions = ">=3.7" -files = [ -    {file = "flake8-isort-6.0.0.tar.gz", hash = "sha256:537f453a660d7e903f602ecfa36136b140de279df58d02eb1b6a0c84e83c528c"}, -    {file = "flake8_isort-6.0.0-py3-none-any.whl", hash = "sha256:aa0cac02a62c7739e370ce6b9c31743edac904bae4b157274511fc8a19c75bbc"}, -] - -[package.dependencies] -flake8 = "*" -isort = ">=5.0.0,<6" - -[package.extras] -test = ["pytest"] - -[[package]] -name = "flake8-string-format" -version = "0.3.0" -description = "string format checker, plugin for flake8" -category = "dev" -optional = false -python-versions = "*" -files = [ -    {file = "flake8-string-format-0.3.0.tar.gz", hash = "sha256:65f3da786a1461ef77fca3780b314edb2853c377f2e35069723348c8917deaa2"}, -    {file = "flake8_string_format-0.3.0-py2.py3-none-any.whl", hash = "sha256:812ff431f10576a74c89be4e85b8e075a705be39bc40c4b4278b5b13e2afa9af"}, -] - -[package.dependencies] -flake8 = "*" - -[[package]] -name = "flake8-tidy-imports" -version = "4.8.0" -description = "A flake8 plugin that helps you write tidier imports." -category = "dev" -optional = false -python-versions = ">=3.7" -files = [ -    {file = "flake8-tidy-imports-4.8.0.tar.gz", hash = "sha256:df44f9c841b5dfb3a7a1f0da8546b319d772c2a816a1afefcce43e167a593d83"}, -    {file = "flake8_tidy_imports-4.8.0-py3-none-any.whl", hash = "sha256:25bd9799358edefa0e010ce2c587b093c3aba942e96aeaa99b6d0500ae1bf09c"}, -] - -[package.dependencies] -flake8 = ">=3.8.0" - -[[package]] -name = "flake8-todo" -version = "0.7" -description = "TODO notes checker, plugin for flake8" -category = "dev" -optional = false -python-versions = "*" -files = [ -    {file = "flake8-todo-0.7.tar.gz", hash = "sha256:6e4c5491ff838c06fe5a771b0e95ee15fc005ca57196011011280fc834a85915"}, -] - -[package.dependencies] -pycodestyle = ">=2.0.0,<3.0.0" - -[[package]]  name = "frozenlist"  version = "1.3.3"  description = "A list-like structure which implements collections.abc.MutableSequence" @@ -989,18 +858,6 @@ htmlsoup = ["BeautifulSoup4"]  source = ["Cython (>=0.29.7)"]  [[package]] -name = "mccabe" -version = "0.7.0" -description = "McCabe checker, plugin for flake8" -category = "dev" -optional = false -python-versions = ">=3.6" -files = [ -    {file = "mccabe-0.7.0-py2.py3-none-any.whl", hash = "sha256:6c2d30ab6be0e4a46919781807b4f0d834ebdd6c6e3dca0bda5a15f863427b6e"}, -    {file = "mccabe-0.7.0.tar.gz", hash = "sha256:348e0240c33b60bbdf4e523192ef919f28cb2c3d7d5c7794f74009290f236325"}, -] - -[[package]]  name = "mslex"  version = "0.3.0"  description = "shlex for windows" @@ -1112,21 +969,6 @@ files = [  setuptools = "*"  [[package]] -name = "pep8-naming" -version = "0.13.3" -description = "Check PEP-8 naming conventions, plugin for flake8" -category = "dev" -optional = false -python-versions = ">=3.7" -files = [ -    {file = "pep8-naming-0.13.3.tar.gz", hash = "sha256:1705f046dfcd851378aac3be1cd1551c7c1e5ff363bacad707d43007877fa971"}, -    {file = "pep8_naming-0.13.3-py3-none-any.whl", hash = "sha256:1a86b8c71a03337c97181917e2b472f0f5e4ccb06844a0d6f0a33522549e7a80"}, -] - -[package.dependencies] -flake8 = ">=5.0.0" - -[[package]]  name = "pillow"  version = "9.5.0"  description = "Python Imaging Library (Fork)" @@ -1373,18 +1215,6 @@ cffi = ">=1.5.0"  idna = ["idna (>=2.1)"]  [[package]] -name = "pycodestyle" -version = "2.10.0" -description = "Python style guide checker" -category = "dev" -optional = false -python-versions = ">=3.6" -files = [ -    {file = "pycodestyle-2.10.0-py2.py3-none-any.whl", hash = "sha256:8a4eaf0d0495c7395bdab3589ac2db602797d76207242c17d470186815706610"}, -    {file = "pycodestyle-2.10.0.tar.gz", hash = "sha256:347187bdb476329d98f695c213d7295a846d1152ff4fe9bacb8a9590b8ee7053"}, -] - -[[package]]  name = "pycparser"  version = "2.21"  description = "C parser in Python" @@ -1472,36 +1302,6 @@ statsd = "4.0.1"  async-rediscache = ["async-rediscache[fakeredis] (==1.0.0rc2)"]  [[package]] -name = "pydocstyle" -version = "6.3.0" -description = "Python docstring style checker" -category = "dev" -optional = false -python-versions = ">=3.6" -files = [ -    {file = "pydocstyle-6.3.0-py3-none-any.whl", hash = "sha256:118762d452a49d6b05e194ef344a55822987a462831ade91ec5c06fd2169d019"}, -    {file = "pydocstyle-6.3.0.tar.gz", hash = "sha256:7ce43f0c0ac87b07494eb9c0b462c0b73e6ff276807f204d6b53edc72b7e44e1"}, -] - -[package.dependencies] -snowballstemmer = ">=2.2.0" - -[package.extras] -toml = ["tomli (>=1.2.3)"] - -[[package]] -name = "pyflakes" -version = "3.0.1" -description = "passive checker of Python programs" -category = "dev" -optional = false -python-versions = ">=3.6" -files = [ -    {file = "pyflakes-3.0.1-py2.py3-none-any.whl", hash = "sha256:ec55bf7fe21fff7f1ad2f7da62363d749e2a470500eab1b555334b67aa1ef8cf"}, -    {file = "pyflakes-3.0.1.tar.gz", hash = "sha256:ec8b276a6b60bd80defed25add7e439881c19e64850afd9b346283d4165fd0fd"}, -] - -[[package]]  name = "pyjokes"  version = "0.6.0"  description = "One line jokes for programmers (jokes as a service)" @@ -1716,24 +1516,51 @@ full = ["numpy"]  [[package]]  name = "redis" -version = "4.5.4" +version = "4.5.5"  description = "Python client for Redis database and key-value store"  category = "main"  optional = false  python-versions = ">=3.7"  files = [ -    {file = "redis-4.5.4-py3-none-any.whl", hash = "sha256:2c19e6767c474f2e85167909061d525ed65bea9301c0770bb151e041b7ac89a2"}, -    {file = "redis-4.5.4.tar.gz", hash = "sha256:73ec35da4da267d6847e47f68730fdd5f62e2ca69e3ef5885c6a78a9374c3893"}, +    {file = "redis-4.5.5-py3-none-any.whl", hash = "sha256:77929bc7f5dab9adf3acba2d3bb7d7658f1e0c2f1cafe7eb36434e751c471119"}, +    {file = "redis-4.5.5.tar.gz", hash = "sha256:dc87a0bdef6c8bfe1ef1e1c40be7034390c2ae02d92dcd0c7ca1729443899880"},  ]  [package.dependencies] -async-timeout = {version = ">=4.0.2", markers = "python_version <= \"3.11.2\""} +async-timeout = {version = ">=4.0.2", markers = "python_full_version <= \"3.11.2\""}  [package.extras]  hiredis = ["hiredis (>=1.0.0)"]  ocsp = ["cryptography (>=36.0.1)", "pyopenssl (==20.0.1)", "requests (>=2.26.0)"]  [[package]] +name = "ruff" +version = "0.0.265" +description = "An extremely fast Python linter, written in Rust." +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ +    {file = "ruff-0.0.265-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:30ddfe22de6ce4eb1260408f4480bbbce998f954dbf470228a21a9b2c45955e4"}, +    {file = "ruff-0.0.265-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:a11bd0889e88d3342e7bc514554bb4461bf6cc30ec115821c2425cfaac0b1b6a"}, +    {file = "ruff-0.0.265-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2a9b38bdb40a998cbc677db55b6225a6c4fadcf8819eb30695e1b8470942426b"}, +    {file = "ruff-0.0.265-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:a8b44a245b60512403a6a03a5b5212da274d33862225c5eed3bcf12037eb19bb"}, +    {file = "ruff-0.0.265-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b279fa55ea175ef953208a6d8bfbcdcffac1c39b38cdb8c2bfafe9222add70bb"}, +    {file = "ruff-0.0.265-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:5028950f7af9b119d43d91b215d5044976e43b96a0d1458d193ef0dd3c587bf8"}, +    {file = "ruff-0.0.265-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:4057eb539a1d88eb84e9f6a36e0a999e0f261ed850ae5d5817e68968e7b89ed9"}, +    {file = "ruff-0.0.265-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d586e69ab5cbf521a1910b733412a5735936f6a610d805b89d35b6647e2a66aa"}, +    {file = "ruff-0.0.265-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:aa17b13cd3f29fc57d06bf34c31f21d043735cc9a681203d634549b0e41047d1"}, +    {file = "ruff-0.0.265-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:9ac13b11d9ad3001de9d637974ec5402a67cefdf9fffc3929ab44c2fcbb850a1"}, +    {file = "ruff-0.0.265-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:62a9578b48cfd292c64ea3d28681dc16b1aa7445b7a7709a2884510fc0822118"}, +    {file = "ruff-0.0.265-py3-none-musllinux_1_2_i686.whl", hash = "sha256:d0f9967f84da42d28e3d9d9354cc1575f96ed69e6e40a7d4b780a7a0418d9409"}, +    {file = "ruff-0.0.265-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:1d5a8de2fbaf91ea5699451a06f4074e7a312accfa774ad9327cde3e4fda2081"}, +    {file = "ruff-0.0.265-py3-none-win32.whl", hash = "sha256:9e9db5ccb810742d621f93272e3cc23b5f277d8d00c4a79668835d26ccbe48dd"}, +    {file = "ruff-0.0.265-py3-none-win_amd64.whl", hash = "sha256:f54facf286103006171a00ce20388d88ed1d6732db3b49c11feb9bf3d46f90e9"}, +    {file = "ruff-0.0.265-py3-none-win_arm64.whl", hash = "sha256:c78470656e33d32ddc54e8482b1b0fc6de58f1195586731e5ff1405d74421499"}, +    {file = "ruff-0.0.265.tar.gz", hash = "sha256:53c17f0dab19ddc22b254b087d1381b601b155acfa8feed514f0d6a413d0ab3a"}, +] + +[[package]]  name = "sentry-sdk"  version = "1.22.1"  description = "Python client for Sentry (https://sentry.io)" @@ -1805,18 +1632,6 @@ files = [  ]  [[package]] -name = "snowballstemmer" -version = "2.2.0" -description = "This package provides 29 stemmers for 28 languages generated from Snowball algorithms." -category = "dev" -optional = false -python-versions = "*" -files = [ -    {file = "snowballstemmer-2.2.0-py2.py3-none-any.whl", hash = "sha256:c8e1716e83cc398ae16824e5572ae04e0d9fc2c6b985fb0f900f5f0c96ecba1a"}, -    {file = "snowballstemmer-2.2.0.tar.gz", hash = "sha256:09b16deb8547d3412ad7b590689584cd0fe25ec8db3be37788be3810cbf19cb1"}, -] - -[[package]]  name = "sortedcontainers"  version = "2.4.0"  description = "Sorted Containers -- Sorted List, Sorted Dict, Sorted Set" @@ -2035,4 +1850,4 @@ multidict = ">=4.0"  [metadata]  lock-version = "2.0"  python-versions = "3.11.*" -content-hash = "033ea5c5dce7b54a791b695f626ac1187ae3ca22f1a270dda09692cd3d87daf5" +content-hash = "e8e4465bbae84187d41bc7471c228249f8d03079829918f92193dca8edf26ffb" diff --git a/pyproject.toml b/pyproject.toml index 44bb95c6..70662865 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -28,18 +28,11 @@ pydantic = { version = "1.10.7", extras = ["dotenv"]}  [tool.poetry.dev-dependencies] -flake8 = "6.0.0" -flake8-annotations = "3.0.0" -flake8-bugbear = "23.3.23" -flake8-docstrings = "1.7.0" -flake8-string-format = "0.3.0" -flake8-tidy-imports = "4.8.0" -flake8-todo = "0.7" -flake8-isort = "6.0.0" -pep8-naming = "0.13.3" +isort = "5.12.0"  pip-licenses = "4.3.1"  pre-commit = "3.3.1"  python-dotenv = "1.0.0" +ruff = "0.0.265"  taskipy = "1.10.4"  [tool.taskipy.tasks] @@ -60,3 +53,21 @@ combine_as_imports = true  line_length = 120  atomic = true  known_first_party = ["bot"] + +[tool.ruff] +target-version = "py311" +extend-exclude = [".cache"] +ignore = [ +    "ANN002", "ANN003", "ANN101", "ANN102", "ANN204", "ANN206", "ANN401", +    "B904", +    "C401", "C408", +    "D100", "D104", "D105", "D107", "D203", "D212", "D214", "D215", "D301", +    "D400", "D401", "D402", "D404", "D405", "D406", "D407", "D408", "D409", "D410", "D411", "D412", "D413", "D414", "D416", "D417", +    "E731", +    "RET504", +    "RUF005", +    "S311", +    "SIM102", "SIM108", +] +line-length = 120 +select = ["ANN", "B", "C4", "D", "DTZ", "E", "F", "ISC", "INT", "N", "PGH", "PIE", "Q", "RET", "RSE", "RUF", "S", "SIM", "T20", "TID", "UP", "W"] diff --git a/tox.ini b/tox.ini deleted file mode 100644 index 7906e6d9..00000000 --- a/tox.ini +++ /dev/null @@ -1,26 +0,0 @@ -[flake8] -max-line-length=120 -application_import_names=bot -docstring-convention=all -extend-ignore= -    P102,B311,W503,E226,S311, -    # Missing Docstrings -    D100,D104,D105,D107, -    # Docstring Whitespace -    D203,D212,D214,D215, -    # Docstring Quotes -    D301,D302, -    # Docstring Content -    D400,D401,D402,D404,D405,D406,D407,D408,D409,D410,D411,D412,D413,D414,D416,D417, -    # Type Annotations -    ANN002,ANN003,ANN101,ANN102,ANN204,ANN206, -    # Binary operators over multiple lines -    W504, -exclude= -    __pycache__,.cache, -    venv,.venv, -    tests, -per-file-ignores = -    # Don't require docstrings in constants -    constants.py:D101 -import-order-style=pycharm  |