Skip to content

Commit 1fb0681

Browse files
authored
Release v2.1.0
2 parents 875ca7f + 00f96fb commit 1fb0681

File tree

12 files changed

+307
-136
lines changed

12 files changed

+307
-136
lines changed

.dependabot/config.yml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,3 +15,5 @@ update_configs:
1515
dependency_name: "pytest*"
1616
- match:
1717
dependency_name: "tox"
18+
- match:
19+
dependency_name: "pep8-naming"

CHANGELOG.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,10 @@
11
# Changelog
22
Versions follow [Semantic Versioning](https://semver.org/spec/v2.0.0.html) (`<major>`.`<minor>`.`<patch>`)
33

4+
## [v2.1.0]
5+
### Added
6+
* #68 Add `--suppress-dummy-args` configuration option to suppress ANN000 level errors for dummy arguments, defined as `"_"`
7+
48
## [v2.0.1]
59
### Added
610
* #71 Add `pep8-naming` to linting toolchain

CONTRIBUTING.md

Lines changed: 25 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -10,12 +10,12 @@ Note that contributions may be rejected on the basis of a contributor failing to
1010
2. If you have direct access to the repository, **create a branch for your changes** and create a pull request for that branch. If not, create a branch on a fork of the repository and create a pull request from there.
1111
* It's common practice for a repository to reject direct pushes to `master`, so make branching a habit!
1212
* If PRing from your own fork, **ensure that "Allow edits from maintainers" is checked**. This gives permission for maintainers to commit changes directly to your fork, speeding up the review process.
13-
3. **Adhere to the prevailing code style**, which we enforce using [flake8](http://flake8.pycqa.org/en/latest/index.html).
14-
* Run `flake8` against your code **before** you push it. Your commit will be rejected by the build server if it fails to lint.
15-
* [Git Hooks](https://git-scm.com/book/en/v2/Customizing-Git-Git-Hooks) are a powerful tool that can be a daunting to set up. Fortunately, [`pre-commit`](https://github.com/pre-commit/pre-commit) abstracts this process away from you and is provided as a dev dependency for this project. Run `pre-commit install` when setting up the project and you'll never have to worry about breaking the build for linting errors.
13+
3. **Adhere to the prevailing code style**, which we enforce using [`flake8`](http://flake8.pycqa.org/en/latest/index.html), [`black`](https://black.readthedocs.io/en/stable/), and [`pre-commit`](https://pre-commit.com/).
14+
* Run `flake8` and `pre-commit` against your code [**before** you push it](https://soundcloud.com/lemonsaurusrex/lint-before-you-push). Your commit will be rejected by the build server if it fails to lint.
15+
* [Git Hooks](https://git-scm.com/book/en/v2/Customizing-Git-Git-Hooks) are a powerful git feature for executing custom scripts when certain important git actions occur. The pre-commit hook is the first hook executed during the commit process and can be used to check the code being committed & abort the commit if issues, such as linting failures, are detected. While git hooks can seem daunting to configure, the `pre-commit` framework abstracts this process away from you and is provided as a dev dependency for this project. Run `pre-commit install` when setting up the project and you'll never have to worry about committing code that fails linting.
1616
4. **Make great commits**. A well structured git log is key to a project's maintainability; it efficiently provides insight into when and *why* things were done for future maintainers of the project.
1717
* Commits should be as narrow in scope as possible. Commits that span hundreds of lines across multiple unrelated functions and/or files are very hard for maintainers to follow. After about a week they'll probably be hard for you to follow too.
18-
* Try to avoid making minor commits for fixing typos or linting errors. Since you've already set up a pre-commit hook to run `flake8` before a commit, you shouldn't be committing linting issues anyway.
18+
* Avoid making minor commits for fixing typos or linting errors. Since you've already set up a `pre-commit` hook to run the linting pipeline before a commit, you shouldn't be committing linting issues anyway.
1919
* A more in-depth guide to writing great commit messages can be found in Chris Beam's [*How to Write a Git Commit Message*](https://chris.beams.io/posts/git-commit/)
2020
5. **Avoid frequent pushes to the main repository**. This goes for PRs opened against your fork as well. Our test build pipelines are triggered every time a push to the repository (or PR) is made. Try to batch your commits until you've finished working for that session, or you've reached a point where collaborators need your commits to continue their own work. This also provides you the opportunity to amend commits for minor changes rather than having to commit them on their own because you've already pushed.
2121
* This includes merging master into your branch. Try to leave merging from master for after your PR passes review; a maintainer will bring your PR up to date before merging. Exceptions to this include: resolving merge conflicts, needing something that was pushed to master for your branch, or something was pushed to master that could potentionally affect the functionality of what you're writing.
@@ -24,11 +24,10 @@ Note that contributions may be rejected on the basis of a contributor failing to
2424
* One option is to fork the other contributor's repository and submit your changes to their branch with your own pull request. We suggest following these guidelines when interacting with their repository as well.
2525
* The author(s) of inactive PRs and claimed issues will be be pinged after a week of inactivity for an update. Continued inactivity may result in the issue being released back to the community and/or PR closure.
2626
8. **Work as a team** and collaborate wherever possible. Keep things friendly and help each other out - these are shared projects and nobody likes to have their feet trodden on.
27-
9. **Internal projects are internal**. As a contributor, you have access to information that the rest of the server does not. With this trust comes responsibility - do not release any information you have learned as a result of your contributor position. We are very strict about announcing things at specific times, and many staff members will not appreciate a disruption of the announcement schedule.
28-
10. All static content, such as images or audio, **must be licensed for open public use**.
27+
9. All static content, such as images or audio, **must be licensed for open public use**.
2928
* Static content must be hosted by a service designed to do so. Failing to do so is known as "leeching" and is frowned upon, as it generates extra bandwidth costs to the host without providing benefit. It would be best if appropriately licensed content is added to the repository itself so it can be served by PyDis' infrastructure.
3029

31-
Above all, the needs of our community should come before the wants of an individual. Work together, build solutions to problems and try to do so in a way that people can learn from easily. Abuse of our trust may result in the loss of your Contributor role, especially in relation to Rule 9.
30+
Above all, the needs of our community should come before the wants of an individual. Work together, build solutions to problems and try to do so in a way that people can learn from easily. Abuse of our trust may result in the loss of your Contributor role.
3231

3332
## Changes to this Arrangement
3433

@@ -39,15 +38,19 @@ All projects evolve over time, and this contribution guide is no different. This
3938
When pulling down changes from GitHub, **remember to sync your environment** using `poetry install` to ensure you're using the most up-to-date versions the project's dependencies.
4039

4140
### Type Hinting
42-
[PEP 484](https://www.python.org/dev/peps/pep-0484/) formally specifies type hints for Python functions, added to the Python Standard Library in version 3.5. Type hints are recognized by most modern code editing tools and provide useful insight into both the input and output types of a function, preventing the user from having to go through the codebase to determine these types.
41+
[PEP 484](https://www.python.org/dev/peps/pep-0484/) formally specifies type hints for Python functions, added to the Python Standard Library in version 3.5. Type hints are recognized by most modern code editing tools and provide useful insight into both the input and output types of a function, preventing the user from having to go through the codebase to determine these types.
4342

4443
For example:
4544

4645
```py
47-
def foo(input_1: int, input_2: dict) -> bool:
46+
import typing as t
47+
48+
49+
def foo(input_1: int, input_2: t.Dict[str, str]) -> bool:
50+
...
4851
```
4952

50-
Tells us that `foo` accepts an `int` and a `dict` and returns a `bool`.
53+
Tells us that `foo` accepts an `int` and a `dict`, with `str` keys and values, and returns a `bool`.
5154

5255
All function declarations should be type hinted in code contributed to the PyDis organization.
5356

@@ -59,41 +62,40 @@ Many documentation packages provide support for automatic documentation generati
5962
For example:
6063

6164
```py
62-
def foo(bar: int, baz: dict=None) -> bool:
65+
import typing as t
66+
67+
68+
def foo(bar: int, baz: t.Optional[t.Dict[str, str]] = None) -> bool:
6369
"""
6470
Does some things with some stuff.
6571
6672
:param bar: Some input
67-
:param baz: Optional, some other input
73+
:param baz: Optional, some dictionary with string keys and values
6874
6975
:return: Some boolean
7076
"""
77+
...
7178
```
7279

7380
Since PyDis does not utilize automatic documentation generation, use of this syntax should not be used in code contributed to the organization. Should the purpose and type of the input variables not be easily discernable from the variable name and type annotation, a prose explanation can be used. Explicit references to variables, functions, classes, etc. should be wrapped with backticks (`` ` ``).
7481

7582
For example, the above docstring would become:
7683

7784
```py
78-
def foo(bar: int, baz: dict=None) -> bool:
85+
import typing as t
86+
87+
88+
def foo(bar: int, baz: t.Optional[t.Dict[str, str]] = None) -> bool:
7989
"""
8090
Does some things with some stuff.
8191
8292
This function takes an index, `bar` and checks for its presence in the database `baz`, passed as a dictionary. Returns `False` if `baz` is not passed.
8393
"""
94+
...
8495
```
8596

86-
### Logging Levels
87-
The project currently defines [`logging`](https://docs.python.org/3/library/logging.html) levels as follows:
88-
* **TRACE:** Use this for tracing every step of a complex process. That way we can see which step of the process failed. Err on the side of verbose. **Note:** This is a PyDis-implemented logging level.
89-
* **DEBUG:** Someone is interacting with the application, and the application is behaving as expected.
90-
* **INFO:** Something completely ordinary happened. Like a cog loading during startup.
91-
* **WARNING:** Someone is interacting with the application in an unexpected way or the application is responding in an unexpected way, but without causing an error.
92-
* **ERROR:** An error that affects the specific part that is being interacted with
93-
* **CRITICAL:** An error that affects the whole application.
94-
9597
### Work in Progress (WIP) PRs
96-
Github [has introduced a new PR feature](https://github.blog/2019-02-14-introducing-draft-pull-requests/) that allows the PR author to mark it as a WIP. This provides both a visual and functional indicator that the contents of the PR are in a draft state and not yet ready for formal review.
98+
Github [provides a PR feature](https://github.blog/2019-02-14-introducing-draft-pull-requests/) that allows the PR author to mark it as a WIP. This provides both a visual and functional indicator that the contents of the PR are in a draft state and not yet ready for formal review.
9799

98100
This feature should be utilized in place of the traditional method of prepending `[WIP]` to the PR title.
99101

README.md

Lines changed: 18 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -23,10 +23,12 @@ You can verify it's being picked up by invoking the following in your shell:
2323

2424
```bash
2525
$ flake8 --version
26-
3.7.8 (flake8-annotations: 2.0.1, mccabe: 0.6.1, pycodestyle: 2.5.0, pyflakes: 2.1.1) CPython 3.7.4 on Darwin
26+
3.7.8 (flake8-annotations: 2.1.0, mccabe: 0.6.1, pycodestyle: 2.5.0, pyflakes: 2.1.1) CPython 3.7.4 on Darwin
2727
```
2828

2929
## Table of Warnings
30+
All warnings are enabled by default.
31+
3032
### Function Annotations
3133
| ID | Description |
3234
|----------|-----------------------------------------------|
@@ -35,10 +37,10 @@ $ flake8 --version
3537
| `ANN003` | Missing type annotation for `**kwargs` |
3638

3739
### Method Annotations
38-
| ID | Description |
39-
|----------|----------------------------------------------------|
40-
| `ANN101` | Missing type annotation for `self` in method |
41-
| `ANN102` | Missing type annotation for `cls` in classmethod |
40+
| ID | Description |
41+
|----------|--------------------------------------------------------------|
42+
| `ANN101` | Missing type annotation for `self` in method<sup>1</sup> |
43+
| `ANN102` | Missing type annotation for `cls` in classmethod<sup>1</sup> |
4244

4345
### Return Annotations
4446
| ID | Description |
@@ -55,15 +57,25 @@ $ flake8 --version
5557
|----------|-----------------------------------------------------------|
5658
| `ANN301` | PEP 484 disallows both type annotations and type comments |
5759

60+
**Notes:**
61+
1. See: [PEP 484](https://www.python.org/dev/peps/pep-0484/#annotating-instance-and-class-methods) and [PEP 563](https://www.python.org/dev/peps/pep-0563/) for suggestions on annotating `self` and `cls` arguments.
62+
5863

5964
## Configuration Options
65+
Some opinionated flags are provided to tailor the linting errors emitted:
66+
6067
### `--suppress-none-returning`: `bool`
6168
Suppress `ANN200`-level errors for functions that meet one of the following criteria:
6269
* Contain no `return` statement, or
6370
* Explicit `return` statement(s) all return `None` (explicitly or implicitly).
6471

6572
Default: `False`
6673

74+
### `--suppress-dummy-args`: `bool`
75+
Suppress `ANN000`-level errors for dummy arguments, defined as `_`.
76+
77+
Default: `False`
78+
6779

6880
## Caveats for PEP 484-style Type Comments
6981
### Function type comments
@@ -92,7 +104,7 @@ def foo(
92104
pass
93105
```
94106

95-
Ellipes are ignored by `flake8-annotations` parser.
107+
Ellipses are ignored by `flake8-annotations` parser.
96108

97109
**Note:** If present, function type comments will override any argument type comments.
98110

azure-pipelines.yml

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,10 +21,12 @@ jobs:
2121
PIP_CACHE_DIR: ".cache/pip"
2222
PIP_SRC: ".cache/src"
2323
POETRY_VIRTUALENVS_CREATE: false
24+
PRE_COMMIT_HOME: $(Pipeline.Workspace)/pre-commit-cache
2425

2526
steps:
2627
- task: UsePythonVersion@0
2728
displayName: 'Set Python version'
29+
name: PythonVersion
2830
inputs:
2931
versionSpec: '$(python.version)'
3032
addToPath: true
@@ -35,8 +37,20 @@ jobs:
3537
- script: python3 -m pip install poetry && poetry install
3638
displayName: 'Install Project Environment'
3739

38-
- script: flake8
39-
displayName: 'Lint flake8-annotations'
40+
- task: Cache@2
41+
displayName: 'Restore pre-commit environment'
42+
condition: and(succeeded(), eq(variables['python.version'], '3.8'))
43+
inputs:
44+
key: pre-commit | "$(PythonVersion.pythonLocation)" | .pre-commit-config.yaml
45+
restoreKeys: |
46+
pre-commit | "$(PythonVersion.pythonLocation)"
47+
path: $(PRE_COMMIT_HOME)
48+
49+
# This will also take care of linting, as we utilize a flake8 hook
50+
# Only run this in one python environment
51+
- script: pre-commit run --all-files
52+
condition: and(succeeded(), eq(variables['python.version'], '3.8'))
53+
displayName: 'Run pre-commit hooks'
4054

4155
- script: tox -e $(tox.env)
4256
displayName: 'Test & generate coverage'

flake8_annotations/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717

1818
PY_GTE_38 = False
1919

20-
__version__ = "2.0.1"
20+
__version__ = "2.1.0"
2121

2222
AST_ARG_TYPES = ("args", "vararg", "kwonlyargs", "kwarg")
2323
if PY_GTE_38:

flake8_annotations/checker.py

Lines changed: 21 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,10 @@ def __init__(self, tree: ast.Module, lines: List[str]):
3434
# Request `lines` here and join to allow for correct handling of input from stdin
3535
self.lines = lines
3636
self.tree = self.get_typed_tree("".join(lines)) # flake8 doesn't strip newlines
37-
self.suppress_none_returning: bool # Set by flake8's config parser
37+
38+
# Set by flake8's config parser
39+
self.suppress_none_returning: bool
40+
self.suppress_dummy_args: bool
3841

3942
def run(self) -> Generator[FORMATTED_ERROR, None, None]:
4043
"""
@@ -75,12 +78,17 @@ def run(self) -> Generator[FORMATTED_ERROR, None, None]:
7578

7679
# Yield explicit errors for arguments that are missing annotations
7780
for arg in function.get_missed_annotations():
78-
# Skip yielding return errors if the `--suppress-none-returning` flag is True and
81+
# Skip yielding return errors if the `--suppress-none-returning` flag is `True` and
7982
# the function has only `None` returns (which includes the case of no returns)
8083
if arg.argname == "return" and self.suppress_none_returning:
8184
if not arg.has_type_annotation and function.has_only_none_returns:
8285
continue
8386

87+
# If the `--suppress-dummy-args` flag is `True`, skip yielding errors for any
88+
# arguments named `_`
89+
if arg.argname == "_" and self.suppress_dummy_args:
90+
continue
91+
8492
yield classify_error(function, arg).to_flake8()
8593

8694
@classmethod
@@ -97,10 +105,21 @@ def add_options(cls, parser: OptionManager) -> None:
97105
),
98106
)
99107

108+
parser.add_option(
109+
"--suppress-dummy-args",
110+
default=False,
111+
action="store_true",
112+
parse_from_config=True,
113+
help=(
114+
"Suppress ANN000-level errors for dummy arguments, defined as '_'. (Default: False)"
115+
),
116+
)
117+
100118
@classmethod
101119
def parse_options(cls, options: Namespace) -> None:
102120
"""Parse the custom configuration options given to flake8."""
103121
cls.suppress_none_returning = options.suppress_none_returning
122+
cls.suppress_dummy_args = options.suppress_dummy_args
104123

105124
@staticmethod
106125
def get_typed_tree(src: str) -> ast.Module:

0 commit comments

Comments
 (0)