Binary file not shown.
Binary file not shown.
@ -0,0 +1,22 @@
|
||||
[paths]
|
||||
source =
|
||||
pylint
|
||||
|
||||
[report]
|
||||
include =
|
||||
pylint/*
|
||||
omit =
|
||||
*/test/*
|
||||
exclude_also =
|
||||
# Debug-only code
|
||||
def __repr__
|
||||
|
||||
# Type checking code not executed during pytest runs
|
||||
if TYPE_CHECKING:
|
||||
@overload
|
||||
|
||||
# Abstract methods are not executed during pytest runs
|
||||
raise NotImplementedError()
|
||||
|
||||
# Fallback cases which should never be executed
|
||||
raise AssertionError
|
||||
@ -0,0 +1 @@
|
||||
3f2842400795ae1aaffc4ae6c35c4ef26857c239
|
||||
@ -0,0 +1,7 @@
|
||||
* text=auto
|
||||
tests/**/functional/** -text
|
||||
tests/input/** -text
|
||||
tests/**/data/** -text
|
||||
tests/regrtest_data/** -text
|
||||
doc/data/messages/u/unexpected-line-ending-format/bad.py -text
|
||||
doc/data/messages/m/mixed-line-endings/bad.py -text
|
||||
@ -0,0 +1,35 @@
|
||||
# Lines starting with '#' are comments.
|
||||
# Each line is a file pattern followed by one or more owners.
|
||||
|
||||
# These owners will be the default owners for everything in the repo.
|
||||
# Right now there is not default owner to avoid spam
|
||||
# * @pierre-sassoulas @DanielNoord @cdce8p @jacobtylerwalls @hippo91
|
||||
|
||||
# Order is important. The last matching pattern has the most precedence.
|
||||
|
||||
### Core components
|
||||
|
||||
# internal message handling
|
||||
pylint/message/* @pierre-sassoulas
|
||||
tests/message/* @pierre-sassoulas
|
||||
|
||||
# typing
|
||||
pylint/typing.py @DanielNoord
|
||||
|
||||
# multiprocessing (doublethefish is not yet a contributor with write access)
|
||||
# pylint/lint/parallel.py @doublethefish
|
||||
# tests/test_check_parallel.py @doublethefish
|
||||
|
||||
### Pyreverse
|
||||
pylint/pyreverse/* @DudeNr33
|
||||
tests/pyreverse/* @DudeNr33
|
||||
|
||||
### Extensions
|
||||
|
||||
# CodeStyle
|
||||
pylint/extensions/code_style.* @cdce8p
|
||||
tests/functional/ext/code_style/* @cdce8p
|
||||
|
||||
# Typing
|
||||
pylint/extensions/typing.* @cdce8p
|
||||
tests/functional/ext/typing/* @cdce8p
|
||||
@ -0,0 +1,2 @@
|
||||
Please read the
|
||||
[contribute doc](https://pylint.readthedocs.io/en/latest/development_guide/contributor_guide/contribute.html).
|
||||
@ -0,0 +1,3 @@
|
||||
# These are supported funding model platforms
|
||||
tidelift: "pypi/pylint"
|
||||
github: [cdce8p, DanielNoord, jacobtylerwalls,Pierre-Sassoulas]
|
||||
@ -0,0 +1,108 @@
|
||||
name: 🐛 Bug report
|
||||
description: Report a bug in pylint
|
||||
labels: ["Needs triage :inbox_tray:"]
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
**Thank you for wanting to report a bug in pylint!**
|
||||
|
||||
⚠ Please make sure that this [issue wasn't already requested][issue search], or already implemented in the main branch.
|
||||
|
||||
|
||||
[issue search]: https://github.com/pylint-dev/pylint/issues?q=is%3Aissue+is%3Aopen+
|
||||
|
||||
- type: textarea
|
||||
id: what-happened
|
||||
attributes:
|
||||
label: Bug description
|
||||
description:
|
||||
What is the bug about? Please provide the code that is causing the issue, and
|
||||
configurations used if required
|
||||
placeholder: |
|
||||
# Please disable message unrelated to the bug
|
||||
# pylint: disable=missing-docstring,
|
||||
<a> = b + 1
|
||||
render: python
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: configuration
|
||||
attributes:
|
||||
label: Configuration
|
||||
description:
|
||||
Please provide the part of the configuration that is causing the bug if required
|
||||
(Leave this part blank if the configuration is not relevant)
|
||||
placeholder: |
|
||||
# Leave this blank if the configuration is not relevant!
|
||||
|
||||
[MAIN]
|
||||
load-plugins=
|
||||
pylint.extensions.code_style
|
||||
|
||||
[MESSAGE CONTROL]
|
||||
enable=
|
||||
useless-suppression
|
||||
|
||||
# ...
|
||||
render: ini
|
||||
- type: textarea
|
||||
id: cmd-used
|
||||
attributes:
|
||||
label: Command used
|
||||
description: What was the command used to invoke pylint?
|
||||
placeholder: |
|
||||
pylint a.py
|
||||
render: shell
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: current-behavior
|
||||
attributes:
|
||||
label: Pylint output
|
||||
description: What is the current pylint output?
|
||||
placeholder: |
|
||||
************* Module a
|
||||
a.py:3:1: E0001: invalid syntax (<unknown>, line 1) (syntax-error)
|
||||
render: python
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: future-behavior
|
||||
attributes:
|
||||
label: Expected behavior
|
||||
description:
|
||||
What would you expect instead? For example expected output or behavior
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: python-interpreter
|
||||
attributes:
|
||||
label: Pylint version
|
||||
description: >-
|
||||
Please copy and paste the result of `pylint --version` or specify the range of
|
||||
versions affected.
|
||||
placeholder: |
|
||||
pylint 3.3.0
|
||||
astroid 3.3.0
|
||||
Python 3.12.0 (v3.12.0:0fb18b02c8, Oct 2 2023, 09:45:56)
|
||||
render: shell
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: OS / Environment
|
||||
description: >-
|
||||
Provide all relevant information below, e.g. OS version, terminal etc.
|
||||
placeholder: Fedora 33, Cygwin, etc.
|
||||
- type: textarea
|
||||
id: additional-deps
|
||||
attributes:
|
||||
label: Additional dependencies
|
||||
description:
|
||||
If applicable ie, if we can't reproduce without it. Please copy and paste the
|
||||
result of `pip freeze`.
|
||||
placeholder: |
|
||||
pandas==0.23.2
|
||||
marshmallow==3.10.0
|
||||
render: python
|
||||
@ -0,0 +1,45 @@
|
||||
name: ✨ Feature request
|
||||
description: Suggest an idea for pylint
|
||||
labels: ["Needs triage :inbox_tray:"]
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
**Thank you for wanting to make a suggestion for pylint!**
|
||||
|
||||
⚠ Please make sure that [this feature wasn't already requested][issue search] or already implemented in the main branch.
|
||||
|
||||
|
||||
[issue search]: https://github.com/pylint-dev/pylint/issues?q=is%3Aissue+is%3Aopen+
|
||||
|
||||
- type: textarea
|
||||
id: current-problem
|
||||
attributes:
|
||||
label: Current problem
|
||||
description:
|
||||
What are you trying to do, that you are unable to achieve with pylint as it
|
||||
currently stands?
|
||||
placeholder: >-
|
||||
I'm trying to do X and I'm missing feature Y for this to be easily achievable.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: proposed-solution
|
||||
attributes:
|
||||
label: Desired solution
|
||||
description: A clear and concise description of what you want to happen.
|
||||
placeholder: >-
|
||||
When I do X, I want to achieve Y in a situation when Z.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Additional context
|
||||
description: >
|
||||
Add any other context, links, etc. about the feature here. Describe how the
|
||||
feature would be used, why it is needed and what it would solve.
|
||||
|
||||
**HINT:** You can paste https://gist.github.com links for larger files.
|
||||
placeholder: >-
|
||||
I asked on https://stackoverflow.com/... and the community advised me to do X, Y
|
||||
and Z.
|
||||
@ -0,0 +1,49 @@
|
||||
name: 🤔 Support question
|
||||
description: Questions about pylint that are not covered in the documentation
|
||||
labels: ["Needs triage :inbox_tray:", "Question", "Documentation :green_book:"]
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: >
|
||||
**Thank you for wanting to report a problem with pylint documentation!**
|
||||
|
||||
|
||||
Please fill out your suggestions below. If the problem seems straightforward,
|
||||
feel free to go ahead and submit a pull request instead!
|
||||
|
||||
|
||||
⚠ Verify first that your issue is not [already reported on GitHub][issue
|
||||
search].
|
||||
|
||||
💬 If you are seeking community support, please consider [starting a discussion
|
||||
on Discord][Discussions].
|
||||
|
||||
|
||||
[issue search]:
|
||||
https://github.com/pylint-dev/pylint/issues?q=is%3Aissue+is%3Aopen+
|
||||
|
||||
[Discussions]: https://discord.com/invite/Egy6P8AMB5
|
||||
|
||||
- type: textarea
|
||||
id: question
|
||||
attributes:
|
||||
label: Question
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: documentation
|
||||
attributes:
|
||||
label: Documentation for future user
|
||||
description:
|
||||
Where did you expect this information to be? What do we need to add or what do
|
||||
we need to reorganize?
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Additional context
|
||||
description: >
|
||||
Add any other context, links, etc. about the question here.
|
||||
placeholder: >-
|
||||
I asked on https://stackoverflow.com/... and the community advised me to do X, Y
|
||||
and Z.
|
||||
@ -0,0 +1,5 @@
|
||||
blank_issues_enabled: true
|
||||
contact_links:
|
||||
- name: 💬 Discord
|
||||
url: https://discord.com/invite/Egy6P8AMB5
|
||||
about: Astroid and pylint informal dev discussion
|
||||
@ -0,0 +1,41 @@
|
||||
<!--
|
||||
Thank you for submitting a PR to pylint!
|
||||
|
||||
To ease the process of reviewing your PR, do make sure to complete the following boxes.
|
||||
|
||||
- [ ] Document your change, if it is a non-trivial one.
|
||||
- A maintainer might label the issue ``skip-news`` if the change does not need to be in the changelog.
|
||||
- Otherwise, create a news fragment with ``towncrier create <IssueNumber>.<type>`` which will be
|
||||
included in the changelog. ``<type>`` can be one of the types defined in `./towncrier.toml`.
|
||||
If necessary you can write details or offer examples on how the new change is supposed to work.
|
||||
- Generating the doc is done with ``tox -e docs``
|
||||
- [ ] Relate your change to an issue in the tracker if such an issue exists (Refs #1234, Closes #1234)
|
||||
- [ ] Write comprehensive commit messages and/or a good description of what the PR does.
|
||||
- [ ] Keep the change small, separate the consensual changes from the opinionated one.
|
||||
Don't hesitate to open multiple PRs if the change requires it. If your review is so
|
||||
big it requires to actually plan and allocate time to review, it's more likely
|
||||
that it's going to go stale.
|
||||
- [ ] If you used multiple emails or multiple names when contributing, add your mails
|
||||
and preferred name in ``script/.contributors_aliases.json``
|
||||
-->
|
||||
|
||||
## Type of Changes
|
||||
|
||||
<!-- Leave the corresponding lines for the applicable type of change: -->
|
||||
|
||||
| | Type |
|
||||
| --- | ---------------------- |
|
||||
| ✓ | :bug: Bug fix |
|
||||
| ✓ | :sparkles: New feature |
|
||||
| ✓ | :hammer: Refactoring |
|
||||
| ✓ | :scroll: Docs |
|
||||
|
||||
## Description
|
||||
|
||||
<!-- If this PR references an issue without fixing it: -->
|
||||
|
||||
Refs #XXXX
|
||||
|
||||
<!-- If this PR fixes an issue, use the following to automatically close when we merge: -->
|
||||
|
||||
Closes #XXXX
|
||||
@ -0,0 +1 @@
|
||||
Coordinated Disclosure Plan: https://tidelift.com/security
|
||||
@ -0,0 +1,255 @@
|
||||
# Pylint Development Instructions
|
||||
|
||||
Always follow these instructions first and fallback to additional search and context
|
||||
gathering only if the information in these instructions is incomplete or found to be in
|
||||
error.
|
||||
|
||||
## Issue Label Guidelines
|
||||
|
||||
Before attempting to fix any issue, check the GitHub issue labels using the GitHub API:
|
||||
|
||||
- If an issue is labeled with "Astroid", "Needs astroid update", "Needs astroid
|
||||
constraint", or "Needs astroid Brain 🧠", **ONLY** create regression tests
|
||||
- Do **NOT** attempt to fix astroid-related issues as you cannot modify astroid from
|
||||
this repository
|
||||
- For astroid-related issues, focus on creating comprehensive regression tests that
|
||||
reproduce the problem
|
||||
- All other issues can be fixed normally following the standard development workflow
|
||||
|
||||
## Development Environment Setup
|
||||
|
||||
### Basic Installation
|
||||
|
||||
Clone and set up pylint development environment:
|
||||
|
||||
- `git clone https://github.com/pylint-dev/pylint` -- clone repository
|
||||
- `cd pylint` -- enter directory
|
||||
- `python3 -m venv venv` -- create virtual environment
|
||||
- `source venv/bin/activate` -- activate virtual environment (Linux/Mac)
|
||||
- `pip install -r requirements_test_min.txt` -- install test dependencies (~30 seconds)
|
||||
- `pip install -e .` -- install pylint in editable mode (~30-60 seconds)
|
||||
|
||||
### Optional Setup Steps
|
||||
|
||||
- `pre-commit install` -- enable pre-commit hooks for autoformatting
|
||||
- `pip install pre-commit` -- install pre-commit separately if needed
|
||||
|
||||
### Astroid Development (if needed)
|
||||
|
||||
If working on astroid changes:
|
||||
|
||||
- `git clone https://github.com/pylint-dev/astroid.git` -- clone astroid
|
||||
- `pip install -e astroid/` -- install astroid in editable mode
|
||||
- `cd astroid/ && git switch my-astroid-dev-branch` -- switch to development branch
|
||||
|
||||
## Running Tests
|
||||
|
||||
### Core Test Commands
|
||||
|
||||
- `pytest tests/test_functional.py -k test_functional` -- run functional tests (~60
|
||||
seconds, NEVER CANCEL, set timeout to 120+ seconds)
|
||||
- `pytest tests/` -- run all tests (several minutes, NEVER CANCEL, set timeout to 300+
|
||||
seconds)
|
||||
- `python3 -m pytest` -- run tests with local python
|
||||
- `pytest tests/test_check_parallel.py -v` -- quick test file (~2 seconds)
|
||||
|
||||
### Specific Test Types
|
||||
|
||||
- **Functional tests:**
|
||||
`pytest "tests/test_functional.py::test_functional[missing_kwoa_py3]"` -- single
|
||||
functional test (~1 second)
|
||||
- **Unit tests:** Located in `/tests/` directory, test specific pylint functionality
|
||||
- **Configuration tests:** In `/tests/config/functional/` for testing configuration
|
||||
loading
|
||||
- **Primer tests:** `pytest -m primer_stdlib --primer-stdlib` -- test on stdlib for
|
||||
crashes
|
||||
|
||||
### Test with Coverage
|
||||
|
||||
- `pytest tests/message/ --cov=pylint.message` -- run with coverage
|
||||
- `coverage html` -- generate HTML coverage report
|
||||
|
||||
### Tox Usage (Optional)
|
||||
|
||||
- `python -m tox` -- run all tox environments
|
||||
- `python -m tox -epy313` -- run Python 3.13 suite only
|
||||
- `python -m tox -epylint` -- run pylint on pylint's codebase
|
||||
- `python -m tox -eformatting` -- run formatting checks
|
||||
- `python -m tox --recreate` -- recreate environments (recommended)
|
||||
- `python -m tox -e py310 -- -k test_functional` -- run specific tests in tox
|
||||
|
||||
## Documentation
|
||||
|
||||
### Building Documentation
|
||||
|
||||
- `make -C doc/ install-dependencies` -- install doc dependencies (~10 seconds)
|
||||
- `make -C doc/ html` -- build documentation (~3 minutes, NEVER CANCEL, set timeout to
|
||||
300+ seconds)
|
||||
- `make -C doc/ clean` -- clean build files when starting from scratch
|
||||
- `tox -e docs` -- alternative way to build docs
|
||||
|
||||
**Network dependency:** Documentation build requires internet access to fetch external
|
||||
inventories.
|
||||
|
||||
## Validation and Quality Checks
|
||||
|
||||
### Running Pylint on Code
|
||||
|
||||
- `pylint --help` -- verify pylint installation works
|
||||
- `pylint --disable=all --enable=E,F pylint/` -- run pylint on itself for errors only
|
||||
(~20 seconds)
|
||||
- `pylint --rcfile=pylintrc --fail-on=I path/to/your/changes.py` -- standard pylint run
|
||||
- `pylint --disable=all --enable=E,F,W path/to/your/changes.py` -- focus on errors and
|
||||
warnings
|
||||
|
||||
### Pre-commit and Formatting
|
||||
|
||||
- `pre-commit run --all-files` -- run all formatting checks (requires network for
|
||||
initial setup)
|
||||
- **Network dependency:** pre-commit may fail in isolated environments due to hook
|
||||
downloads
|
||||
|
||||
### Validation Test Scenarios
|
||||
|
||||
Always test your changes with these validation scenarios:
|
||||
|
||||
- `echo "def badFunction(): pass" > /tmp/test_sample.py && pylint --enable=C0103 /tmp/test_sample.py`
|
||||
-- should find naming issues
|
||||
- `pylint --help` and `pylint --list-msgs | head -10` -- verify CLI functionality
|
||||
- `pylint --help-msg=C0103` -- should show invalid-name help
|
||||
- `pylint --rcfile=pylintrc --fail-on=I pylint/__init__.py` -- should get 10.00/10
|
||||
rating
|
||||
|
||||
## Writing Tests
|
||||
|
||||
### Functional Tests
|
||||
|
||||
Located in `/tests/functional/`, consists of `.py` test files with corresponding `.txt`
|
||||
expected output files:
|
||||
|
||||
- Annotate lines where messages are expected:
|
||||
`a, b, c = 1 # [unbalanced-tuple-unpacking]`
|
||||
- Multiple messages on same line:
|
||||
`a, b, c = 1.test # [unbalanced-tuple-unpacking, no-member]`
|
||||
- Use offset syntax for special cases: `# +1: [singleton-comparison]`
|
||||
- **Run and update:**
|
||||
`python tests/test_functional.py --update-functional-output -k "test_functional[test_name]"`
|
||||
|
||||
### Test File Organization
|
||||
|
||||
- **New checkers:** Create `new_checker_message.py` in `/tests/functional/n/`
|
||||
- **Extensions:** Place in `/tests/functional/ext/extension_name/`
|
||||
- **Regression tests:** Place in `/tests/r/regression/` with `regression_` prefix
|
||||
- **Configuration tests:** Place in `/tests/config/functional/`
|
||||
|
||||
### Configuration Test Files
|
||||
|
||||
Create `.result.json` files with configuration differences from standard config:
|
||||
|
||||
```json
|
||||
{
|
||||
"functional_append": {
|
||||
"disable": [["a-message-to-be-added"]]
|
||||
},
|
||||
"jobs": 10
|
||||
}
|
||||
```
|
||||
|
||||
## Codebase Structure
|
||||
|
||||
```
|
||||
pylint/ # Main package
|
||||
├── checkers/ # All pylint checkers (rules implementation)
|
||||
├── config/ # Configuration handling and parsing
|
||||
├── message/ # Message system and formatting
|
||||
├── reporters/ # Output formatters (text, json, etc.)
|
||||
├── testutils/ # Testing utilities and helpers
|
||||
└── extensions/ # Optional extensions and plugins
|
||||
|
||||
tests/ # Test suite
|
||||
├── functional/ # Functional test files (.py + .txt expected output)
|
||||
├── config/functional/ # Configuration functional tests
|
||||
├── r/regression/ # Regression tests
|
||||
├── test_*.py # Unit tests
|
||||
└── regrtest_data/ # Test data files
|
||||
|
||||
doc/ # Documentation
|
||||
├── user_guide/ # User documentation
|
||||
├── development_guide/ # Developer and contributor documentation
|
||||
│ ├── contributor_guide/ # Setup, testing, contribution guidelines
|
||||
│ ├── technical_reference/ # Technical implementation details
|
||||
│ └── how_tos/ # Guides for custom checkers, plugins
|
||||
└── additional_tools/ # Tools documentation
|
||||
|
||||
script/ # Development utility scripts
|
||||
```
|
||||
|
||||
### Key Files
|
||||
|
||||
- `pyproject.toml` -- Main configuration (dependencies, build, tools)
|
||||
- `tox.ini` -- Multi-environment testing configuration
|
||||
- `.pre-commit-config.yaml` -- Code quality checks configuration
|
||||
- `pylintrc` -- Pylint's own configuration
|
||||
- `requirements_test_min.txt` -- Minimal test dependencies
|
||||
- `.gitignore` do not add the 'venv' inside the .gitignore, don't commit the venv in the
|
||||
first place (humans add it to their global gitignore)
|
||||
|
||||
## Creating New Checkers
|
||||
|
||||
### Getting Started
|
||||
|
||||
- `python script/get_unused_message_id_category.py` -- get next available message ID
|
||||
- Study existing checkers in `pylint/checkers/` for patterns
|
||||
- Read technical reference documentation in `doc/development_guide/technical_reference/`
|
||||
- Use `astroid.extract_node` for AST manipulation
|
||||
|
||||
### Workflow
|
||||
|
||||
1. Create checker class in appropriate `pylint/checkers/` file
|
||||
2. Add functional tests in `tests/functional/`
|
||||
3. Search existing code for warning message to find where logic exists
|
||||
4. Test with sample code to ensure functionality works
|
||||
|
||||
## Pull Request Guidelines
|
||||
|
||||
### Before Submitting
|
||||
|
||||
- Use Python 3.8+ for development (required for latest AST parser and pre-commit hooks)
|
||||
- Write comprehensive commit messages relating to tracker issues
|
||||
- Keep changes small and separate consensual from opinionated changes
|
||||
- Add news fragment: `towncrier create <IssueNumber>.<type>`
|
||||
- Always launch `pre-commit run -a` before committing
|
||||
|
||||
### Documentation Changes
|
||||
|
||||
- Document non-trivial changes
|
||||
- Generate docs with `tox -e docs`
|
||||
- Maintainers may label issues `skip-news` if no changelog needed
|
||||
|
||||
### Contribution Credits
|
||||
|
||||
- Add emails/names to `script/.contributors_aliases.json` if using multiple identities
|
||||
|
||||
## Critical Timing Information
|
||||
|
||||
- **NEVER CANCEL:** All operations that show "NEVER CANCEL" may take significant time
|
||||
- **Full test suite:** 60+ seconds (set timeout to 120+ seconds)
|
||||
- **Documentation build:** 180 seconds (set timeout to 300+ seconds)
|
||||
- **Functional tests:** 60 seconds (set timeout to 120+ seconds)
|
||||
- **Pylint self-check:** 20 seconds (set timeout to 60+ seconds)
|
||||
- **Individual test files:** 1-15 seconds
|
||||
- **Installation steps:** 30-60 seconds each
|
||||
|
||||
## Environment Limitations and Workarounds
|
||||
|
||||
- **Network connectivity required:** Documentation build and pre-commit setup require
|
||||
internet access
|
||||
- **Tox failures:** In isolated environments, use direct pytest and pip commands instead
|
||||
of tox
|
||||
- **Import errors in self-check:** Some import errors when running pylint on itself are
|
||||
expected (git dependencies not installed)
|
||||
- **Build environments:** Use direct pip/pytest commands when tox environments fail to
|
||||
build
|
||||
|
||||
Always validate your changes by running pylint on sample code to ensure functionality
|
||||
works correctly.
|
||||
@ -0,0 +1,21 @@
|
||||
version: 2
|
||||
updates:
|
||||
- package-ecosystem: "pip"
|
||||
directory: "/"
|
||||
schedule:
|
||||
interval: "weekly"
|
||||
labels:
|
||||
- "dependency"
|
||||
- "Skip news :mute:"
|
||||
open-pull-requests-limit: 10
|
||||
rebase-strategy: "disabled"
|
||||
|
||||
- package-ecosystem: "github-actions"
|
||||
directory: "/"
|
||||
schedule:
|
||||
interval: "weekly"
|
||||
labels:
|
||||
- "dependency"
|
||||
- "Skip news :mute:"
|
||||
open-pull-requests-limit: 10
|
||||
rebase-strategy: "disabled"
|
||||
@ -0,0 +1,40 @@
|
||||
name: Backport
|
||||
on:
|
||||
pull_request_target:
|
||||
types:
|
||||
- closed
|
||||
- labeled
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
backport:
|
||||
name: Backport
|
||||
runs-on: ubuntu-latest
|
||||
environment:
|
||||
name: Backport
|
||||
# Only react to merged PRs for security reasons.
|
||||
# See https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#pull_request_target.
|
||||
if: >
|
||||
github.event.pull_request.merged && (
|
||||
github.event.action == 'closed'
|
||||
|| (
|
||||
github.event.action == 'labeled'
|
||||
&& contains(github.event.label.name, 'backport')
|
||||
)
|
||||
)
|
||||
steps:
|
||||
- uses: actions/create-github-app-token@67018539274d69449ef7c02e8e71183d1719ab42 # v2.1.4
|
||||
id: app-token
|
||||
with:
|
||||
app-id: ${{ vars.BACKPORT_APP_ID }}
|
||||
private-key: ${{ secrets.PRIVATE_KEY }}
|
||||
permission-contents: write # push branch to Github
|
||||
permission-pull-requests: write # create PR / add comment for manual backport
|
||||
permission-workflows: write # modify files in .github/workflows
|
||||
- uses: pylint-dev/backport@94367840595495e101f9a31415897c05da1f08d9 # v2.1.1
|
||||
with:
|
||||
github_token: ${{ steps.app-token.outputs.token }}
|
||||
user_name: ${{ vars.BACKPORT_USER_NAME }}
|
||||
user_email: ${{ vars.BACKPORT_USER_EMAIL }}
|
||||
@ -0,0 +1,65 @@
|
||||
name: changelog
|
||||
|
||||
on:
|
||||
pull_request:
|
||||
types: [opened, synchronize, labeled, unlabeled, reopened]
|
||||
branches-ignore:
|
||||
- "maintenance/**"
|
||||
env:
|
||||
CACHE_VERSION: 1
|
||||
KEY_PREFIX: base-venv
|
||||
DEFAULT_PYTHON: "3.13"
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
check-changelog:
|
||||
if: contains(github.event.pull_request.labels.*.name, 'skip news :mute:') != true
|
||||
name: Changelog Entry Check
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 10
|
||||
steps:
|
||||
- name: Check out code from GitHub
|
||||
uses: actions/checkout@v5.0.0
|
||||
with:
|
||||
# `towncrier check` runs `git diff --name-only origin/main...`, which
|
||||
# needs a non-shallow clone.
|
||||
fetch-depth: 0
|
||||
- name: Set up Python ${{ env.DEFAULT_PYTHON }}
|
||||
id: python
|
||||
uses: actions/setup-python@v6.0.0
|
||||
with:
|
||||
python-version: ${{ env.DEFAULT_PYTHON }}
|
||||
check-latest: true
|
||||
- name: Generate partial Python venv restore key
|
||||
id: generate-python-key
|
||||
run: >-
|
||||
echo "key=${{ env.KEY_PREFIX }}-${{ env.CACHE_VERSION }}-${{
|
||||
hashFiles('pyproject.toml', 'requirements_test.txt',
|
||||
'requirements_test_min.txt', 'requirements_test_pre_commit.txt') }}" >>
|
||||
$GITHUB_OUTPUT
|
||||
- name: Restore Python virtual environment
|
||||
id: cache-venv
|
||||
uses: actions/cache@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
key: >-
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
steps.generate-python-key.outputs.key }}
|
||||
- name: Create Python virtual environment
|
||||
if: steps.cache-venv.outputs.cache-hit != 'true'
|
||||
run: |
|
||||
python -m venv venv
|
||||
. venv/bin/activate
|
||||
python -m pip install --upgrade pip
|
||||
pip install --upgrade --requirement requirements_test.txt --requirement doc/requirements.txt
|
||||
- name: Emit warning if news fragment is missing
|
||||
env:
|
||||
BASE_BRANCH: ${{ github.base_ref }}
|
||||
run: |
|
||||
# Fetch the pull request' base branch so towncrier will be able to
|
||||
# compare the current branch with the base branch.
|
||||
git fetch --no-tags origin +refs/heads/${BASE_BRANCH}:refs/remotes/origin/${BASE_BRANCH}
|
||||
. venv/bin/activate
|
||||
towncrier check --compare-with origin/${{ github.base_ref }}
|
||||
@ -0,0 +1,160 @@
|
||||
name: Checks
|
||||
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
- "maintenance/**"
|
||||
pull_request:
|
||||
branches:
|
||||
- main
|
||||
- "maintenance/**"
|
||||
workflow_dispatch:
|
||||
|
||||
env:
|
||||
CACHE_VERSION: 3
|
||||
KEY_PREFIX: base-venv
|
||||
DEFAULT_PYTHON: "3.13"
|
||||
PRE_COMMIT_CACHE: ~/.cache/pre-commit
|
||||
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
|
||||
cancel-in-progress: true
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
prepare-base:
|
||||
name: Prepare base dependencies
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 10
|
||||
outputs:
|
||||
python-key: ${{ steps.generate-python-key.outputs.key }}
|
||||
pre-commit-key: ${{ steps.generate-pre-commit-key.outputs.key }}
|
||||
steps:
|
||||
- &checkout
|
||||
name: Check out code from GitHub
|
||||
uses: actions/checkout@v5.0.0
|
||||
- &setup-python
|
||||
name: Set up Python ${{ env.DEFAULT_PYTHON }}
|
||||
id: python
|
||||
uses: actions/setup-python@v6.0.0
|
||||
with:
|
||||
python-version: ${{ env.DEFAULT_PYTHON }}
|
||||
check-latest: true
|
||||
- name: Generate partial Python venv restore key
|
||||
id: generate-python-key
|
||||
run: >-
|
||||
echo "key=${{ env.KEY_PREFIX }}-${{ env.CACHE_VERSION }}-${{
|
||||
hashFiles('pyproject.toml', 'requirements_test.txt',
|
||||
'requirements_test_min.txt', 'requirements_test_pre_commit.txt') }}" >>
|
||||
$GITHUB_OUTPUT
|
||||
- name: Restore Python virtual environment
|
||||
id: cache-venv
|
||||
uses: actions/cache@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
key: >-
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
steps.generate-python-key.outputs.key }}
|
||||
- name: Create Python virtual environment
|
||||
if: steps.cache-venv.outputs.cache-hit != 'true'
|
||||
run: |
|
||||
python -m venv venv
|
||||
. venv/bin/activate
|
||||
python -m pip install --upgrade pip
|
||||
pip install --upgrade --requirement requirements_test.txt --requirement doc/requirements.txt
|
||||
pip install pre-commit
|
||||
- name: Generate pre-commit restore key
|
||||
id: generate-pre-commit-key
|
||||
run: >-
|
||||
echo "key=pre-commit-${{ env.CACHE_VERSION }}-${{
|
||||
hashFiles('.pre-commit-config.yaml') }}" >> $GITHUB_OUTPUT
|
||||
- name: Restore pre-commit environment
|
||||
id: cache-precommit
|
||||
uses: actions/cache@v4.3.0
|
||||
with:
|
||||
path: ${{ env.PRE_COMMIT_CACHE }}
|
||||
key: >-
|
||||
${{ runner.os }}-${{ steps.generate-pre-commit-key.outputs.key }}
|
||||
- name: Install pre-commit dependencies
|
||||
if: steps.cache-precommit.outputs.cache-hit != 'true'
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
pre-commit install --install-hooks
|
||||
|
||||
pylint:
|
||||
name: pylint
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 10
|
||||
needs: [prepare-base]
|
||||
steps:
|
||||
- *checkout
|
||||
- *setup-python
|
||||
- &cache-restore-python
|
||||
name: Restore Python virtual environment
|
||||
id: cache-venv
|
||||
uses: actions/cache/restore@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
fail-on-cache-miss: true
|
||||
key:
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
needs.prepare-base.outputs.python-key }}
|
||||
- name: Restore pre-commit environment
|
||||
id: cache-precommit
|
||||
uses: actions/cache/restore@v4.3.0
|
||||
with:
|
||||
path: ${{ env.PRE_COMMIT_CACHE }}
|
||||
fail-on-cache-miss: true
|
||||
key: ${{ runner.os }}-${{ needs.prepare-base.outputs.pre-commit-key }}
|
||||
- name: Install enchant and aspell
|
||||
run: |
|
||||
sudo apt-get update
|
||||
sudo apt-get install enchant-2 aspell-en
|
||||
- name: Run pylint checks
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
pip install . --no-deps
|
||||
pip list | grep 'astroid\|pylint'
|
||||
pre-commit run --hook-stage manual pylint-with-spelling --all-files
|
||||
|
||||
spelling:
|
||||
name: spelling tests
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 5
|
||||
needs: [prepare-base]
|
||||
steps:
|
||||
- *checkout
|
||||
- *setup-python
|
||||
- *cache-restore-python
|
||||
- name: Run spelling checks
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
pip install . --no-deps
|
||||
pytest tests/ -k unittest_spelling --benchmark-disable
|
||||
|
||||
documentation:
|
||||
name: documentation
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 20
|
||||
needs: [prepare-base]
|
||||
steps:
|
||||
- *checkout
|
||||
- *setup-python
|
||||
- *cache-restore-python
|
||||
- name: Run checks on documentation code examples
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
tox -e test_doc
|
||||
- name: Check documentation build and links
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
tox -e docs || {
|
||||
echo "git diff:" ; \
|
||||
git diff ; \
|
||||
echo "End of 'git diff'" ; \
|
||||
echo "Make sure that 'tox -e docs' succeed without any modifications locally." ; \
|
||||
exit 1; \
|
||||
}
|
||||
@ -0,0 +1,95 @@
|
||||
name: Primer
|
||||
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
pull_request:
|
||||
paths:
|
||||
- "pylint/**"
|
||||
- "tests/primer/**"
|
||||
- "requirements*"
|
||||
- ".github/workflows/primer-test.yaml"
|
||||
branches:
|
||||
- main
|
||||
env:
|
||||
CACHE_VERSION: 4
|
||||
KEY_PREFIX: venv
|
||||
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
|
||||
cancel-in-progress: true
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
prepare-tests-linux:
|
||||
name: prepare / ${{ matrix.python-version }} / Linux
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 5
|
||||
strategy:
|
||||
matrix:
|
||||
python-version: &matrix-python-version ["3.10", "3.11", "3.12", "3.13", "3.14"]
|
||||
outputs:
|
||||
python-key: ${{ steps.generate-python-key.outputs.key }}
|
||||
steps:
|
||||
- &checkout
|
||||
name: Check out code from GitHub
|
||||
uses: actions/checkout@v5.0.0
|
||||
- &setup-python
|
||||
name: Set up Python ${{ matrix.python-version }}
|
||||
id: python
|
||||
uses: actions/setup-python@v6.0.0
|
||||
with:
|
||||
python-version: ${{ matrix.python-version }}
|
||||
allow-prereleases: true
|
||||
check-latest: true
|
||||
- name: Generate partial Python venv restore key
|
||||
id: generate-python-key
|
||||
run: >-
|
||||
echo "key=${{ env.KEY_PREFIX }}-${{ env.CACHE_VERSION }}-${{
|
||||
hashFiles('pyproject.toml', 'requirements_test.txt',
|
||||
'requirements_test_min.txt', 'requirements_test_pre_commit.txt') }}" >>
|
||||
$GITHUB_OUTPUT
|
||||
- name: Restore Python virtual environment
|
||||
id: cache-venv
|
||||
uses: actions/cache@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
key: >-
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
steps.generate-python-key.outputs.key }}
|
||||
- name: Create Python virtual environment
|
||||
if: steps.cache-venv.outputs.cache-hit != 'true'
|
||||
run: |
|
||||
python -m venv venv
|
||||
. venv/bin/activate
|
||||
python -m pip install --upgrade pip
|
||||
pip install --upgrade --requirement requirements_test.txt
|
||||
|
||||
pytest-primer-stdlib:
|
||||
name: run on stdlib / ${{ matrix.python-version }} / Linux
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 10
|
||||
needs: prepare-tests-linux
|
||||
strategy:
|
||||
matrix:
|
||||
python-version: *matrix-python-version
|
||||
steps:
|
||||
- *checkout
|
||||
- *setup-python
|
||||
- name: Restore Python virtual environment
|
||||
id: cache-venv
|
||||
uses: actions/cache/restore@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
fail-on-cache-miss: true
|
||||
key:
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
needs.prepare-tests-linux.outputs.python-key }}
|
||||
- name: Run pytest
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
pip install . --no-deps
|
||||
pytest -m primer_stdlib --primer-stdlib -n auto -vv --benchmark-disable
|
||||
@ -0,0 +1,125 @@
|
||||
# Most of this is inspired by the mypy primer
|
||||
# See: https://github.com/hauntsaninja/mypy_primer
|
||||
# This is the primer job that creates the comment on the PR
|
||||
# It needs to trigger on workflow_run instead of pull_request
|
||||
# as we need repository wide access to create a comment
|
||||
|
||||
name: Primer / Comment
|
||||
|
||||
on:
|
||||
workflow_run:
|
||||
workflows: [Primer / Run]
|
||||
types:
|
||||
- completed
|
||||
|
||||
env:
|
||||
# This needs to be the SAME as in the Main and PR job
|
||||
CACHE_VERSION: 4
|
||||
KEY_PREFIX: venv-primer
|
||||
# If you change this, also change PRIMER_CURRENT_INTERPRETER in
|
||||
# tests/testutils/_primer/test_primer.py
|
||||
DEFAULT_PYTHON: "3.13"
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
pull-requests: write
|
||||
|
||||
jobs:
|
||||
primer-comment:
|
||||
# Skip job if the workflow failed
|
||||
if: ${{ github.event.workflow_run.conclusion == 'success' }}
|
||||
name: Run
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Check out code from GitHub
|
||||
uses: actions/checkout@v5.0.0
|
||||
- name: Set up Python ${{ env.DEFAULT_PYTHON }}
|
||||
id: python
|
||||
uses: actions/setup-python@v6.0.0
|
||||
with:
|
||||
python-version: ${{ env.DEFAULT_PYTHON }}
|
||||
check-latest: true
|
||||
|
||||
# Restore cached Python environment
|
||||
- name: Restore Python virtual environment
|
||||
id: cache-venv
|
||||
uses: actions/cache@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
key:
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
env.KEY_PREFIX }}-${{ env.CACHE_VERSION }}-${{ hashFiles('pyproject.toml',
|
||||
'requirements_test.txt', 'requirements_test_min.txt',
|
||||
'requirements_test_pre_commit.txt') }}
|
||||
|
||||
- name: Download outputs
|
||||
uses: actions/github-script@v8.0.0
|
||||
with:
|
||||
script: |
|
||||
// Download workflow pylint output
|
||||
const fs = require('fs');
|
||||
const artifacts_workflow = await github.rest.actions.listWorkflowRunArtifacts({
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
run_id: ${{ github.event.workflow_run.id }},
|
||||
});
|
||||
|
||||
// Get 'main' and 'PR' outputs and PR number
|
||||
const artifacts = artifacts_workflow.data.artifacts.filter((artifact) =>
|
||||
artifact.name.startsWith(`primer_output_main_${process.env.DEFAULT_PYTHON}`)
|
||||
|| artifact.name.startsWith(`primer_output_pr_${process.env.DEFAULT_PYTHON}`)
|
||||
|| artifact.name === 'pr_number'
|
||||
);
|
||||
for (const artifact of artifacts) {
|
||||
const downloaded = await github.rest.actions.downloadArtifact({
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
artifact_id: artifact.id,
|
||||
archive_format: "zip",
|
||||
});
|
||||
fs.writeFileSync(`${artifact.name}.zip`, Buffer.from(downloaded.data));
|
||||
}
|
||||
|
||||
- name: Unzip outputs
|
||||
run: |
|
||||
unzip primer_output_main_${{ env.DEFAULT_PYTHON }}_batch0.zip
|
||||
unzip primer_output_main_${{ env.DEFAULT_PYTHON }}_batch1.zip
|
||||
unzip primer_output_main_${{ env.DEFAULT_PYTHON }}_batch2.zip
|
||||
unzip primer_output_main_${{ env.DEFAULT_PYTHON }}_batch3.zip
|
||||
unzip primer_output_pr_${{ env.DEFAULT_PYTHON }}_batch0.zip
|
||||
unzip primer_output_pr_${{ env.DEFAULT_PYTHON }}_batch1.zip
|
||||
unzip primer_output_pr_${{ env.DEFAULT_PYTHON }}_batch2.zip
|
||||
unzip primer_output_pr_${{ env.DEFAULT_PYTHON }}_batch3.zip
|
||||
unzip pr_number.zip
|
||||
- name: Compare outputs
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
python tests/primer/__main__.py compare \
|
||||
--commit=${{ github.event.workflow_run.head_sha }} \
|
||||
--base-file=output_${{ env.DEFAULT_PYTHON }}_main_BATCHIDX.txt \
|
||||
--new-file=output_${{ env.DEFAULT_PYTHON }}_pr_BATCHIDX.txt \
|
||||
--batches=4
|
||||
- name: Post comment
|
||||
id: post-comment
|
||||
uses: actions/github-script@v8.0.0
|
||||
with:
|
||||
script: |
|
||||
const fs = require('fs')
|
||||
const comment = fs.readFileSync('tests/.pylint_primer_tests/comment.txt', { encoding: 'utf8' })
|
||||
console.log("Comment to post:")
|
||||
console.log(comment)
|
||||
const prNumber = parseInt(fs.readFileSync("pr_number.txt", { encoding: "utf8" }))
|
||||
await github.rest.issues.createComment({
|
||||
issue_number: prNumber,
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
body: comment
|
||||
})
|
||||
return prNumber
|
||||
- name: Hide old comments
|
||||
# Taken from mypy primer
|
||||
uses: kanga333/comment-hider@c12bb20b48aeb8fc098e35967de8d4f8018fffdf # v0.4.0
|
||||
with:
|
||||
github_token: ${{ secrets.GITHUB_TOKEN }}
|
||||
leave_visible: 1
|
||||
issue_number: ${{ steps.post-comment.outputs.result }}
|
||||
@ -0,0 +1,132 @@
|
||||
# Most of this is inspired by the mypy primer
|
||||
# See: https://github.com/hauntsaninja/mypy_primer
|
||||
# This is the primer job that runs on the default 'main' branch
|
||||
# It is also responsible for caching the packages to prime on
|
||||
|
||||
name: Primer / Main
|
||||
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.ref }}
|
||||
cancel-in-progress: true
|
||||
|
||||
env:
|
||||
# This needs to be the SAME as in the PR and comment job
|
||||
CACHE_VERSION: 4
|
||||
KEY_PREFIX: venv-primer
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
run-primer:
|
||||
name: Run / ${{ matrix.python-version }} / batch index ${{ matrix.batchIdx }}
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 45
|
||||
strategy:
|
||||
matrix:
|
||||
python-version: ["3.10", "3.13"]
|
||||
batches: [4]
|
||||
batchIdx: [0, 1, 2, 3]
|
||||
steps:
|
||||
- name: Check out code from GitHub
|
||||
uses: actions/checkout@v5.0.0
|
||||
- name: Set up Python ${{ matrix.python-version }}
|
||||
id: python
|
||||
uses: actions/setup-python@v6.0.0
|
||||
with:
|
||||
python-version: ${{ matrix.python-version }}
|
||||
check-latest: true
|
||||
|
||||
# Create a re-usable virtual environment
|
||||
- name: Restore Python virtual environment cache
|
||||
id: cache-venv
|
||||
uses: actions/cache/restore@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
key:
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
env.KEY_PREFIX }}-${{ env.CACHE_VERSION }}-${{ hashFiles('pyproject.toml',
|
||||
'requirements_test.txt', 'requirements_test_min.txt',
|
||||
'requirements_test_pre_commit.txt') }}
|
||||
- name: Create Python virtual environment
|
||||
if: steps.cache-venv.outputs.cache-hit != 'true'
|
||||
run: |
|
||||
python -m venv venv
|
||||
. venv/bin/activate
|
||||
python -m pip install --upgrade pip
|
||||
pip install --upgrade --requirement requirements_test.txt
|
||||
# Save cached Python environment (explicit because cancel-in-progress: true)
|
||||
- name: Save Python virtual environment to cache
|
||||
if: steps.cache-venv.outputs.cache-hit != 'true'
|
||||
uses: actions/cache/save@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
key:
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
env.KEY_PREFIX }}-${{ env.CACHE_VERSION }}-${{ hashFiles('pyproject.toml',
|
||||
'requirements_test.txt', 'requirements_test_min.txt',
|
||||
'requirements_test_pre_commit.txt') }}
|
||||
|
||||
# Cache primer packages
|
||||
- name: Get commit string
|
||||
id: commitstring
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
python tests/primer/__main__.py prepare --make-commit-string
|
||||
output=$(python tests/primer/__main__.py prepare --read-commit-string)
|
||||
echo "commitstring=$output" >> $GITHUB_OUTPUT
|
||||
- name: Restore projects cache
|
||||
id: cache-projects
|
||||
uses: actions/cache/restore@v4.3.0
|
||||
with:
|
||||
path: tests/.pylint_primer_tests/
|
||||
key: >-
|
||||
${{ runner.os }}-${{ matrix.python-version }}-${{
|
||||
steps.commitstring.outputs.commitstring }}-primer
|
||||
- name: Regenerate cache
|
||||
if: steps.cache-projects.outputs.cache-hit != 'true'
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
python tests/primer/__main__.py prepare --clone
|
||||
- name: Save projects cache
|
||||
if: steps.cache-projects.outputs.cache-hit != 'true'
|
||||
uses: actions/cache/save@v4.3.0
|
||||
with:
|
||||
path: tests/.pylint_primer_tests/
|
||||
key: >-
|
||||
${{ runner.os }}-${{ matrix.python-version }}-${{
|
||||
steps.commitstring.outputs.commitstring }}-primer
|
||||
- name: Upload commit string
|
||||
uses: actions/upload-artifact@v4.6.2
|
||||
if: matrix.batchIdx == 0
|
||||
with:
|
||||
name: primer_commitstring_${{ matrix.python-version }}
|
||||
path:
|
||||
tests/.pylint_primer_tests/commit_string_${{ matrix.python-version }}.txt
|
||||
|
||||
# Run primer
|
||||
- name: Run pylint primer
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
pip install . --no-deps
|
||||
python tests/primer/__main__.py run --type=main --batches=${{ matrix.batches }} --batchIdx=${{ matrix.batchIdx }} 2>warnings.txt
|
||||
- name: Echo warnings
|
||||
if: success() || failure()
|
||||
run: |
|
||||
WARNINGS=$(head -c 65000 < warnings.txt)
|
||||
if [[ $WARNINGS ]]
|
||||
then echo "::warning ::$WARNINGS"
|
||||
fi
|
||||
- name: Upload output
|
||||
uses: actions/upload-artifact@v4.6.2
|
||||
with:
|
||||
name:
|
||||
primer_output_main_${{ matrix.python-version }}_batch${{ matrix.batchIdx }}
|
||||
path: >-
|
||||
tests/.pylint_primer_tests/output_${{ matrix.python-version }}_main_batch${{
|
||||
matrix.batchIdx }}.txt
|
||||
@ -0,0 +1,225 @@
|
||||
# Most of this is inspired by the mypy primer
|
||||
# See: https://github.com/hauntsaninja/mypy_primer
|
||||
# This is the primer job that runs on every PR
|
||||
|
||||
name: Primer / Run
|
||||
|
||||
on:
|
||||
pull_request:
|
||||
paths:
|
||||
- "pylint/**"
|
||||
- "tests/primer/**"
|
||||
- "requirements*"
|
||||
- ".github/workflows/**"
|
||||
# We ignore these specific files because they need to be changed
|
||||
# on 'main' and will always fail the PR run.
|
||||
- "!.github/workflows/primer_run_main.yaml"
|
||||
- "!.github/workflows/primer_comment.yaml"
|
||||
- "!tests/primer/packages_to_prime.json"
|
||||
branches:
|
||||
- main
|
||||
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
|
||||
cancel-in-progress: true
|
||||
|
||||
env:
|
||||
# This needs to be the SAME as in the Main and comment job
|
||||
CACHE_VERSION: 4
|
||||
KEY_PREFIX: venv-primer
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
run-primer:
|
||||
name: Run / ${{ matrix.python-version }} / batch index ${{ matrix.batchIdx }}
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 45
|
||||
strategy:
|
||||
matrix:
|
||||
python-version: ["3.10", "3.13"]
|
||||
batches: [4]
|
||||
batchIdx: [0, 1, 2, 3]
|
||||
steps:
|
||||
- name: Check out code from GitHub
|
||||
uses: actions/checkout@v5.0.0
|
||||
with:
|
||||
fetch-depth: 0
|
||||
- name: Set up Python ${{ matrix.python-version }}
|
||||
id: python
|
||||
uses: actions/setup-python@v6.0.0
|
||||
with:
|
||||
python-version: ${{ matrix.python-version }}
|
||||
check-latest: true
|
||||
|
||||
# Restore cached Python environment
|
||||
- name: Restore Python virtual environment
|
||||
id: cache-venv
|
||||
uses: actions/cache/restore@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
key:
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
env.KEY_PREFIX }}-${{ env.CACHE_VERSION }}-${{ hashFiles('pyproject.toml',
|
||||
'requirements_test.txt', 'requirements_test_min.txt',
|
||||
'requirements_test_pre_commit.txt') }}
|
||||
# Create environment must match step in 'Primer / Main'
|
||||
- name: Create Python virtual environment
|
||||
if: steps.cache-venv.outputs.cache-hit != 'true'
|
||||
run: |
|
||||
python -m venv venv
|
||||
. venv/bin/activate
|
||||
python -m pip install --upgrade pip
|
||||
pip install --upgrade --requirement requirements_test.txt
|
||||
# Save cached Python environment (explicit because cancel-in-progress: true)
|
||||
- name: Save Python virtual environment
|
||||
if: steps.cache-venv.outputs.cache-hit != 'true'
|
||||
uses: actions/cache/save@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
key:
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
env.KEY_PREFIX }}-${{ env.CACHE_VERSION }}-${{ hashFiles('pyproject.toml',
|
||||
'requirements_test.txt', 'requirements_test_min.txt',
|
||||
'requirements_test_pre_commit.txt') }}
|
||||
|
||||
# Cache primer packages
|
||||
- name: Download last 'main' run info
|
||||
id: download-main-run
|
||||
uses: actions/github-script@v8.0.0
|
||||
env:
|
||||
COMMIT_STRING_ARTIFACT: primer_commitstring_${{ matrix.python-version }}
|
||||
OUTPUT_ARTIFACT:
|
||||
primer_output_main_${{ matrix.python-version }}_batch${{ matrix.batchIdx }}
|
||||
with:
|
||||
script: |
|
||||
const { COMMIT_STRING_ARTIFACT, OUTPUT_ARTIFACT } = process.env
|
||||
// Download 'main' pylint output
|
||||
const fs = require('fs');
|
||||
const runs = await github.rest.actions.listWorkflowRuns({
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
workflow_id: ".github/workflows/primer_run_main.yaml",
|
||||
status: "success"
|
||||
});
|
||||
const lastRunMain = runs.data.workflow_runs.reduce(function(prev, current) {
|
||||
return (prev.run_number > current.run_number) ? prev : current
|
||||
})
|
||||
console.log("Last run on main:")
|
||||
console.log(lastRunMain.html_url)
|
||||
const artifacts_main = await github.rest.actions.listWorkflowRunArtifacts({
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
run_id: lastRunMain.id,
|
||||
});
|
||||
|
||||
// Get commitstring
|
||||
const [matchArtifactMain] = artifacts_main.data.artifacts.filter((artifact) =>
|
||||
artifact.name === COMMIT_STRING_ARTIFACT);
|
||||
const downloadWorkflow = await github.rest.actions.downloadArtifact({
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
artifact_id: matchArtifactMain.id,
|
||||
archive_format: "zip",
|
||||
});
|
||||
fs.writeFileSync(`${COMMIT_STRING_ARTIFACT}.zip`, Buffer.from(downloadWorkflow.data));
|
||||
|
||||
// Get output
|
||||
const [matchArtifactMainOutput] = artifacts_main.data.artifacts.filter((artifact) =>
|
||||
artifact.name === OUTPUT_ARTIFACT);
|
||||
const downloadWorkflowTwo = await github.rest.actions.downloadArtifact({
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
artifact_id: matchArtifactMainOutput.id,
|
||||
archive_format: "zip",
|
||||
});
|
||||
fs.writeFileSync(`${OUTPUT_ARTIFACT}.zip`, Buffer.from(downloadWorkflowTwo.data));
|
||||
return lastRunMain.head_sha;
|
||||
- name: Copy and unzip the commit string
|
||||
run: |
|
||||
unzip primer_commitstring_${{ matrix.python-version }}.zip
|
||||
cp commit_string_${{ matrix.python-version }}.txt tests/.pylint_primer_tests/commit_string_${{ matrix.python-version }}.txt
|
||||
- name: Unzip the output of 'main'
|
||||
run: |
|
||||
unzip primer_output_main_${{ matrix.python-version }}_batch${{ matrix.batchIdx }}.zip
|
||||
- name: Get commit string
|
||||
id: commitstring
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
output=$(python tests/primer/__main__.py prepare --read-commit-string)
|
||||
echo "commitstring=$output" >> $GITHUB_OUTPUT
|
||||
- name: Restore projects cache
|
||||
id: cache-projects
|
||||
uses: actions/cache/restore@v4.3.0
|
||||
with:
|
||||
path: tests/.pylint_primer_tests/
|
||||
key: >-
|
||||
${{ runner.os }}-${{ matrix.python-version }}-${{
|
||||
steps.commitstring.outputs.commitstring }}-primer
|
||||
- name: Regenerate cache
|
||||
if: steps.cache-projects.outputs.cache-hit != 'true'
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
python tests/primer/__main__.py prepare --clone
|
||||
- name: Save projects cache
|
||||
if: steps.cache-projects.outputs.cache-hit != 'true'
|
||||
uses: actions/cache/save@v4.3.0
|
||||
with:
|
||||
path: tests/.pylint_primer_tests/
|
||||
key: >-
|
||||
${{ runner.os }}-${{ matrix.python-version }}-${{
|
||||
steps.commitstring.outputs.commitstring }}-primer
|
||||
- name: Check cache
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
python tests/primer/__main__.py prepare --check
|
||||
|
||||
# Merge the 'main' commit of last successful run
|
||||
- name: Pull 'main'
|
||||
shell: bash
|
||||
run: |
|
||||
git config --global user.email "primer@example.com"
|
||||
git config --global user.name "Pylint Primer"
|
||||
git pull origin ${{ steps.download-main-run.outputs.result }} --no-edit --no-commit --no-rebase
|
||||
|
||||
# Run primer
|
||||
- name: Run pylint primer
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
pip install . --no-deps
|
||||
python tests/primer/__main__.py run --type=pr --batches=${{ matrix.batches }} --batchIdx=${{ matrix.batchIdx }} 2>warnings.txt
|
||||
- name: Echo warnings
|
||||
if: success() || failure()
|
||||
run: |
|
||||
WARNINGS=$(head -c 65000 < warnings.txt)
|
||||
if [[ $WARNINGS ]]
|
||||
then echo "::warning ::$WARNINGS"
|
||||
fi
|
||||
- name: Upload output of PR
|
||||
uses: actions/upload-artifact@v4.6.2
|
||||
with:
|
||||
name:
|
||||
primer_output_pr_${{ matrix.python-version }}_batch${{ matrix.batchIdx }}
|
||||
path:
|
||||
tests/.pylint_primer_tests/output_${{ matrix.python-version }}_pr_batch${{
|
||||
matrix.batchIdx }}.txt
|
||||
- name: Upload output of 'main'
|
||||
uses: actions/upload-artifact@v4.6.2
|
||||
with:
|
||||
name:
|
||||
primer_output_main_${{ matrix.python-version }}_batch${{ matrix.batchIdx }}
|
||||
path: output_${{ matrix.python-version }}_main_batch${{ matrix.batchIdx }}.txt
|
||||
|
||||
# Save PR number so we know which PR to comment on
|
||||
- name: Save PR number
|
||||
run: |
|
||||
echo ${{ github.event.pull_request.number }} | tee pr_number.txt
|
||||
- name: Upload PR number
|
||||
if:
|
||||
startsWith(steps.python.outputs.python-version, '3.10') && matrix.batchIdx ==
|
||||
0
|
||||
uses: actions/upload-artifact@v4.6.2
|
||||
with:
|
||||
name: pr_number
|
||||
path: pr_number.txt
|
||||
@ -0,0 +1,80 @@
|
||||
name: Release
|
||||
|
||||
on:
|
||||
release:
|
||||
types:
|
||||
- published
|
||||
|
||||
env:
|
||||
DEFAULT_PYTHON: "3.13"
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
jobs:
|
||||
build:
|
||||
name: Build release assets
|
||||
runs-on: ubuntu-latest
|
||||
if: github.event_name == 'release'
|
||||
steps:
|
||||
- name: Check out code from Github
|
||||
uses: actions/checkout@v5.0.0
|
||||
- name: Set up Python ${{ env.DEFAULT_PYTHON }}
|
||||
id: python
|
||||
uses: actions/setup-python@v6.0.0
|
||||
with:
|
||||
python-version: ${{ env.DEFAULT_PYTHON }}
|
||||
check-latest: true
|
||||
- name: Install requirements
|
||||
run: |
|
||||
# Remove dist, build, and pylint.egg-info
|
||||
# when building locally for testing!
|
||||
python -m pip install build
|
||||
- name: Build distributions
|
||||
run: |
|
||||
python -m build
|
||||
- name: Upload release assets
|
||||
uses: actions/upload-artifact@v4.6.2
|
||||
with:
|
||||
name: release-assets
|
||||
path: dist/
|
||||
|
||||
release-pypi:
|
||||
name: Upload release to PyPI
|
||||
runs-on: ubuntu-latest
|
||||
needs: ["build"]
|
||||
environment:
|
||||
name: PyPI
|
||||
url: https://pypi.org/project/pylint/
|
||||
permissions:
|
||||
id-token: write
|
||||
steps:
|
||||
- name: Download release assets
|
||||
uses: actions/download-artifact@v5.0.0
|
||||
with:
|
||||
name: release-assets
|
||||
path: dist/
|
||||
- name: Upload to PyPI
|
||||
if: github.event_name == 'release'
|
||||
uses: pypa/gh-action-pypi-publish@release/v1
|
||||
|
||||
release-github:
|
||||
name: Upload assets to Github release
|
||||
runs-on: ubuntu-latest
|
||||
needs: ["build"]
|
||||
permissions:
|
||||
contents: write
|
||||
id-token: write
|
||||
steps:
|
||||
- name: Download release assets
|
||||
uses: actions/download-artifact@v5.0.0
|
||||
with:
|
||||
name: release-assets
|
||||
path: dist/
|
||||
- name: Sign the dists with Sigstore and upload assets to Github release
|
||||
if: github.event_name == 'release'
|
||||
uses: sigstore/gh-action-sigstore-python@v3.0.1
|
||||
with:
|
||||
inputs: |
|
||||
./dist/*.tar.gz
|
||||
./dist/*.whl
|
||||
@ -0,0 +1,44 @@
|
||||
name: close stale issues and pr
|
||||
on:
|
||||
schedule:
|
||||
- cron: "30 1 * * *"
|
||||
workflow_dispatch:
|
||||
|
||||
jobs:
|
||||
close-issues:
|
||||
if: github.repository_owner == 'pylint-dev'
|
||||
runs-on: ubuntu-latest
|
||||
permissions:
|
||||
actions: write
|
||||
issues: write
|
||||
pull-requests: write
|
||||
steps:
|
||||
- uses: actions/stale@v10
|
||||
with:
|
||||
operations-per-run: 100
|
||||
|
||||
days-before-issue-stale: 28
|
||||
days-before-issue-close: 7
|
||||
any-of-issue-labels:
|
||||
"Waiting on author,Cannot reproduce 🤷,python past end of life,Won't fix/not
|
||||
planned"
|
||||
exempt-issue-labels: "High priority,Blocked 🚧,Needs decision 🔒"
|
||||
stale-issue-message:
|
||||
"This issue is stale because it has been open 4 weeks with no activity.
|
||||
Remove 'Stale' label or comment or this will be closed in a week."
|
||||
close-issue-message:
|
||||
"This issue was closed because it has been stalled for five weeks with no
|
||||
activity."
|
||||
|
||||
any-of-pr-labels:
|
||||
"Waiting on author,python past end of life,Won't fix/not planned"
|
||||
exempt-pr-labels: "High priority,Blocked 🚧,Needs review 🔍"
|
||||
days-before-pr-stale: 56
|
||||
days-before-pr-close: -1
|
||||
stale-pr-label: "Needs take over 🛎️"
|
||||
close-pr-message:
|
||||
"This PR was closed because it needed to be taken over for 16 weeks with no
|
||||
one stepping up."
|
||||
stale-pr-message:
|
||||
"This PR needs take over because because it has been open 8 weeks with no
|
||||
activity."
|
||||
@ -0,0 +1,208 @@
|
||||
name: Tests
|
||||
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
- "maintenance/**"
|
||||
paths-ignore:
|
||||
- doc/data/messages/**
|
||||
pull_request:
|
||||
branches:
|
||||
- main
|
||||
- "maintenance/**"
|
||||
workflow_dispatch:
|
||||
|
||||
env:
|
||||
CACHE_VERSION: 5
|
||||
KEY_PREFIX: venv
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
|
||||
cancel-in-progress: true
|
||||
|
||||
jobs:
|
||||
tests:
|
||||
name: run / ${{ matrix.python-version }} / ${{ matrix.os }}
|
||||
timeout-minutes: 25
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
os: [ubuntu-latest]
|
||||
python-version: &matrix-python-version ["3.10", "3.11", "3.12", "3.13", "3.14"]
|
||||
include:
|
||||
- os: macos-latest
|
||||
python-version: "3.10"
|
||||
- os: ubuntu-latest
|
||||
python-version: "pypy-3.10"
|
||||
- os: ubuntu-latest
|
||||
python-version: "pypy-3.11"
|
||||
runs-on: ${{ matrix.os }}
|
||||
outputs:
|
||||
python-key: ${{ steps.generate-python-key.outputs.key }}
|
||||
steps:
|
||||
- &checkout
|
||||
name: Check out code from GitHub
|
||||
uses: actions/checkout@v5.0.0
|
||||
- &setup-python
|
||||
name: Set up Python ${{ matrix.python-version }}
|
||||
id: python
|
||||
uses: actions/setup-python@v6.0.0
|
||||
with:
|
||||
python-version: ${{ matrix.python-version }}
|
||||
allow-prereleases: true
|
||||
check-latest: true
|
||||
- name: Generate partial Python venv restore key
|
||||
id: generate-python-key
|
||||
run: >-
|
||||
echo "key=${{ env.KEY_PREFIX }}-${{ env.CACHE_VERSION }}-${{
|
||||
hashFiles('pyproject.toml', 'requirements_test.txt',
|
||||
'requirements_test_min.txt', 'requirements_test_pre_commit.txt') }}" >>
|
||||
$GITHUB_OUTPUT
|
||||
- &cache-python
|
||||
name: Restore Python virtual environment
|
||||
id: cache-venv
|
||||
uses: actions/cache@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
key: >-
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
steps.generate-python-key.outputs.key }}
|
||||
- name: Create Python virtual environment
|
||||
if: steps.cache-venv.outputs.cache-hit != 'true'
|
||||
run: |
|
||||
python -m venv venv
|
||||
. venv/bin/activate
|
||||
python -m pip install --upgrade pip
|
||||
pip install --upgrade --requirement requirements_test.txt
|
||||
- name: Run pytest
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
pip install . --no-deps
|
||||
pip list | grep 'astroid\|pylint'
|
||||
python -m pytest --durations=10 --benchmark-disable --cov --cov-report= tests/
|
||||
- name: Run functional tests with minimal messages config
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
pip list | grep 'astroid\|pylint'
|
||||
python -m pytest -vv --minimal-messages-config tests/test_functional.py --benchmark-disable
|
||||
- name: Upload coverage artifact
|
||||
if: runner.os == 'Linux'
|
||||
uses: actions/upload-artifact@v4.6.2
|
||||
with:
|
||||
name: coverage-${{ matrix.python-version }}
|
||||
include-hidden-files: true
|
||||
path: .coverage
|
||||
|
||||
coverage:
|
||||
name: process / coverage
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 5
|
||||
needs: [tests]
|
||||
steps:
|
||||
- *checkout
|
||||
- name: Set up Python 3.13
|
||||
id: python
|
||||
uses: actions/setup-python@v6.0.0
|
||||
with:
|
||||
python-version: "3.13"
|
||||
check-latest: true
|
||||
- &cache-restore-python
|
||||
name: Restore Python virtual environment
|
||||
id: cache-venv
|
||||
uses: actions/cache/restore@v4.3.0
|
||||
with:
|
||||
path: venv
|
||||
fail-on-cache-miss: true
|
||||
key:
|
||||
${{ runner.os }}-${{ steps.python.outputs.python-version }}-${{
|
||||
needs.tests.outputs.python-key }}
|
||||
- name: Download all coverage artifacts
|
||||
uses: actions/download-artifact@v5.0.0
|
||||
- name: Combine coverage results
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
coverage combine coverage*/.coverage
|
||||
coverage xml
|
||||
- uses: codecov/codecov-action@v5
|
||||
with:
|
||||
token: ${{ secrets.CODECOV_TOKEN }}
|
||||
fail_ci_if_error: true
|
||||
verbose: true
|
||||
|
||||
benchmark-linux:
|
||||
name: run benchmark / ${{ matrix.python-version }} / Linux
|
||||
runs-on: ubuntu-latest
|
||||
timeout-minutes: 10
|
||||
needs: [tests]
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
python-version: ["3.13"]
|
||||
steps:
|
||||
- *checkout
|
||||
- *setup-python
|
||||
- *cache-restore-python
|
||||
- name: Run pytest
|
||||
run: |
|
||||
. venv/bin/activate
|
||||
pip install pygal
|
||||
pip install . --no-deps
|
||||
pip list | grep 'astroid\|pylint'
|
||||
pytest --exitfirst \
|
||||
--benchmark-only \
|
||||
--benchmark-autosave \
|
||||
--benchmark-save-data \
|
||||
--benchmark-group-by="group"
|
||||
- name: Create partial artifact name suffix
|
||||
id: artifact-name-suffix
|
||||
run: >-
|
||||
echo "datetime="$(date "+%Y%m%d_%H%M") >> $GITHUB_OUTPUT
|
||||
- name: Upload benchmark artifact
|
||||
uses: actions/upload-artifact@v4.6.2
|
||||
with:
|
||||
name:
|
||||
benchmark-${{ runner.os }}-${{ matrix.python-version }}_${{
|
||||
steps.artifact-name-suffix.outputs.datetime }}
|
||||
include-hidden-files: true
|
||||
path: .benchmarks/
|
||||
|
||||
tests-windows:
|
||||
name: run / ${{ matrix.python-version }} / Windows
|
||||
runs-on: windows-latest
|
||||
timeout-minutes: 25
|
||||
needs: [tests]
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
python-version: *matrix-python-version
|
||||
steps:
|
||||
- name: Set temp directory
|
||||
run: echo "TEMP=$env:USERPROFILE\AppData\Local\Temp" >> $env:GITHUB_ENV
|
||||
# Workaround to set correct temp directory on Windows
|
||||
# https://github.com/actions/virtual-environments/issues/712
|
||||
- *checkout
|
||||
- *setup-python
|
||||
- name: Generate partial Python venv restore key
|
||||
id: generate-python-key
|
||||
run: >-
|
||||
echo "key=venv-${{ env.CACHE_VERSION }}-${{
|
||||
hashFiles('pyproject.toml', 'requirements_test_min.txt')
|
||||
}}" >> $env:GITHUB_OUTPUT
|
||||
- *cache-python
|
||||
- name: Create Python virtual environment
|
||||
if: steps.cache-venv.outputs.cache-hit != 'true'
|
||||
run: |
|
||||
python -m venv venv
|
||||
. venv\\Scripts\\activate
|
||||
python -m pip install --upgrade pip
|
||||
pip install --upgrade --requirement requirements_test_min.txt
|
||||
- name: Run pytest
|
||||
run: |
|
||||
. venv\\Scripts\\activate
|
||||
pip install . --no-deps
|
||||
pip list | grep 'astroid\|pylint'
|
||||
python -m pytest --durations=10 --benchmark-disable tests/
|
||||
@ -0,0 +1,29 @@
|
||||
# Do not add entries specific to your dev environment or development
|
||||
# preferences in this file. You can use the global .gitignore for that:
|
||||
# git config --global core.excludesFile '~/.gitignore'
|
||||
/log
|
||||
*.py[cod]
|
||||
/build
|
||||
/doc/_build
|
||||
/dist/
|
||||
/pylint.egg-info/
|
||||
.tox
|
||||
*.sw[a-z]
|
||||
# Can't use | operator in .gitignore, see
|
||||
# https://unix.stackexchange.com/a/31806/189111
|
||||
doc/user_guide/messages/convention/
|
||||
doc/user_guide/messages/error/
|
||||
doc/user_guide/messages/fatal/
|
||||
doc/user_guide/messages/information/
|
||||
doc/user_guide/messages/refactor/
|
||||
doc/user_guide/messages/warning/
|
||||
tests/.pylint_primer_tests/
|
||||
pyve
|
||||
build-stamp
|
||||
.coverage
|
||||
.coverage.*
|
||||
.cache/
|
||||
.eggs/
|
||||
.pytest_cache/
|
||||
.mypy_cache/
|
||||
.benchmarks/
|
||||
@ -0,0 +1,174 @@
|
||||
ci:
|
||||
skip: [pylint]
|
||||
|
||||
repos:
|
||||
- repo: https://github.com/pre-commit/pre-commit-hooks
|
||||
rev: v6.0.0
|
||||
hooks:
|
||||
- id: trailing-whitespace
|
||||
exclude: tests(/\w*)*/functional/t/trailing_whitespaces.py|tests/pyreverse/data/.*.html|doc/data/messages/t/trailing-whitespace/bad.py
|
||||
# - id: file-contents-sorter # commented out because it does not preserve comments order
|
||||
# args: ["--ignore-case", "--unique"]
|
||||
# files: "custom_dict.txt"
|
||||
- id: end-of-file-fixer
|
||||
exclude: |
|
||||
(?x)^(
|
||||
tests(/\w*)*/functional/m/missing/missing_final_newline.py|
|
||||
tests/functional/t/trailing_newlines.py|
|
||||
doc/data/messages/t/trailing-newlines/bad.py|
|
||||
doc/data/messages/m/missing-final-newline/bad/lf.py|
|
||||
doc/data/messages/m/missing-final-newline/bad/crlf.py
|
||||
)$
|
||||
- repo: https://github.com/astral-sh/ruff-pre-commit
|
||||
rev: "v0.14.0"
|
||||
hooks:
|
||||
- id: ruff-check
|
||||
args: ["--fix"]
|
||||
exclude: doc/data/messages
|
||||
- id: ruff-check
|
||||
name: ruff-doc
|
||||
files: doc/data/messages
|
||||
# Please exclude using doc/data/ruff.toml
|
||||
# exclude: "" # Leave empty
|
||||
- repo: https://github.com/Pierre-Sassoulas/copyright_notice_precommit
|
||||
rev: 0.1.2
|
||||
hooks:
|
||||
- id: copyright-notice
|
||||
args: ["--notice=script/copyright.txt", "--enforce-all"]
|
||||
exclude: tests(/\w*)*/functional/|tests/input|doc/data/messages|examples/|setup.py|tests(/\w*)*data/
|
||||
types: [python]
|
||||
- repo: https://github.com/PyCQA/isort
|
||||
rev: 7.0.0
|
||||
hooks:
|
||||
- id: isort
|
||||
exclude: doc/data/messages/
|
||||
- repo: https://github.com/psf/black-pre-commit-mirror
|
||||
rev: 25.9.0
|
||||
hooks:
|
||||
- id: black
|
||||
args: [--safe, --quiet]
|
||||
exclude: &fixtures tests(/\w*)*/functional/|tests/input|doc/data/messages|tests(/\w*)*data/
|
||||
- id: black
|
||||
name: black-doc
|
||||
args: [--safe, --quiet]
|
||||
files: doc/data/messages/
|
||||
exclude: |
|
||||
(?x)^(
|
||||
doc/data/messages/b/bad-indentation/bad.py|
|
||||
doc/data/messages/i/inconsistent-quotes/bad.py|
|
||||
doc/data/messages/i/invalid-format-index/bad.py|
|
||||
doc/data/messages/l/line-too-long/bad.py|
|
||||
doc/data/messages/m/missing-final-newline/bad/crlf.py|
|
||||
doc/data/messages/m/missing-final-newline/bad/lf.py|
|
||||
doc/data/messages/m/multiple-statements/bad.py|
|
||||
doc/data/messages/r/redundant-u-string-prefix/bad.py|
|
||||
doc/data/messages/s/superfluous-parens/bad/example_1.py|
|
||||
doc/data/messages/s/syntax-error/bad.py|
|
||||
doc/data/messages/t/too-many-ancestors/bad.py|
|
||||
doc/data/messages/t/trailing-comma-tuple/bad.py|
|
||||
doc/data/messages/t/trailing-newlines/bad.py|
|
||||
doc/data/messages/t/trailing-whitespace/bad.py|
|
||||
doc/data/messages/u/unnecessary-semicolon/bad.py
|
||||
)$
|
||||
- repo: https://github.com/Pierre-Sassoulas/black-disable-checker
|
||||
rev: v1.1.3
|
||||
hooks:
|
||||
- id: black-disable-checker
|
||||
- repo: local
|
||||
hooks:
|
||||
- id: pylint
|
||||
name: pylint
|
||||
entry: pylint
|
||||
language: system
|
||||
types: [python]
|
||||
# Not that problematic to run in parallel see Pre-commit
|
||||
# integration in the doc for details
|
||||
# require_serial: true
|
||||
args: ["-rn", "-sn", "--rcfile=pylintrc", "--fail-on=I"]
|
||||
exclude: tests(/\w*)*/functional/|tests/input|tests(/\w*)*data/|doc/
|
||||
- id: pyright
|
||||
name: pyright
|
||||
description: "Python command line wrapper for pyright, a static type checker"
|
||||
entry: pyright
|
||||
language: python
|
||||
"types_or": [python, pyi]
|
||||
require_serial: true
|
||||
minimum_pre_commit_version: "2.9.2"
|
||||
exclude: tests(/\w*)*/functional/|tests/input|tests(/.*)+/conftest.py|doc/data/messages|tests(/\w*)*data/
|
||||
stages: [manual]
|
||||
# We define an additional manual step to allow running pylint with a spelling
|
||||
# checker in CI.
|
||||
- id: pylint
|
||||
alias: pylint-with-spelling
|
||||
name: pylint
|
||||
entry: pylint
|
||||
language: system
|
||||
types: [python]
|
||||
args:
|
||||
[
|
||||
"-rn",
|
||||
"-sn",
|
||||
"--rcfile=pylintrc",
|
||||
"--fail-on=I",
|
||||
"--spelling-dict=en",
|
||||
"--output-format=github",
|
||||
]
|
||||
exclude: tests(/\w*)*/functional/|tests/input|tests(/\w*)*data/|doc/
|
||||
stages: [manual]
|
||||
- id: check-newsfragments
|
||||
name: Check newsfragments
|
||||
entry: python3 -m script.check_newsfragments
|
||||
language: system
|
||||
types: [text]
|
||||
files: ^(doc/whatsnew/fragments)
|
||||
exclude: doc/whatsnew/fragments/_.*.rst
|
||||
- repo: https://github.com/rstcheck/rstcheck
|
||||
rev: "v6.2.5"
|
||||
hooks:
|
||||
- id: rstcheck
|
||||
args: ["--report-level=warning"]
|
||||
files: ^(doc/(.*/)*.*\.rst)
|
||||
additional_dependencies: ["Sphinx==7.4.3"]
|
||||
- repo: https://github.com/pre-commit/mirrors-mypy
|
||||
rev: v1.18.2
|
||||
hooks:
|
||||
- id: mypy
|
||||
name: mypy
|
||||
args: []
|
||||
additional_dependencies:
|
||||
["isort>=5", "platformdirs==2.2.0", "py==1.11", "tomlkit>=0.10.1"]
|
||||
exclude: tests(/\w*)*/functional/|tests/input|tests(/.*)+/conftest.py|doc/data/messages|tests(/\w*)*data/
|
||||
- repo: https://github.com/rbubley/mirrors-prettier
|
||||
rev: v3.6.2
|
||||
hooks:
|
||||
- id: prettier
|
||||
args: [--prose-wrap=always, --print-width=88]
|
||||
exclude: (tests(/\w*)*data/|.github/FUNDING.yml)
|
||||
- repo: https://github.com/DanielNoord/pydocstringformatter
|
||||
rev: v0.7.5
|
||||
hooks:
|
||||
- id: pydocstringformatter
|
||||
exclude: *fixtures
|
||||
args: ["--max-summary-lines=2", "--linewrap-full-docstring"]
|
||||
files: "pylint"
|
||||
- repo: https://github.com/PyCQA/bandit
|
||||
rev: 1.8.6
|
||||
hooks:
|
||||
- id: bandit
|
||||
args: ["-r", "-lll"]
|
||||
exclude: *fixtures
|
||||
- repo: https://github.com/codespell-project/codespell
|
||||
rev: v2.4.1
|
||||
hooks:
|
||||
- id: codespell
|
||||
args: ["--toml=pyproject.toml"]
|
||||
additional_dependencies:
|
||||
- tomli
|
||||
- repo: https://github.com/tox-dev/pyproject-fmt
|
||||
rev: "v2.10.0"
|
||||
hooks:
|
||||
- id: pyproject-fmt
|
||||
- repo: https://github.com/abravalheri/validate-pyproject
|
||||
rev: v0.24.1
|
||||
hooks:
|
||||
- id: validate-pyproject
|
||||
@ -0,0 +1,6 @@
|
||||
- id: pylint
|
||||
name: pylint
|
||||
entry: pylint
|
||||
language: python
|
||||
types: [python]
|
||||
require_serial: true
|
||||
@ -0,0 +1,19 @@
|
||||
# See https://docs.readthedocs.io/en/stable/config-file/v2.html for details
|
||||
|
||||
version: 2
|
||||
|
||||
sphinx:
|
||||
fail_on_warning: true
|
||||
configuration: doc/conf.py
|
||||
|
||||
python:
|
||||
install:
|
||||
- requirements: doc/readthedoc_requirements.txt
|
||||
|
||||
build:
|
||||
os: ubuntu-22.04
|
||||
tools:
|
||||
python: "3.11"
|
||||
jobs:
|
||||
pre_build:
|
||||
- towncrier build --yes --date TBA
|
||||
@ -0,0 +1,14 @@
|
||||
cff-version: 1.2.0
|
||||
title: "Pylint"
|
||||
message: >-
|
||||
If you use this software, please cite it using the metadata from this file.
|
||||
type: software
|
||||
authors:
|
||||
- name: "Pylint contributors"
|
||||
repository-code: "https://github.com/pylint-dev/pylint"
|
||||
url: "https://pylint.readthedocs.io/en/latest/"
|
||||
abstract: >-
|
||||
Pylint is a static code analyser for Python 2 or 3. Pylint analyses your code without
|
||||
actually running it. It checks for errors, enforces a coding standard, looks for code
|
||||
smells, and can make suggestions about how the code could be refactored.
|
||||
license: GPL-2.0
|
||||
@ -0,0 +1,120 @@
|
||||
# Contributor Covenant Code of Conduct
|
||||
|
||||
## Our Pledge
|
||||
|
||||
We as members, contributors, and leaders pledge to make participation in our community a
|
||||
harassment-free experience for everyone, regardless of age, body size, visible or
|
||||
invisible disability, ethnicity, sex characteristics, gender identity and expression,
|
||||
level of experience, education, socio-economic status, nationality, personal appearance,
|
||||
race, religion, or sexual identity and orientation.
|
||||
|
||||
We pledge to act and interact in ways that contribute to an open, welcoming, diverse,
|
||||
inclusive, and healthy community.
|
||||
|
||||
## Our Standards
|
||||
|
||||
Examples of behavior that contributes to a positive environment for our community
|
||||
include:
|
||||
|
||||
- Demonstrating empathy and kindness toward other people
|
||||
- Being respectful of differing opinions, viewpoints, and experiences
|
||||
- Giving and gracefully accepting constructive feedback
|
||||
- Accepting responsibility and apologizing to those affected by our mistakes, and
|
||||
learning from the experience
|
||||
- Focusing on what is best not just for us as individuals, but for the overall community
|
||||
|
||||
Examples of unacceptable behavior include:
|
||||
|
||||
- The use of sexualized language or imagery, and sexual attention or advances of any
|
||||
kind
|
||||
- Trolling, insulting or derogatory comments, and personal or political attacks
|
||||
- Public or private harassment
|
||||
- Publishing others' private information, such as a physical or email address, without
|
||||
their explicit permission
|
||||
- Other conduct which could reasonably be considered inappropriate in a professional
|
||||
setting
|
||||
|
||||
## Enforcement Responsibilities
|
||||
|
||||
Community leaders are responsible for clarifying and enforcing our standards of
|
||||
acceptable behavior and will take appropriate and fair corrective action in response to
|
||||
any behavior that they deem inappropriate, threatening, offensive, or harmful.
|
||||
|
||||
Community leaders have the right and responsibility to remove, edit, or reject comments,
|
||||
commits, code, wiki edits, issues, and other contributions that are not aligned to this
|
||||
Code of Conduct, and will communicate reasons for moderation decisions when appropriate.
|
||||
|
||||
## Scope
|
||||
|
||||
This Code of Conduct applies within all community spaces, and also applies when an
|
||||
individual is officially representing the community in public spaces. Examples of
|
||||
representing our community include using an official e-mail address, posting via an
|
||||
official social media account, or acting as an appointed representative at an online or
|
||||
offline event.
|
||||
|
||||
## Enforcement
|
||||
|
||||
Instances of abusive, harassing, or otherwise unacceptable behavior may be reported to
|
||||
the community leaders responsible for enforcement at pierre.sassoulas at gmail.com. All
|
||||
complaints will be reviewed and investigated promptly and fairly.
|
||||
|
||||
All community leaders are obligated to respect the privacy and security of the reporter
|
||||
of any incident.
|
||||
|
||||
## Enforcement Guidelines
|
||||
|
||||
Community leaders will follow these Community Impact Guidelines in determining the
|
||||
consequences for any action they deem in violation of this Code of Conduct:
|
||||
|
||||
### 1. Correction
|
||||
|
||||
**Community Impact**: Use of inappropriate language or other behavior deemed
|
||||
unprofessional or unwelcome in the community.
|
||||
|
||||
**Consequence**: A private, written warning from community leaders, providing clarity
|
||||
around the nature of the violation and an explanation of why the behavior was
|
||||
inappropriate. A public apology may be requested.
|
||||
|
||||
### 2. Warning
|
||||
|
||||
**Community Impact**: A violation through a single incident or series of actions.
|
||||
|
||||
**Consequence**: A warning with consequences for continued behavior. No interaction with
|
||||
the people involved, including unsolicited interaction with those enforcing the Code of
|
||||
Conduct, for a specified period of time. This includes avoiding interactions in
|
||||
community spaces as well as external channels like social media. Violating these terms
|
||||
may lead to a temporary or permanent ban.
|
||||
|
||||
### 3. Temporary Ban
|
||||
|
||||
**Community Impact**: A serious violation of community standards, including sustained
|
||||
inappropriate behavior.
|
||||
|
||||
**Consequence**: A temporary ban from any sort of interaction or public communication
|
||||
with the community for a specified period of time. No public or private interaction with
|
||||
the people involved, including unsolicited interaction with those enforcing the Code of
|
||||
Conduct, is allowed during this period. Violating these terms may lead to a permanent
|
||||
ban.
|
||||
|
||||
### 4. Permanent Ban
|
||||
|
||||
**Community Impact**: Demonstrating a pattern of violation of community standards,
|
||||
including sustained inappropriate behavior, harassment of an individual, or aggression
|
||||
toward or disparagement of classes of individuals.
|
||||
|
||||
**Consequence**: A permanent ban from any sort of public interaction within the
|
||||
community.
|
||||
|
||||
## Attribution
|
||||
|
||||
This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 2.0,
|
||||
available at https://www.contributor-covenant.org/version/2/0/code_of_conduct.html.
|
||||
|
||||
Community Impact Guidelines were inspired by
|
||||
[Mozilla's code of conduct enforcement ladder](https://github.com/mozilla/diversity).
|
||||
|
||||
[homepage]: https://www.contributor-covenant.org
|
||||
|
||||
For answers to common questions about this code of conduct, see the FAQ at
|
||||
https://www.contributor-covenant.org/faq. Translations are available at
|
||||
https://www.contributor-covenant.org/translations.
|
||||
@ -0,0 +1,699 @@
|
||||
# This file is autocompleted by 'contributors-txt',
|
||||
# using the configuration in 'script/.contributors_aliases.json'.
|
||||
# Do not add new persons manually and only add information without
|
||||
# using '-' as the line first character.
|
||||
# Please verify that your change are stable if you modify manually.
|
||||
|
||||
Ex-maintainers
|
||||
--------------
|
||||
- Claudiu Popa <pcmanticore@gmail.com>
|
||||
- Sylvain Thénault <thenault@gmail.com> : main author / maintainer
|
||||
- Torsten Marek <shlomme@gmail.com>
|
||||
|
||||
|
||||
Maintainers
|
||||
-----------
|
||||
- Pierre Sassoulas <pierre.sassoulas@gmail.com>
|
||||
- Daniël van Noord <13665637+DanielNoord@users.noreply.github.com>
|
||||
- Jacob Walls <jacobtylerwalls@gmail.com>
|
||||
- Marc Mueller <30130371+cdce8p@users.noreply.github.com>
|
||||
- Hippo91 <guillaume.peillex@gmail.com>
|
||||
- Mark Byrne <31762852+mbyrnepr2@users.noreply.github.com>
|
||||
- Andreas Finkler <3929834+DudeNr33@users.noreply.github.com>
|
||||
- Matus Valo <matusvalo@users.noreply.github.com>
|
||||
- Dani Alcala <112832187+clavedeluna@users.noreply.github.com>
|
||||
- Łukasz Rogalski <rogalski.91@gmail.com>
|
||||
- Nick Drozd <nicholasdrozd@gmail.com>: performance improvements to astroid
|
||||
- Ashley Whetter <ashley@awhetter.co.uk>
|
||||
- Bryce Guinta <bryce.paul.guinta@gmail.com>
|
||||
- Yu Shao, Pang <36848472+yushao2@users.noreply.github.com>
|
||||
- Dimitri Prybysh <dmand@yandex.ru>
|
||||
* multiple-imports, not-iterable, not-a-mapping, various patches.
|
||||
- Roy Williams <roy.williams.iii@gmail.com> (Lyft)
|
||||
* added check for implementing __eq__ without implementing __hash__,
|
||||
* Added Python 3 check for accessing Exception.message.
|
||||
* Added Python 3 check for calling encode/decode with invalid codecs.
|
||||
* Added Python 3 check for accessing sys.maxint.
|
||||
* Added Python 3 check for bad import statements.
|
||||
* Added Python 3 check for accessing deprecated methods on the 'string' module,
|
||||
various patches.
|
||||
- Florian Bruhin <me@the-compiler.org>
|
||||
- Arianna Yang <areveny@protonmail.com>
|
||||
|
||||
|
||||
Contributors
|
||||
------------
|
||||
|
||||
We would not be here without folks that contributed patches, pull requests,
|
||||
issues and their time to pylint. We're incredibly grateful to all of these
|
||||
contributors:
|
||||
|
||||
- Emile Anclin <emile.anclin@logilab.fr> (Logilab): python 3 support
|
||||
- Michal Nowikowski <godfryd@gmail.com>:
|
||||
* wrong-spelling-in-comment
|
||||
* wrong-spelling-in-docstring
|
||||
* parallel execution on multiple CPUs
|
||||
- Julthep Nandakwang <julthep@nandakwang.com>
|
||||
- Bruno Daniel <bruno.daniel@blue-yonder.com>: check_docs extension.
|
||||
- Sushobhit <31987769+sushobhit27@users.noreply.github.com> (sushobhit27)
|
||||
* Added new check 'comparison-with-itself'.
|
||||
* Added new check 'useless-import-alias'.
|
||||
* Added support of annotations in missing-type-doc and missing-return-type-doc.
|
||||
* Added new check 'comparison-with-callable'.
|
||||
* Removed six package dependency.
|
||||
* Added new check 'chained-comparison'.
|
||||
* Added new check 'useless-object-inheritance'.
|
||||
- Brett Cannon <brett@python.org>:
|
||||
* Port source code to be Python 2/3 compatible
|
||||
* Python 3 checker
|
||||
- Laura Médioni <laura.medioni@logilab.fr> (Logilab, on behalf of the CNES):
|
||||
* misplaced-comparison-constant
|
||||
* no-classmethod-decorator
|
||||
* no-staticmethod-decorator
|
||||
* too-many-nested-blocks,
|
||||
* too-many-boolean-expressions
|
||||
* unneeded-not
|
||||
* wrong-import-order
|
||||
* ungrouped-imports,
|
||||
* wrong-import-position
|
||||
* redefined-variable-type
|
||||
- Harutaka Kawamura <hkawamura0130@gmail.com>
|
||||
- Alexandre Fayolle <alexandre.fayolle@logilab.fr> (Logilab): TkInter gui, documentation, debian support
|
||||
- Ville Skyttä <ville.skytta@iki.fi>
|
||||
- Zen Lee <53538590+zenlyj@users.noreply.github.com>
|
||||
- Julien Cristau <julien.cristau@logilab.fr> (Logilab): python 3 support
|
||||
- Moisés López <6644187+moylop260@users.noreply.github.com>:
|
||||
* Support for deprecated-modules in modules not installed,
|
||||
* Refactor wrong-import-order to integrate it with `isort` library
|
||||
* Add check too-complex with mccabe for cyclomatic complexity
|
||||
* Refactor wrong-import-position to skip try-import and nested cases
|
||||
* Add consider-merging-isinstance, superfluous-else-return
|
||||
* Fix consider-using-ternary for 'True and True and True or True' case
|
||||
* Add bad-docstring-quotes and docstring-first-line-empty
|
||||
* Add missing-timeout
|
||||
* Fix false negative for `deprecated-module` when a `__import__` method is used instead of `import` sentence
|
||||
- Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
|
||||
- Frank Harrison <frank@doublethefish.com> (doublethefish)
|
||||
- Pierre-Yves David <pierre-yves.david@logilab.fr>
|
||||
- David Shea <dshea@redhat.com>: invalid sequence and slice index
|
||||
- Gunung P. Wibisono <55311527+gunungpw@users.noreply.github.com>
|
||||
- Derek Gustafson <degustaf@gmail.com>
|
||||
- Cezar Elnazli <cezar.elnazli2@gmail.com>: deprecated-method
|
||||
- Joseph Young <80432516+jpy-git@users.noreply.github.com> (jpy-git)
|
||||
- Tim Martin <tim@asymptotic.co.uk>
|
||||
- Ollie <46904826+ollie-iterators@users.noreply.github.com>
|
||||
- Julian Grimm <51880314+Julfried@users.noreply.github.com>
|
||||
- Tushar Sadhwani <tushar.sadhwani000@gmail.com> (tusharsadhwani)
|
||||
- Nicolas Chauvat <nicolas.chauvat@logilab.fr>
|
||||
- orSolocate <38433858+orSolocate@users.noreply.github.com>
|
||||
- Radu Ciorba <radu@devrandom.ro>: not-context-manager and confusing-with-statement warnings.
|
||||
- Holger Peters <email@holger-peters.de>
|
||||
- Cosmin Poieană <cmin@ropython.org>: unichr-builtin and improvements to bad-open-mode.
|
||||
- Yilei "Dolee" Yang <yileiyang@google.com>
|
||||
- Steven Myint <hg@stevenmyint.com>: duplicate-except.
|
||||
- Peter Kolbus <peter.kolbus@gmail.com> (Garmin)
|
||||
- Luigi Bertaco Cristofolini <lucristofolini@gmail.com> (luigibertaco)
|
||||
- Glenn Matthews <glenn@e-dad.net>:
|
||||
* autogenerated documentation for optional extensions,
|
||||
* bug fixes and enhancements for docparams (née check_docs) extension
|
||||
- crazybolillo <antonio@zoftko.com>
|
||||
- correctmost <134317971+correctmost@users.noreply.github.com>
|
||||
- Vlad Temian <vladtemian@gmail.com>: redundant-unittest-assert and the JSON reporter.
|
||||
- Julien Jehannet <julien.jehannet@logilab.fr>
|
||||
- Boris Feld <lothiraldan@gmail.com>
|
||||
- Anthony Sottile <asottile@umich.edu>
|
||||
- Andrew Haigh <nelfin@gmail.com> (nelfin)
|
||||
- Robert Hofer <hofrob@protonmail.com>
|
||||
- Pedro Algarvio <pedro@algarvio.me> (s0undt3ch)
|
||||
- Julien Palard <julien@palard.fr>
|
||||
- Hugo van Kemenade <hugovk@users.noreply.github.com>
|
||||
- David Liu <david@cs.toronto.edu> (david-yz-liu)
|
||||
- Dan Goldsmith <djgoldsmith@googlemail.com>: support for msg-template in HTML reporter.
|
||||
- Buck Evan <buck.2019@gmail.com>
|
||||
- Mariatta Wijaya <Mariatta@users.noreply.github.com>
|
||||
* Added new check `logging-fstring-interpolation`
|
||||
* Documentation typo fixes
|
||||
- Jakub Wilk <jwilk@jwilk.net>
|
||||
- Eli Fine <ejfine@gmail.com> (eli88fine): Fixed false positive duplicate code warning for lines with symbols only
|
||||
- Émile Crater <emile@crater.logilab.fr>
|
||||
- Pavel Roskin <proski@gnu.org>
|
||||
- David Gilman <davidgilman1@gmail.com>
|
||||
- へーさん <hira9603859504@gmail.com>
|
||||
- Thomas Hisch <t.hisch@gmail.com>
|
||||
- Marianna Polatoglou <mpolatoglou@bloomberg.net>: minor contribution for wildcard import check
|
||||
- Manuel Vázquez Acosta <mva.led@gmail.com>
|
||||
- Luis Escobar <lescobar@vauxoo.com> (Vauxoo): Add bad-docstring-quotes and docstring-first-line-empty
|
||||
- Lucas Cimon <lucas.cimon@gmail.com>
|
||||
- Konstantina Saketou <56515303+ksaketou@users.noreply.github.com>
|
||||
- Konstantin <Github@pheanex.de>
|
||||
- Jim Robertson <jrobertson98atx@gmail.com>
|
||||
- Ethan Leba <ethanleba5@gmail.com>
|
||||
- Enji Cooper <yaneurabeya@gmail.com>
|
||||
- Drum Ogilvie <me@daogilvie.com>
|
||||
- David Lindquist <dlindquist@google.com>: logging-format-interpolation warning.
|
||||
- Daniel Harding <dharding@gmail.com>
|
||||
- Anthony Truchet <anthony.truchet@logilab.fr>
|
||||
- Alexander Todorov <atodorov@otb.bg>:
|
||||
* added new error conditions to 'bad-super-call',
|
||||
* Added new check for incorrect len(SEQUENCE) usage,
|
||||
* Added new extension for comparison against empty string constants,
|
||||
* Added new extension which detects comparing integers to zero,
|
||||
* Added new useless-return checker,
|
||||
* Added new try-except-raise checker
|
||||
- theirix <theirix@gmail.com>
|
||||
- Téo Bouvard <teobouvard@gmail.com>
|
||||
- Sviatoslav Sydorenko <sviat@redhat.com>
|
||||
- Stavros Ntentos <133706+stdedos@users.noreply.github.com>
|
||||
- Nicolas Boulenguez <nicolas@debian.org>
|
||||
- Mihai Balint <balint.mihai@gmail.com>
|
||||
- Mark Bell <mark00bell@googlemail.com>
|
||||
- Levi Gruspe <mail.levig@gmail.com>
|
||||
- Jakub Kuczys <me@jacken.men>
|
||||
- Hornwitser <github@hornwitser.no>: fix import graph
|
||||
- Fureigh <rhys.fureigh@gsa.gov>
|
||||
- David Douard <david.douard@sdfa3.org>
|
||||
- Daniel Balparda <balparda@google.com> (Google): GPyLint maintainer (Google's pylint variant)
|
||||
- Christian Clauss <cclauss@me.com>
|
||||
- Bastien Vallet <bastien.vallet@gmail.com> (Djailla)
|
||||
- Aru Sahni <arusahni@gmail.com>: Git ignoring, regex-based ignores
|
||||
- Andreas Freimuth <andreas.freimuth@united-bits.de>: fix indentation checking with tabs
|
||||
- Alexandru Coman <fcoman@bitdefender.com>
|
||||
- jpkotta <jpkotta@gmail.com>
|
||||
- Thomas Grainger <tagrain@gmail.com>
|
||||
- Takahide Nojima <nozzy123nozzy@gmail.com>
|
||||
- Taewon D. Kim <kimt33@mcmaster.ca>
|
||||
- Sneaky Pete <sneakypete81@gmail.com>
|
||||
- Sergey B Kirpichev <skirpichev@gmail.com>
|
||||
- Sandro Tosi <sandro.tosi@gmail.com>: Debian packaging
|
||||
- Rogdham <contact@rogdham.net>
|
||||
- Rene Zhang <rz99@cornell.edu>
|
||||
- Paul Lichtenberger <paul.lichtenberger.rgbg@gmail.com>
|
||||
- Or Bahari <or.ba402@gmail.com>
|
||||
- Mr. Senko <atodorov@mrsenko.com>
|
||||
- Mike Frysinger <vapier@gmail.com>
|
||||
- Martin von Gagern <gagern@google.com> (Google): Added 'raising-format-tuple' warning.
|
||||
- Martin Vielsmaier <martin@vielsmaier.net>
|
||||
- Martin Pool <mbp@google.com> (Google):
|
||||
* warnings for anomalous backslashes
|
||||
* symbolic names for messages (like 'unused')
|
||||
* etc.
|
||||
- Martin Bašti <MartinBasti@users.noreply.github.com>
|
||||
* Added new check for shallow copy of os.environ
|
||||
* Added new check for useless `with threading.Lock():` statement
|
||||
- Marcus Näslund <naslundx@gmail.com> (naslundx)
|
||||
- Marco Pernigotti <7657251+mpernigo@users.noreply.github.com>
|
||||
- Marco Forte <fortemarco.irl@gmail.com>
|
||||
- James Addison <55152140+jayaddison@users.noreply.github.com>
|
||||
- Ionel Maries Cristian <contact@ionelmc.ro>
|
||||
- Gergely Kalmár <gergely.kalmar@logikal.jp>
|
||||
- Damien Baty <damien.baty@polyconseil.fr>
|
||||
- Benjamin Drung <benjamin.drung@profitbricks.com>: contributing Debian Developer
|
||||
- Anubhav <35621759+anubh-v@users.noreply.github.com>
|
||||
- Antonio Quarta <sgheppy88@gmail.com>
|
||||
- Andrew J. Simmons <anjsimmo@gmail.com>
|
||||
- Alvaro Frias <alvarofriasgaray@gmail.com>
|
||||
- Alexey Pelykh <alexey.pelykh@gmail.com>
|
||||
- Alex Prabhat Bara <alexpbara@gmail.com>
|
||||
- wtracy <afishionado@gmail.com>
|
||||
- jessebrennan <jesse@jesse.computer>
|
||||
- chohner <mail@chohner.com>
|
||||
- aatle <168398276+aatle@users.noreply.github.com>
|
||||
- Tiago Honorato <61059243+tiagohonorato@users.noreply.github.com>
|
||||
- Steven M. Vascellaro <svascellaro@gmail.com>
|
||||
- Robin Tweedie <70587124+robin-wayve@users.noreply.github.com>
|
||||
- Roberto Leinardi <leinardi@gmail.com>: PyCharm plugin maintainer
|
||||
- Ricardo Gemignani <ricardo.gemignani@gmail.com>
|
||||
- Piotr Idzik <65706193+vil02@users.noreply.github.com>
|
||||
- Pieter Engelbrecht <pengelbrecht@rems2.com>
|
||||
- Philipp Albrecht <flying-sheep@web.de> (pylbrecht)
|
||||
- Nicolas Dickreuter <dickreuter@gmail.com>
|
||||
- Nick Bastin <nick.bastin@gmail.com>
|
||||
- Nathaniel Manista <nathaniel@google.com>: suspicious lambda checking
|
||||
- Maksym Humetskyi <Humetsky@gmail.com> (mhumetskyi)
|
||||
* Fixed ignored empty functions by similarities checker with "ignore-signatures" option enabled
|
||||
* Ignore function decorators signatures as well by similarities checker with "ignore-signatures" option enabled
|
||||
* Ignore class methods and nested functions signatures as well by similarities checker with "ignore-signatures" option enabled
|
||||
- Kylian <development@goudcode.nl>
|
||||
- Konstantin Manna <Konstantin@Manna.uno>
|
||||
- Kai Mueller <15907922+kasium@users.noreply.github.com>
|
||||
- Joshua Cannon <joshdcannon@gmail.com>
|
||||
- John Leach <jfleach@jfleach.com>
|
||||
- James Morgensen <james.morgensen@gmail.com>: ignored-modules option applies to import errors.
|
||||
- Jaehoon Hwang <jaehoonhwang@users.noreply.github.com> (jaehoonhwang)
|
||||
- Huw Jones <huw@huwcbjones.co.uk>
|
||||
- Gideon <87426140+GideonBear@users.noreply.github.com>
|
||||
- Ganden Schaffner <gschaffner@pm.me>
|
||||
- Frost Ming <frostming@tencent.com>
|
||||
- Federico Bond <federicobond@gmail.com>
|
||||
- Erik Wright <erik.wright@shopify.com>
|
||||
- Erik Eriksson <molobrakos@users.noreply.github.com>: Added overlapping-except error check.
|
||||
- Emmanuel Ferdman <emmanuelferdman@gmail.com>
|
||||
- Dave Bunten <dave.bunten@cuanschutz.edu>
|
||||
- Daniel Wang <danielwang405@gmail.com>
|
||||
- Daniel Mouritzen <dmrtzn@gmail.com>
|
||||
- Dan Hemberger <846186+hemberger@users.noreply.github.com>
|
||||
- Chris Rebert <code@rebertia.com>: unidiomatic-typecheck.
|
||||
- Aurelien Campeas <aurelien.campeas@logilab.fr>
|
||||
- Alexander Pervakov <frost.nzcr4@jagmort.com>
|
||||
- Alain Leufroy <alain.leufroy@logilab.fr>
|
||||
- Akhil Kamat <akhil.kamat@gmail.com>
|
||||
- Adam Williamson <awilliam@redhat.com>
|
||||
- Aaron Liu <aaronliu0130@gmail.com>
|
||||
- xmo-odoo <xmo-odoo@users.noreply.github.com>
|
||||
- tbennett0 <tbennett0@users.noreply.github.com>
|
||||
- purajit <7026198+purajit@users.noreply.github.com>
|
||||
- omarandlorraine <64254276+omarandlorraine@users.noreply.github.com>
|
||||
- craig-sh <craig-sh@users.noreply.github.com>
|
||||
- bernie gray <bfgray3@users.noreply.github.com>
|
||||
- azinneck0485 <123660683+azinneck0485@users.noreply.github.com>
|
||||
- Wing Lian <wing.lian@gmail.com>
|
||||
- Wes Turner <westurner@google.com> (Google): added new check 'inconsistent-quotes'
|
||||
- Tyler Thieding <tyler@thieding.com>
|
||||
- Tobias Hernstig <30827238+thernstig@users.noreply.github.com>
|
||||
- Smixi <sismixx@hotmail.fr>
|
||||
- Simu Toni <simutoni@gmail.com>
|
||||
- Sergei Lebedev <185856+superbobry@users.noreply.github.com>
|
||||
- Scott Worley <scottworley@scottworley.com>
|
||||
- Saugat Pachhai <suagatchhetri@outlook.com>
|
||||
- Samuel FORESTIER <HorlogeSkynet@users.noreply.github.com>
|
||||
- Rémi Cardona <remi.cardona@polyconseil.fr>
|
||||
- Ryan Ozawa <ryan.ozawa21@gmail.com>
|
||||
- Roger Sheu <78449574+rogersheu@users.noreply.github.com>
|
||||
- Raphael Gaschignard <raphael@makeleaps.com>
|
||||
- Ram Rachum <ram@rachum.com> (cool-RR)
|
||||
- Radostin Stoyanov <rst0git@users.noreply.github.com>
|
||||
- Peter Bittner <django@bittner.it>
|
||||
- Paul Renvoisé <PaulRenvoise@users.noreply.github.com>
|
||||
- PHeanEX <github@pheanex.de>
|
||||
- Omega Weapon <OmegaPhil+hg@gmail.com>
|
||||
- Nikolai Kristiansen <nikolaik@gmail.com>
|
||||
- Nick Pesce <nickpesce22@gmail.com>
|
||||
- Nedelcu Ioan-Andrei <138256980+nedelcu-ioan@users.noreply.github.com>
|
||||
- Nathan Marrow <nmarrow@google.com>
|
||||
- Mikhail Fesenko <m.fesenko@corp.vk.com>
|
||||
- Matthew Suozzo <msuozzo@google.com>
|
||||
- Matthew Beckers <17108752+mattlbeck@users.noreply.github.com> (mattlbeck)
|
||||
- Mark Roman Miller <mtmiller@users.noreply.github.com>: fix inline defs in too-many-statements
|
||||
- MalanB <malan.kmu@gmail.com>
|
||||
- Mads Kiilerich <mads@kiilerich.com>
|
||||
- Maarten ter Huurne <maarten@treewalker.org>
|
||||
- Lefteris Karapetsas <lefteris@refu.co>
|
||||
- LCD 47 <lcd047@gmail.com>
|
||||
- Jérome Perrin <perrinjerome@gmail.com>
|
||||
- Justin Li <justinnhli@gmail.com>
|
||||
- John Kirkham <jakirkham@gmail.com>
|
||||
- Jens H. Nielsen <Jens.Nielsen@microsoft.com>
|
||||
- Jake Lishman <jake.lishman@ibm.com>
|
||||
- Ioana Tagirta <ioana.tagirta@gmail.com>: fix bad thread instantiation check
|
||||
- Ikraduya Edian <ikraduya@gmail.com>: Added new checks 'consider-using-generator' and 'use-a-generator'.
|
||||
- Hugues Bruant <hugues.bruant@affirm.com>
|
||||
- Hashem Nasarat <Hnasar@users.noreply.github.com>
|
||||
- Harut <yes@harutune.name>
|
||||
- Grygorii Iermolenko <gyermolenko@gmail.com>
|
||||
- Grizzly Nyo <grizzly.nyo@gmail.com>
|
||||
- Gabriel R. Sezefredo <g@briel.dev>: Fixed "exception-escape" false positive with generators
|
||||
- Filipe Brandenburger <filbranden@google.com>
|
||||
- Fantix King <fantix@uchicago.edu> (UChicago)
|
||||
- Eric McDonald <221418+emcd@users.noreply.github.com>
|
||||
- Elias Dorneles <eliasdorneles@gmail.com>: minor adjust to config defaults and docs
|
||||
- Elazrod56 <thomas.lf5629@gmail.com>
|
||||
- Edward K. Ream <edreamleo@gmail.com>
|
||||
- Derek Harland <derek.harland@finq.co.nz>
|
||||
- David Pursehouse <david.pursehouse@gmail.com>
|
||||
- Daniel Miller <millerdev@gmail.com>
|
||||
- Christoph Blessing <33834216+cblessing24@users.noreply.github.com>
|
||||
- Chris Murray <chris@chrismurray.scot>
|
||||
- Chris Lamb <chris@chris-lamb.co.uk>
|
||||
- Charles Hebert <charles.hebert@logilab.fr>
|
||||
- Carli Freudenberg <carli.freudenberg@energymeteo.de> (CarliJoy)
|
||||
* Fixed issue 5281, added Unicode checker
|
||||
* Improve non-ascii-name checker
|
||||
- Bruce Dawson <randomascii@users.noreply.github.com>
|
||||
- Brian Shaginaw <brian.shaginaw@warbyparker.com>: prevent error on exception check for functions
|
||||
- Benny Mueller <benny.mueller91@gmail.com>
|
||||
- Ben James <benjames1999@hotmail.co.uk>
|
||||
- Ben Green <benhgreen@icloud.com>
|
||||
- Batuhan Taskaya <batuhanosmantaskaya@gmail.com>
|
||||
- Artem Yurchenko <artemyurchenko@zoho.com>
|
||||
- Alexander Kapshuna <kapsh@kap.sh>
|
||||
- Akshay Choudhary <153769403+Akshay9715@users.noreply.github.com>
|
||||
- Adam Parkin <pzelnip@users.noreply.github.com>
|
||||
- 谭九鼎 <109224573@qq.com>
|
||||
- Łukasz Sznuk <ls@rdprojekt.pl>
|
||||
- zasca <gorstav@gmail.com>
|
||||
- y2kbugger <y2kbugger@users.noreply.github.com>
|
||||
- vinnyrose <vinnyrose@users.noreply.github.com>
|
||||
- ttenhoeve-aa <ttenhoeve@appannie.com>
|
||||
- thinwybk <florian.k@mailbox.org>
|
||||
- temyurchenko <44875844+temyurchenko@users.noreply.github.com>
|
||||
- syutbai <syutbai@gmail.com>
|
||||
- sur.la.route <17788706+christopherpickering@users.noreply.github.com>
|
||||
- sdet_liang <liangway@users.noreply.github.com>
|
||||
- pavan-msys <149513767+pavan-msys@users.noreply.github.com>
|
||||
- paschich <millen@gridium.com>
|
||||
- oittaa <8972248+oittaa@users.noreply.github.com>
|
||||
- nyabkun <75878387+nyabkun@users.noreply.github.com>
|
||||
- nhdsd <wyx070906@outlook.com>
|
||||
- moxian <aleftmail@inbox.ru>
|
||||
- mar-chi-pan <mar.polatoglou@gmail.com>
|
||||
- lrjball <50599110+lrjball@users.noreply.github.com>
|
||||
- levon-d <mycroft2003@gmail.com>
|
||||
- laike9m <laike9m@users.noreply.github.com>
|
||||
- kyoto7250 <50972773+kyoto7250@users.noreply.github.com>
|
||||
- kriek <sylvain.ackermann@gmail.com>
|
||||
- kdestin <101366538+kdestin@users.noreply.github.com>
|
||||
- jaydesl <35102795+jaydesl@users.noreply.github.com>
|
||||
- jab <jab@users.noreply.github.com>
|
||||
- gracejiang16 <70730457+gracejiang16@users.noreply.github.com>
|
||||
- glmdgrielson <32415403+glmdgrielson@users.noreply.github.com>
|
||||
- glegoux <gilles.legoux@gmail.com>
|
||||
- gaurikholkar <f2013002@goa.bits-pilani.ac.in>
|
||||
- flyingbot91 <flyingbot91@gmx.com>
|
||||
- fly <fly@users.noreply.github.com>
|
||||
- fahhem <fahhem>
|
||||
- fadedDexofan <fadedDexofan@gmail.com>
|
||||
- epenet <6771947+epenet@users.noreply.github.com>
|
||||
- danields <danields761@gmail.com>
|
||||
- cosven <cosven@users.noreply.github.com>
|
||||
- cordis-dev <darius@adroiti.com>
|
||||
- cherryblossom <31467609+cherryblossom000@users.noreply.github.com>
|
||||
- bluesheeptoken <louis.fruleux1@gmail.com>
|
||||
- anatoly techtonik <techtonik@gmail.com>
|
||||
- amelenty <ada.melentyeva@gmail.com>
|
||||
- akirchhoff-modular <github-work@kirchhoff.digital>
|
||||
- agutole <toldo_carp@hotmail.com>
|
||||
- Zeckie <49095968+Zeckie@users.noreply.github.com>
|
||||
- Zeb Nicholls <zebedee.nicholls@climate-energy-college.org>
|
||||
* Made W9011 compatible with 'of' syntax in return types
|
||||
- Yuval Langer <yuvallanger@mail.tau.ac.il>
|
||||
- Yury Gribov <tetra2005@gmail.com>
|
||||
- Yuri Bochkarev <baltazar.bz@gmail.com>: Added epytext support to docparams extension.
|
||||
- Youngsoo Sung <ysung@bepro11.com>
|
||||
- Yory <39745367+yory8@users.noreply.github.com>
|
||||
- Yoichi Nakayama <yoichi.nakayama@gmail.com>
|
||||
- Yeting Li <liyt@ios.ac.cn> (yetingli)
|
||||
- Yannack <yannack@users.noreply.github.com>
|
||||
- Yann Dirson <ydirson@free.fr>
|
||||
- Yang Yang <y4n9squared@gmail.com>
|
||||
- Xi Shen <davidshen84@gmail.com>
|
||||
- Winston H <56998716+winstxnhdw@users.noreply.github.com>
|
||||
- Will Shanks <wsha@posteo.net>
|
||||
- Viorel Știrbu <viorels@gmail.com>: intern-builtin warning.
|
||||
- VictorT <victor.taix@gmail.com>
|
||||
- Victor Jiajunsu <16359131+jiajunsu@users.noreply.github.com>
|
||||
- ViRuSTriNiTy <cradle-of-mail@gmx.de>
|
||||
- Val Lorentz <progval+github@progval.net>
|
||||
- Ulrich Eckhardt <UlrichEckhardt@users.noreply.github.com>
|
||||
- Udi Fuchs <udifuchs@gmail.com>
|
||||
- Trevor Bekolay <tbekolay@gmail.com>
|
||||
* Added --list-msgs-enabled command
|
||||
- Tomer Chachamu <tomer.chachamu@gmail.com>: simplifiable-if-expression
|
||||
- Tomasz Michalski <tomasz.michalski@rtbhouse.com>
|
||||
- Tomasz Magulski <tomasz@magullab.io>
|
||||
- Tom <tsarantis@proton.me>
|
||||
- Tim Hatch <tim@timhatch.com>
|
||||
- Tim Gates <tim.gates@iress.com>
|
||||
- Tianyu Chen <124018391+UTsweetyfish@users.noreply.github.com>
|
||||
- Théo Battrel <theo.util@protonmail.ch>
|
||||
- Thomas Benhamou <thomas@lightricks.com>
|
||||
- Theodore Ni <3806110+tjni@users.noreply.github.com>
|
||||
- Tanvi Moharir <74228962+tanvimoharir@users.noreply.github.com>: Fix for invalid toml config
|
||||
- T.Rzepka <Tobias.Rzepka@gmail.com>
|
||||
- Svetoslav Neykov <svet@hyperscience.com>
|
||||
- SubaruArai <78188579+SubaruArai@users.noreply.github.com>
|
||||
- Stéphane Wirtel <stephane@wirtel.be>: nonlocal-without-binding
|
||||
- Stephen Longofono <8992396+SLongofono@users.noreply.github.com>
|
||||
- Stephane Odul <1504511+sodul@users.noreply.github.com>
|
||||
- Stanislav Levin <slev@altlinux.org>
|
||||
- Sorin Sbarnea <ssbarnea@redhat.com>
|
||||
- Slavfox <slavfoxman@gmail.com>
|
||||
- Skip Montanaro <skip@pobox.com>
|
||||
- Sigurd Spieckermann <2206639+sisp@users.noreply.github.com>
|
||||
- Shiv Venkatasubrahmanyam <shvenkat@users.noreply.github.com>
|
||||
- Sebastian Müller <mueller.seb@posteo.de>
|
||||
- Sayyed Faisal Ali <80758388+C0DE-SLAYER@users.noreply.github.com>
|
||||
- Sasha Bagan <pnlbagan@gmail.com>
|
||||
- Sardorbek Imomaliev <sardorbek.imomaliev@gmail.com>
|
||||
- Santiago Castro <bryant@montevideo.com.uy>
|
||||
- Samuel Freilich <sfreilich@google.com> (sfreilich)
|
||||
- Sam Vermeiren <88253337+PaaEl@users.noreply.github.com>
|
||||
- Ryan McGuire <ryan@enigmacurry.com>
|
||||
- Ry4an Brase <ry4an-hg@ry4an.org>
|
||||
- Ruro <ruro.ruro@ya.ru>
|
||||
- Roshan Shetty <roshan.shetty2816@gmail.com>
|
||||
- Roman Ivanov <me@roivanov.com>
|
||||
- Robert Schweizer <robert_schweizer@gmx.de>
|
||||
- Reverb Chu <reverbc@users.noreply.github.com>
|
||||
- Renat Galimov <renat2017@gmail.com>
|
||||
- Rebecca Turner <rbt@sent.as> (9999years)
|
||||
- Randall Leeds <randall@bleeds.info>
|
||||
- Ranadheer Gorrepati <35244169+ranadheerg@users.noreply.github.com>
|
||||
- Ramon Saraiva <ramonsaraiva@gmail.com>
|
||||
- Ramiro Leal-Cavazos <ramiroleal050@gmail.com> (ramiro050): Fixed bug preventing pylint from working with Emacs tramp
|
||||
- RSTdefg <34202999+RSTdefg@users.noreply.github.com>
|
||||
- R. N. West <98110034+rnwst@users.noreply.github.com>
|
||||
- Qwiddle13 <32040075+Qwiddle13@users.noreply.github.com>
|
||||
- Quentin Young <qlyoung@users.noreply.github.com>
|
||||
- Prajwal Borkar <sunnyborkar7777@gmail.com>
|
||||
- Petr Pulc <petrpulc@gmail.com>: require whitespace around annotations
|
||||
- Peter Dawyndt <Peter.Dawyndt@UGent.be>
|
||||
- Peter Dave Hello <hsu@peterdavehello.org>
|
||||
- Peter Aronoff <peter@aronoff.org>
|
||||
- Paul Cochrane <paul@liekut.de>
|
||||
- Patrik <patrik.mrx@gmail.com>
|
||||
- Pascal Corpet <pcorpet@users.noreply.github.com>
|
||||
- Pablo Galindo Salgado <Pablogsal@gmail.com>
|
||||
* Fix false positive 'Non-iterable value' with async comprehensions.
|
||||
- Osher De Paz <odepaz@redhat.com>
|
||||
- Oisín Moran <OisinMoran@users.noreply.github.com>
|
||||
- Obscuron <Abscuron@gmail.com>
|
||||
- Noam Yorav-Raphael <noamraph@gmail.com>
|
||||
- Noah-Agnel <138210920+Noah-Agnel@users.noreply.github.com>
|
||||
- Nir Soffer <nirsof@gmail.com>
|
||||
- Niko Wenselowski <niko@nerdno.de>
|
||||
- Nikita Sobolev <mail@sobolevn.me>
|
||||
- Nick Smith <clickthisnick@users.noreply.github.com>
|
||||
- Neowizard <Neowizard@users.noreply.github.com>
|
||||
- Ned Batchelder <ned@nedbatchelder.com>
|
||||
- Natalie Serebryakova <natalie.serebryakova@Natalies-MacBook-Pro.local>
|
||||
- Naglis Jonaitis <827324+naglis@users.noreply.github.com>
|
||||
- Moody <mooodyhunter@outlook.com>
|
||||
- Mitchell Young <mitchelly@gmail.com>: minor adjustment to docparams
|
||||
- Mitar <mitar.github@tnode.com>
|
||||
- Ming Lyu <CareF.Lm@gmail.com>
|
||||
- Mikhail f. Shiryaev <mr.felixoid@gmail.com>
|
||||
- Mike Fiedler <miketheman@gmail.com> (miketheman)
|
||||
- Mike Bryant <leachim@leachim.info>
|
||||
- Mike Bernard <mdbernard@pm.me>
|
||||
- Michka Popoff <michkapopoff@gmail.com>
|
||||
- Michal Vasilek <michal@vasilek.cz>
|
||||
- Michael Scott Cuthbert <cuthbert@mit.edu>
|
||||
- Michael Kefeder <oss@multiwave.ch>
|
||||
- Michael K <michael-k@users.noreply.github.com>
|
||||
- Michael Hudson-Doyle <michael.hudson@canonical.com>
|
||||
- Michael Giuffrida <mgiuffrida@users.noreply.github.com>
|
||||
- Melvin Hazeleger <31448155+melvio@users.noreply.github.com>
|
||||
- Meltem Kenis <meltem.kenis@plentific.com>
|
||||
- Mehdi Drissi <mdrissi@hmc.edu>
|
||||
- Matěj Grabovský <mgrabovs@redhat.com>
|
||||
- Matthijs Blom <19817960+MatthijsBlom@users.noreply.github.com>
|
||||
- Matej Spiller Muys <matej.spiller-muys@bitstamp.net>
|
||||
- Matej Marušák <marusak.matej@gmail.com>
|
||||
- Marzuk Rashid <mail@marzuk.io>
|
||||
- Markus Siebenhaar <41283549+siehar@users.noreply.github.com>
|
||||
- Marco Edward Gorelli <marcogorelli@protonmail.com>: Documented Jupyter integration
|
||||
- Marcin Kurczewski <rr-@sakuya.pl> (rr-)
|
||||
- Maik Röder <maikroeder@gmail.com>
|
||||
- Lumír 'Frenzy' Balhar <frenzy.madness@gmail.com>
|
||||
- Ludovic Aubry <ludal@logilab.fr>
|
||||
- Louis Sautier <sautier.louis@gmail.com>
|
||||
- Lorena Buciu <46202743+lorena-b@users.noreply.github.com>
|
||||
- Logan Miller <14319179+komodo472@users.noreply.github.com>
|
||||
- Kári Tristan Helgason <kthelgason@gmail.com>
|
||||
- Kurian Benoy <70306694+kurianbenoy-aot@users.noreply.github.com>
|
||||
- Krzysztof Czapla <k.czapla68@gmail.com>
|
||||
- Kraig Brockschmidt <kraigbr@msn.com>
|
||||
- Kound <norman.freudenberg@posteo.de>
|
||||
- KotlinIsland <65446343+KotlinIsland@users.noreply.github.com>
|
||||
- Kosarchuk Sergey <sergeykosarchuk@gmail.com>
|
||||
- Konrad Weihmann <46938494+priv-kweihmann@users.noreply.github.com>
|
||||
- Kian Meng, Ang <kianmeng.ang@gmail.com>
|
||||
- Kevin Phillips <thefriendlycoder@gmail.com>
|
||||
- Kevin Jing Qiu <kevin.jing.qiu@gmail.com>
|
||||
- Kenneth Schackart <schackartk1@gmail.com>
|
||||
- Kayran Schmidt <59456929+yumasheta@users.noreply.github.com>
|
||||
- Karthik Nadig <kanadig@microsoft.com>
|
||||
- Jürgen Hermann <jh@web.de>
|
||||
- Josselin Feist <josselin@trailofbits.com>
|
||||
- Jonathan Kotta <KottaJonathan@JohnDeere.com>
|
||||
- John Paraskevopoulos <io.paraskev@gmail.com>: add 'differing-param-doc' and 'differing-type-doc'
|
||||
- John McGehee <jmcgehee@altera.com>
|
||||
- John Gabriele <jgabriele@fastmail.fm>
|
||||
- John Belmonte <john@neggie.net>
|
||||
- Johannes Maron <johannes@maron.family>
|
||||
- Joffrey Mander <joffrey.mander+pro@gmail.com>
|
||||
- Jochen Preusche <iilei@users.noreply.github.com>
|
||||
- Jeroen Seegers <jeroenseegers@users.noreply.github.com>:
|
||||
* Fixed `toml` dependency issue
|
||||
- Jeremy Fleischman <jeremyfleischman@gmail.com>
|
||||
- Jason Owen <jason.a.owen@gmail.com>
|
||||
- Jason Lau <github.com@dotkr.nl>
|
||||
- Jared Garst <cultofjared@gmail.com>
|
||||
- Jared Deckard <jared.deckard@gmail.com>
|
||||
- Janne Rönkkö <jannero@users.noreply.github.com>
|
||||
- Jamie Scott <jamie@jami.org.uk>
|
||||
- James Sinclair <james@nurfherder.com>
|
||||
- James M. Allen <james.m.allen@gmail.com>
|
||||
- James Lingard <jchl@aristanetworks.com>
|
||||
- James Broadhead <jamesbroadhead@gmail.com>
|
||||
- Jakub Kulík <Kulikjak@gmail.com>
|
||||
- Jakob Normark <jakobnormark@gmail.com>
|
||||
- Jacques Kvam <jwkvam@gmail.com>
|
||||
- Jace Browning <jacebrowning@gmail.com>: updated default report format with clickable paths
|
||||
- JZ <jzohrab@gmail.com>
|
||||
- JT Olds <jtolds@xnet5.com>
|
||||
- Iggy Eom <iggy.eom@sendbird.com>
|
||||
- Ige-kun <178478713+Ige-kun@users.noreply.github.com>
|
||||
- Hayden Richards <62866982+SupImDos@users.noreply.github.com>
|
||||
* Fixed "no-self-use" for async methods
|
||||
* Fixed "docparams" extension for async functions and methods
|
||||
- Harshil <37377066+harshil21@users.noreply.github.com>
|
||||
- Harry <harrymcwinters@gmail.com>
|
||||
- Gwanbin Park <bgb1028@gmail.com>
|
||||
- Grégoire <96051754+gregoire-mullvad@users.noreply.github.com>
|
||||
- Grant Welch <gwelch925+github@gmail.com>
|
||||
- Giuseppe Valente <gvalente@arista.com>
|
||||
- Gary Tyler McLeod <mail@garytyler.com>
|
||||
- Felix von Drigalski <FvDrigalski@gmail.com>
|
||||
- Felix Preuschoff <37065638+felixp98@users.noreply.github.com>
|
||||
- Fabrice Douchant <Fabrice.Douchant@logilab.fr>
|
||||
- Fabio Natali <me@fabionatali.com>
|
||||
- Fabian Damken <fdamken+github@frisp.org>
|
||||
- Eric Froemling <ericfroemling@gmail.com>
|
||||
- Emmanuel Chaudron <manu.chaud@hotmail.fr>
|
||||
- Elizabeth Bott <52465744+elizabethbott@users.noreply.github.com>
|
||||
- Ekin Dursun <ekindursun@gmail.com>
|
||||
- Eisuke Kawashima <e-kwsm@users.noreply.github.com>
|
||||
- Edgemaster <grand.edgemaster@gmail.com>
|
||||
- Eddie Darling <eddie.darling@genapsys.com>
|
||||
- Drew Risinger <drewrisinger@users.noreply.github.com>
|
||||
- Dr. Nick <das-intensity@users.noreply.github.com>
|
||||
- Don Kirkby <donkirkby@users.noreply.github.com>
|
||||
- Don Jayamanne <don.jayamanne@yahoo.com>
|
||||
- Dominic Lavery <che@thisdevice.co.uk>
|
||||
- Dmytro Kyrychuk <dmytro.kyrychuck@gmail.com>
|
||||
- Dionisio E Alonso <baco@users.noreply.github.com>
|
||||
- DetachHead <57028336+DetachHead@users.noreply.github.com>
|
||||
- Dennis Keck <26092524+fellhorn@users.noreply.github.com>
|
||||
- Denis Laxalde <denis.laxalde@logilab.fr>
|
||||
- David Lawson <dmrlawson@gmail.com>
|
||||
- David Cain <davidjosephcain@gmail.com>
|
||||
- Danny Hermes <daniel.j.hermes@gmail.com>
|
||||
- Daniele Procida <daniele@vurt.org>
|
||||
- Daniela Plascencia <daplascen@gmail.com>
|
||||
- Daniel Werner <daniel.werner@scalableminds.com>
|
||||
- Daniel R. Neal <dan.r.neal@gmail.com> (danrneal)
|
||||
- Daniel Draper <Germandrummer92@users.noreply.github.com>
|
||||
- Daniel Dorani <ddandd@gmail.com> (doranid)
|
||||
- Daniel Brookman <53625739+dbrookman@users.noreply.github.com>
|
||||
- Dan Garrette <dhgarrette@gmail.com>
|
||||
- Damien Nozay <damien.nozay@gmail.com>
|
||||
- Cubicpath <Cubicpath@protonmail.com>
|
||||
- Craig Citro <craigcitro@gmail.com>
|
||||
- Cosmo <cosmo@cosmo.red>
|
||||
- Clément Schreiner <clement@mux.me>
|
||||
- Clément Pit-Claudel <cpitclaudel@users.noreply.github.com>
|
||||
- Christopher Zurcher <zurcher@users.noreply.github.com>
|
||||
- ChandanChainani <chandan.chainani@ibm.com>
|
||||
- Carl Crowder <bitbucket@carlcrowder.com>: don't evaluate the value of arguments for 'dangerous-default-value'
|
||||
- Carey Metcalfe <carey@cmetcalfe.ca>: demoted `try-except-raise` from error to warning
|
||||
- Cameron Olechowski <camsterole@users.noreply.github.com>
|
||||
- Calin Don <calin.don@gmail.com>
|
||||
- Caio Carrara <ccarrara@redhat.com>
|
||||
- C.A.M. Gerlach <WIDEnetServices@gmail.com>
|
||||
- Bruno P. Kinoshita <kinow@users.noreply.github.com>
|
||||
- Brice Chardin <brice.chardin@gmail.com>
|
||||
- Brian C. Lane <bcl@redhat.com>
|
||||
- Brandon W Maister <quodlibetor@gmail.com>
|
||||
- BioGeek <jeroen.vangoey@gmail.com>
|
||||
- Berker ŞAL <brkr.sal@gmail.com>
|
||||
- Benjamin Partzsch <32679788+bnjmnp@users.noreply.github.com>
|
||||
- Benjamin Graham <benwilliamgraham@gmail.com>
|
||||
- Benedikt Morbach <benedikt.morbach@googlemail.com>
|
||||
- Ben Greiner <code@bnavigator.de>
|
||||
- Barak Shoshany <baraksh@gmail.com>
|
||||
- Banjamin Freeman <befreeman@users.noreply.github.com>
|
||||
- Ayushi Kotiyal <70513726+Ayushikotiyal@users.noreply.github.com>
|
||||
- Avram Lubkin <avylove@rockhopper.net>
|
||||
- Athos Ribeiro <athoscr@fedoraproject.org>: Fixed dict-keys-not-iterating false positive for inverse containment checks
|
||||
- Arun Persaud <arun@nubati.net>
|
||||
- Arthur Lutz <arthur.lutz@logilab.fr>
|
||||
- Antonio Ossa <aaossa@uc.cl>
|
||||
- Antonio Gámiz Delgado <73933988+antoniogamizbadger@users.noreply.github.com>
|
||||
- Anthony VEREZ <anthony.verez.external@cassidian.com>
|
||||
- Anthony Tan <tanant@users.noreply.github.com>
|
||||
- Anthony Foglia <afoglia@users.noreply.github.com> (Google): Added simple string slots check.
|
||||
- Anentropic <ego@anentropic.com>
|
||||
- Andy Young <a7young@ucsd.edu>
|
||||
- Andy Palmer <25123779+ninezerozeronine@users.noreply.github.com>
|
||||
- Andrzej Klajnert <github@aklajnert.pl>
|
||||
- Andrew Howe <howeaj@users.noreply.github.com>
|
||||
- Andres Perez Hortal <andresperezcba@gmail.com>
|
||||
- Andre Hora <andrehora@users.noreply.github.com>
|
||||
- Aman Salwan <121633121+AmanSal1@users.noreply.github.com>
|
||||
- Alok Singh <8325708+alok@users.noreply.github.com>
|
||||
- Allan Chandler <95424144+allanc65@users.noreply.github.com> (allanc65)
|
||||
* Fixed issue 5452, false positive missing-param-doc for multi-line Google-style params
|
||||
- Alex Waygood <alex.waygood@gmail.com>
|
||||
- Alex Mor <5476113+nashcontrol@users.noreply.github.com>
|
||||
- Alex Jurkiewicz <alex@jurkiewi.cz>
|
||||
- Alex Hearn <alex.d.hearn@gmail.com>
|
||||
- Alex Fortin <alex.antoine.fortin@gmail.com>
|
||||
- Aleksander Mamla <alek.mamla@gmail.com>
|
||||
- Alan Evangelista <alanoe@linux.vnet.ibm.com>
|
||||
- Alan Chan <achan961117@gmail.com>
|
||||
- Aivar Annamaa <aivarannamaa@users.noreply.github.com>
|
||||
- Aidan Haase <44787650+haasea@users.noreply.github.com>
|
||||
- Ahirnish Pareek <ahirnish@gmail.com>: 'keyword-arg-before-var-arg' check
|
||||
- Agustin Marquez <agusdmb@gmail.com>
|
||||
- Adrian Chirieac <chirieacam@gmail.com>
|
||||
- Aditya Gupta <adityagupta1089@users.noreply.github.com> (adityagupta1089)
|
||||
* Added ignore_signatures to duplicate checker
|
||||
- Adam Tuft <73994535+adamtuft@users.noreply.github.com>
|
||||
- Adam Dangoor <adamdangoor@gmail.com>
|
||||
- 243f6a88 85a308d3 <33170174+243f6a8885a308d313198a2e037@users.noreply.github.com>
|
||||
|
||||
|
||||
Co-Author
|
||||
---------
|
||||
The following persons were credited manually but did not commit themselves
|
||||
under this name, or we did not manage to find their commits in the history.
|
||||
|
||||
- Agustin Toledo
|
||||
- Amaury Forgeot d'Arc: check names imported from a module exists in the module
|
||||
- Anthony Tan
|
||||
- Axel Muller
|
||||
- Benjamin Niemann: allow block level enabling/disabling of messages
|
||||
- Bernard Nauwelaerts
|
||||
- Bill Wendling
|
||||
- Brian van den Broek: windows installation documentation
|
||||
- Craig Henriques
|
||||
- D. Alphus (Alphadelta14)
|
||||
- Daniil Kharkov
|
||||
- Eero Vuojolahti
|
||||
- Fabio Zadrozny
|
||||
- Gauthier Sebaux
|
||||
- James DesLauriers
|
||||
- manderj
|
||||
- Mirko Friedenhagen
|
||||
- Nicholas Smith
|
||||
- Nuzula H. Yudaka (Nuzhuka)
|
||||
- Pek Chhan
|
||||
- Peter Hammond
|
||||
- Pierre Rouleau
|
||||
- Richard Goodman: simplifiable-if-expression (with Tomer Chachamu)
|
||||
- Sebastian Ulrich
|
||||
- Takashi Hirashima
|
||||
- Thomas Snowden: fix missing-docstring for inner functions
|
||||
- Wolfgang Grafen
|
||||
- Yannick Brehon
|
||||
@ -0,0 +1,340 @@
|
||||
GNU GENERAL PUBLIC LICENSE
|
||||
Version 2, June 1991
|
||||
|
||||
Copyright (C) 1989, 1991 Free Software Foundation, Inc.
|
||||
51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
Everyone is permitted to copy and distribute verbatim copies
|
||||
of this license document, but changing it is not allowed.
|
||||
|
||||
Preamble
|
||||
|
||||
The licenses for most software are designed to take away your
|
||||
freedom to share and change it. By contrast, the GNU General Public
|
||||
License is intended to guarantee your freedom to share and change free
|
||||
software--to make sure the software is free for all its users. This
|
||||
General Public License applies to most of the Free Software
|
||||
Foundation's software and to any other program whose authors commit to
|
||||
using it. (Some other Free Software Foundation software is covered by
|
||||
the GNU Library General Public License instead.) You can apply it to
|
||||
your programs, too.
|
||||
|
||||
When we speak of free software, we are referring to freedom, not
|
||||
price. Our General Public Licenses are designed to make sure that you
|
||||
have the freedom to distribute copies of free software (and charge for
|
||||
this service if you wish), that you receive source code or can get it
|
||||
if you want it, that you can change the software or use pieces of it
|
||||
in new free programs; and that you know you can do these things.
|
||||
|
||||
To protect your rights, we need to make restrictions that forbid
|
||||
anyone to deny you these rights or to ask you to surrender the rights.
|
||||
These restrictions translate to certain responsibilities for you if you
|
||||
distribute copies of the software, or if you modify it.
|
||||
|
||||
For example, if you distribute copies of such a program, whether
|
||||
gratis or for a fee, you must give the recipients all the rights that
|
||||
you have. You must make sure that they, too, receive or can get the
|
||||
source code. And you must show them these terms so they know their
|
||||
rights.
|
||||
|
||||
We protect your rights with two steps: (1) copyright the software, and
|
||||
(2) offer you this license which gives you legal permission to copy,
|
||||
distribute and/or modify the software.
|
||||
|
||||
Also, for each author's protection and ours, we want to make certain
|
||||
that everyone understands that there is no warranty for this free
|
||||
software. If the software is modified by someone else and passed on, we
|
||||
want its recipients to know that what they have is not the original, so
|
||||
that any problems introduced by others will not reflect on the original
|
||||
authors' reputations.
|
||||
|
||||
Finally, any free program is threatened constantly by software
|
||||
patents. We wish to avoid the danger that redistributors of a free
|
||||
program will individually obtain patent licenses, in effect making the
|
||||
program proprietary. To prevent this, we have made it clear that any
|
||||
patent must be licensed for everyone's free use or not licensed at all.
|
||||
|
||||
The precise terms and conditions for copying, distribution and
|
||||
modification follow.
|
||||
|
||||
GNU GENERAL PUBLIC LICENSE
|
||||
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
||||
|
||||
0. This License applies to any program or other work which contains
|
||||
a notice placed by the copyright holder saying it may be distributed
|
||||
under the terms of this General Public License. The "Program", below,
|
||||
refers to any such program or work, and a "work based on the Program"
|
||||
means either the Program or any derivative work under copyright law:
|
||||
that is to say, a work containing the Program or a portion of it,
|
||||
either verbatim or with modifications and/or translated into another
|
||||
language. (Hereinafter, translation is included without limitation in
|
||||
the term "modification".) Each licensee is addressed as "you".
|
||||
|
||||
Activities other than copying, distribution and modification are not
|
||||
covered by this License; they are outside its scope. The act of
|
||||
running the Program is not restricted, and the output from the Program
|
||||
is covered only if its contents constitute a work based on the
|
||||
Program (independent of having been made by running the Program).
|
||||
Whether that is true depends on what the Program does.
|
||||
|
||||
1. You may copy and distribute verbatim copies of the Program's
|
||||
source code as you receive it, in any medium, provided that you
|
||||
conspicuously and appropriately publish on each copy an appropriate
|
||||
copyright notice and disclaimer of warranty; keep intact all the
|
||||
notices that refer to this License and to the absence of any warranty;
|
||||
and give any other recipients of the Program a copy of this License
|
||||
along with the Program.
|
||||
|
||||
You may charge a fee for the physical act of transferring a copy, and
|
||||
you may at your option offer warranty protection in exchange for a fee.
|
||||
|
||||
2. You may modify your copy or copies of the Program or any portion
|
||||
of it, thus forming a work based on the Program, and copy and
|
||||
distribute such modifications or work under the terms of Section 1
|
||||
above, provided that you also meet all of these conditions:
|
||||
|
||||
a) You must cause the modified files to carry prominent notices
|
||||
stating that you changed the files and the date of any change.
|
||||
|
||||
b) You must cause any work that you distribute or publish, that in
|
||||
whole or in part contains or is derived from the Program or any
|
||||
part thereof, to be licensed as a whole at no charge to all third
|
||||
parties under the terms of this License.
|
||||
|
||||
c) If the modified program normally reads commands interactively
|
||||
when run, you must cause it, when started running for such
|
||||
interactive use in the most ordinary way, to print or display an
|
||||
announcement including an appropriate copyright notice and a
|
||||
notice that there is no warranty (or else, saying that you provide
|
||||
a warranty) and that users may redistribute the program under
|
||||
these conditions, and telling the user how to view a copy of this
|
||||
License. (Exception: if the Program itself is interactive but
|
||||
does not normally print such an announcement, your work based on
|
||||
the Program is not required to print an announcement.)
|
||||
|
||||
These requirements apply to the modified work as a whole. If
|
||||
identifiable sections of that work are not derived from the Program,
|
||||
and can be reasonably considered independent and separate works in
|
||||
themselves, then this License, and its terms, do not apply to those
|
||||
sections when you distribute them as separate works. But when you
|
||||
distribute the same sections as part of a whole which is a work based
|
||||
on the Program, the distribution of the whole must be on the terms of
|
||||
this License, whose permissions for other licensees extend to the
|
||||
entire whole, and thus to each and every part regardless of who wrote it.
|
||||
|
||||
Thus, it is not the intent of this section to claim rights or contest
|
||||
your rights to work written entirely by you; rather, the intent is to
|
||||
exercise the right to control the distribution of derivative or
|
||||
collective works based on the Program.
|
||||
|
||||
In addition, mere aggregation of another work not based on the Program
|
||||
with the Program (or with a work based on the Program) on a volume of
|
||||
a storage or distribution medium does not bring the other work under
|
||||
the scope of this License.
|
||||
|
||||
3. You may copy and distribute the Program (or a work based on it,
|
||||
under Section 2) in object code or executable form under the terms of
|
||||
Sections 1 and 2 above provided that you also do one of the following:
|
||||
|
||||
a) Accompany it with the complete corresponding machine-readable
|
||||
source code, which must be distributed under the terms of Sections
|
||||
1 and 2 above on a medium customarily used for software interchange; or,
|
||||
|
||||
b) Accompany it with a written offer, valid for at least three
|
||||
years, to give any third party, for a charge no more than your
|
||||
cost of physically performing source distribution, a complete
|
||||
machine-readable copy of the corresponding source code, to be
|
||||
distributed under the terms of Sections 1 and 2 above on a medium
|
||||
customarily used for software interchange; or,
|
||||
|
||||
c) Accompany it with the information you received as to the offer
|
||||
to distribute corresponding source code. (This alternative is
|
||||
allowed only for noncommercial distribution and only if you
|
||||
received the program in object code or executable form with such
|
||||
an offer, in accord with Subsection b above.)
|
||||
|
||||
The source code for a work means the preferred form of the work for
|
||||
making modifications to it. For an executable work, complete source
|
||||
code means all the source code for all modules it contains, plus any
|
||||
associated interface definition files, plus the scripts used to
|
||||
control compilation and installation of the executable. However, as a
|
||||
special exception, the source code distributed need not include
|
||||
anything that is normally distributed (in either source or binary
|
||||
form) with the major components (compiler, kernel, and so on) of the
|
||||
operating system on which the executable runs, unless that component
|
||||
itself accompanies the executable.
|
||||
|
||||
If distribution of executable or object code is made by offering
|
||||
access to copy from a designated place, then offering equivalent
|
||||
access to copy the source code from the same place counts as
|
||||
distribution of the source code, even though third parties are not
|
||||
compelled to copy the source along with the object code.
|
||||
|
||||
4. You may not copy, modify, sublicense, or distribute the Program
|
||||
except as expressly provided under this License. Any attempt
|
||||
otherwise to copy, modify, sublicense or distribute the Program is
|
||||
void, and will automatically terminate your rights under this License.
|
||||
However, parties who have received copies, or rights, from you under
|
||||
this License will not have their licenses terminated so long as such
|
||||
parties remain in full compliance.
|
||||
|
||||
5. You are not required to accept this License, since you have not
|
||||
signed it. However, nothing else grants you permission to modify or
|
||||
distribute the Program or its derivative works. These actions are
|
||||
prohibited by law if you do not accept this License. Therefore, by
|
||||
modifying or distributing the Program (or any work based on the
|
||||
Program), you indicate your acceptance of this License to do so, and
|
||||
all its terms and conditions for copying, distributing or modifying
|
||||
the Program or works based on it.
|
||||
|
||||
6. Each time you redistribute the Program (or any work based on the
|
||||
Program), the recipient automatically receives a license from the
|
||||
original licensor to copy, distribute or modify the Program subject to
|
||||
these terms and conditions. You may not impose any further
|
||||
restrictions on the recipients' exercise of the rights granted herein.
|
||||
You are not responsible for enforcing compliance by third parties to
|
||||
this License.
|
||||
|
||||
7. If, as a consequence of a court judgment or allegation of patent
|
||||
infringement or for any other reason (not limited to patent issues),
|
||||
conditions are imposed on you (whether by court order, agreement or
|
||||
otherwise) that contradict the conditions of this License, they do not
|
||||
excuse you from the conditions of this License. If you cannot
|
||||
distribute so as to satisfy simultaneously your obligations under this
|
||||
License and any other pertinent obligations, then as a consequence you
|
||||
may not distribute the Program at all. For example, if a patent
|
||||
license would not permit royalty-free redistribution of the Program by
|
||||
all those who receive copies directly or indirectly through you, then
|
||||
the only way you could satisfy both it and this License would be to
|
||||
refrain entirely from distribution of the Program.
|
||||
|
||||
If any portion of this section is held invalid or unenforceable under
|
||||
any particular circumstance, the balance of the section is intended to
|
||||
apply and the section as a whole is intended to apply in other
|
||||
circumstances.
|
||||
|
||||
It is not the purpose of this section to induce you to infringe any
|
||||
patents or other property right claims or to contest validity of any
|
||||
such claims; this section has the sole purpose of protecting the
|
||||
integrity of the free software distribution system, which is
|
||||
implemented by public license practices. Many people have made
|
||||
generous contributions to the wide range of software distributed
|
||||
through that system in reliance on consistent application of that
|
||||
system; it is up to the author/donor to decide if he or she is willing
|
||||
to distribute software through any other system and a licensee cannot
|
||||
impose that choice.
|
||||
|
||||
This section is intended to make thoroughly clear what is believed to
|
||||
be a consequence of the rest of this License.
|
||||
|
||||
8. If the distribution and/or use of the Program is restricted in
|
||||
certain countries either by patents or by copyrighted interfaces, the
|
||||
original copyright holder who places the Program under this License
|
||||
may add an explicit geographical distribution limitation excluding
|
||||
those countries, so that distribution is permitted only in or among
|
||||
countries not thus excluded. In such case, this License incorporates
|
||||
the limitation as if written in the body of this License.
|
||||
|
||||
9. The Free Software Foundation may publish revised and/or new versions
|
||||
of the General Public License from time to time. Such new versions will
|
||||
be similar in spirit to the present version, but may differ in detail to
|
||||
address new problems or concerns.
|
||||
|
||||
Each version is given a distinguishing version number. If the Program
|
||||
specifies a version number of this License which applies to it and "any
|
||||
later version", you have the option of following the terms and conditions
|
||||
either of that version or of any later version published by the Free
|
||||
Software Foundation. If the Program does not specify a version number of
|
||||
this License, you may choose any version ever published by the Free Software
|
||||
Foundation.
|
||||
|
||||
10. If you wish to incorporate parts of the Program into other free
|
||||
programs whose distribution conditions are different, write to the author
|
||||
to ask for permission. For software which is copyrighted by the Free
|
||||
Software Foundation, write to the Free Software Foundation; we sometimes
|
||||
make exceptions for this. Our decision will be guided by the two goals
|
||||
of preserving the free status of all derivatives of our free software and
|
||||
of promoting the sharing and reuse of software generally.
|
||||
|
||||
NO WARRANTY
|
||||
|
||||
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
|
||||
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
|
||||
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
|
||||
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
|
||||
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
||||
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
|
||||
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
|
||||
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
|
||||
REPAIR OR CORRECTION.
|
||||
|
||||
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
|
||||
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
|
||||
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
|
||||
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
|
||||
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
|
||||
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
|
||||
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
|
||||
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
|
||||
POSSIBILITY OF SUCH DAMAGES.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
How to Apply These Terms to Your New Programs
|
||||
|
||||
If you develop a new program, and you want it to be of the greatest
|
||||
possible use to the public, the best way to achieve this is to make it
|
||||
free software which everyone can redistribute and change under these terms.
|
||||
|
||||
To do so, attach the following notices to the program. It is safest
|
||||
to attach them to the start of each source file to most effectively
|
||||
convey the exclusion of warranty; and each file should have at least
|
||||
the "copyright" line and a pointer to where the full notice is found.
|
||||
|
||||
<one line to give the program's name and a brief idea of what it does.>
|
||||
Copyright (C) <year> <name of author>
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
|
||||
|
||||
Also add information on how to contact you by electronic and paper mail.
|
||||
|
||||
If the program is interactive, make it output a short notice like this
|
||||
when it starts in an interactive mode:
|
||||
|
||||
Gnomovision version 69, Copyright (C) year name of author
|
||||
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
|
||||
This is free software, and you are welcome to redistribute it
|
||||
under certain conditions; type `show c' for details.
|
||||
|
||||
The hypothetical commands `show w' and `show c' should show the appropriate
|
||||
parts of the General Public License. Of course, the commands you use may
|
||||
be called something other than `show w' and `show c'; they could even be
|
||||
mouse-clicks or menu items--whatever suits your program.
|
||||
|
||||
You should also get your employer (if you work as a programmer) or your
|
||||
school, if any, to sign a "copyright disclaimer" for the program, if
|
||||
necessary. Here is a sample; alter the names:
|
||||
|
||||
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
|
||||
`Gnomovision' (which makes passes at compilers) written by James Hacker.
|
||||
|
||||
<signature of Ty Coon>, 1 April 1989
|
||||
Ty Coon, President of Vice
|
||||
|
||||
This General Public License does not permit incorporating your program into
|
||||
proprietary programs. If your program is a subroutine library, you may
|
||||
consider it more useful to permit linking proprietary applications with the
|
||||
library. If this is what you want to do, use the GNU Library General
|
||||
Public License instead of this License.
|
||||
@ -0,0 +1,14 @@
|
||||
include README.rst
|
||||
include requirements_test_min.txt
|
||||
include requirements_test_pre_commit.txt
|
||||
include requirements_test.txt
|
||||
include tox.ini
|
||||
graft doc
|
||||
graft examples
|
||||
graft script
|
||||
graft tests
|
||||
prune doc/_build
|
||||
prune tests/.benchmarks
|
||||
prune tests/.pylint_primer_tests
|
||||
global-exclude __pycache__
|
||||
global-exclude *.py[co]
|
||||
@ -0,0 +1,225 @@
|
||||
`Pylint`_
|
||||
=========
|
||||
|
||||
.. _`Pylint`: https://pylint.readthedocs.io/
|
||||
|
||||
.. This is used inside the doc to recover the start of the introduction
|
||||
|
||||
.. image:: https://github.com/pylint-dev/pylint/actions/workflows/tests.yaml/badge.svg?branch=main
|
||||
:target: https://github.com/pylint-dev/pylint/actions
|
||||
|
||||
.. image:: https://codecov.io/gh/pylint-dev/pylint/branch/main/graph/badge.svg?token=ZETEzayrfk
|
||||
:target: https://codecov.io/gh/pylint-dev/pylint
|
||||
|
||||
.. image:: https://img.shields.io/pypi/v/pylint.svg
|
||||
:alt: PyPI Package version
|
||||
:target: https://pypi.python.org/pypi/pylint
|
||||
|
||||
.. image:: https://readthedocs.org/projects/pylint/badge/?version=latest
|
||||
:target: https://pylint.readthedocs.io/en/latest/?badge=latest
|
||||
:alt: Documentation Status
|
||||
|
||||
.. image:: https://img.shields.io/badge/code%20style-black-000000.svg
|
||||
:target: https://github.com/ambv/black
|
||||
|
||||
.. image:: https://img.shields.io/badge/linting-pylint-yellowgreen
|
||||
:target: https://github.com/pylint-dev/pylint
|
||||
|
||||
.. image:: https://results.pre-commit.ci/badge/github/pylint-dev/pylint/main.svg
|
||||
:target: https://results.pre-commit.ci/latest/github/pylint-dev/pylint/main
|
||||
:alt: pre-commit.ci status
|
||||
|
||||
.. image:: https://bestpractices.coreinfrastructure.org/projects/6328/badge
|
||||
:target: https://bestpractices.coreinfrastructure.org/projects/6328
|
||||
:alt: CII Best Practices
|
||||
|
||||
.. image:: https://img.shields.io/ossf-scorecard/github.com/PyCQA/pylint?label=openssf%20scorecard&style=flat
|
||||
:target: https://api.securityscorecards.dev/projects/github.com/PyCQA/pylint
|
||||
:alt: OpenSSF Scorecard
|
||||
|
||||
.. image:: https://img.shields.io/discord/825463413634891776.svg
|
||||
:target: https://discord.gg/qYxpadCgkx
|
||||
:alt: Discord
|
||||
|
||||
What is Pylint?
|
||||
---------------
|
||||
|
||||
Pylint is a `static code analyser`_ for Python 2 or 3. The latest version supports Python
|
||||
3.10.0 and above.
|
||||
|
||||
.. _`static code analyser`: https://en.wikipedia.org/wiki/Static_code_analysis
|
||||
|
||||
Pylint analyses your code without actually running it. It checks for errors, enforces a
|
||||
coding standard, looks for `code smells`_, and can make suggestions about how the code
|
||||
could be refactored.
|
||||
|
||||
.. _`code smells`: https://martinfowler.com/bliki/CodeSmell.html
|
||||
|
||||
Install
|
||||
-------
|
||||
|
||||
.. This is used inside the doc to recover the start of the short text for installation
|
||||
|
||||
For command line use, pylint is installed with::
|
||||
|
||||
pip install pylint
|
||||
|
||||
Or if you want to also check spelling with ``enchant`` (you might need to
|
||||
`install the enchant C library <https://pyenchant.github.io/pyenchant/install.html#installing-the-enchant-c-library>`_):
|
||||
|
||||
.. code-block:: sh
|
||||
|
||||
pip install pylint[spelling]
|
||||
|
||||
It can also be integrated in most editors or IDEs. More information can be found
|
||||
`in the documentation`_.
|
||||
|
||||
.. _in the documentation: https://pylint.readthedocs.io/en/latest/user_guide/installation/index.html
|
||||
|
||||
.. This is used inside the doc to recover the end of the short text for installation
|
||||
|
||||
What differentiates Pylint?
|
||||
---------------------------
|
||||
|
||||
Pylint is not trusting your typing and is inferring the actual values of nodes (for a
|
||||
start because there was no typing when pylint started off) using its internal code
|
||||
representation (astroid). If your code is ``import logging as argparse``, Pylint
|
||||
can check and know that ``argparse.error(...)`` is in fact a logging call and not an
|
||||
argparse call. This makes pylint slower, but it also lets pylint find more issues if
|
||||
your code is not fully typed.
|
||||
|
||||
[inference] is the killer feature that keeps us using [pylint] in our project despite how painfully slow it is.
|
||||
- `Realist pylint user`_, 2022
|
||||
|
||||
.. _`Realist pylint user`: https://github.com/charliermarsh/ruff/issues/970#issuecomment-1381067064
|
||||
|
||||
pylint, not afraid of being a little slower than it already is, is also a lot more thorough than other linters.
|
||||
There are more checks, including some opinionated ones that are deactivated by default
|
||||
but can be enabled using configuration.
|
||||
|
||||
How to use pylint
|
||||
-----------------
|
||||
|
||||
Pylint isn't smarter than you: it may warn you about things that you have
|
||||
conscientiously done or check for some things that you don't care about.
|
||||
During adoption, especially in a legacy project where pylint was never enforced,
|
||||
it's best to start with the ``--errors-only`` flag, then disable
|
||||
convention and refactor messages with ``--disable=C,R`` and progressively
|
||||
re-evaluate and re-enable messages as your priorities evolve.
|
||||
|
||||
Pylint is highly configurable and permits to write plugins in order to add your
|
||||
own checks (for example, for internal libraries or an internal rule). Pylint also has an
|
||||
ecosystem of existing plugins for popular frameworks and third-party libraries.
|
||||
|
||||
.. note::
|
||||
|
||||
Pylint supports the Python standard library out of the box. Third-party
|
||||
libraries are not always supported, so a plugin might be needed. A good place
|
||||
to start is ``PyPI`` which often returns a plugin by searching for
|
||||
``pylint <library>``. `pylint-pydantic`_, `pylint-django`_ and
|
||||
`pylint-sonarjson`_ are examples of such plugins. More information about plugins
|
||||
and how to load them can be found at `plugins`_.
|
||||
|
||||
.. _`plugins`: https://pylint.readthedocs.io/en/latest/development_guide/how_tos/plugins.html#plugins
|
||||
.. _`pylint-pydantic`: https://pypi.org/project/pylint-pydantic
|
||||
.. _`pylint-django`: https://github.com/pylint-dev/pylint-django
|
||||
.. _`pylint-sonarjson`: https://github.com/cnescatlab/pylint-sonarjson-catlab
|
||||
|
||||
Advised linters alongside pylint
|
||||
--------------------------------
|
||||
|
||||
Projects that you might want to use alongside pylint include ruff_ (**really** fast,
|
||||
with builtin auto-fix and a large number of checks taken from popular linters, but
|
||||
implemented in ``rust``) or flake8_ (a framework to implement your own checks in python using ``ast`` directly),
|
||||
mypy_, pyright_ / pylance or pyre_ (typing checks), bandit_ (security oriented checks), black_ and
|
||||
isort_ (auto-formatting), autoflake_ (automated removal of unused imports or variables), pyupgrade_
|
||||
(automated upgrade to newer python syntax) and pydocstringformatter_ (automated pep257).
|
||||
|
||||
.. _ruff: https://github.com/astral-sh/ruff
|
||||
.. _flake8: https://github.com/PyCQA/flake8
|
||||
.. _bandit: https://github.com/PyCQA/bandit
|
||||
.. _mypy: https://github.com/python/mypy
|
||||
.. _pyright: https://github.com/microsoft/pyright
|
||||
.. _pyre: https://github.com/facebook/pyre-check
|
||||
.. _black: https://github.com/psf/black
|
||||
.. _autoflake: https://github.com/myint/autoflake
|
||||
.. _pyupgrade: https://github.com/asottile/pyupgrade
|
||||
.. _pydocstringformatter: https://github.com/DanielNoord/pydocstringformatter
|
||||
.. _isort: https://pycqa.github.io/isort/
|
||||
|
||||
Additional tools included in pylint
|
||||
-----------------------------------
|
||||
|
||||
Pylint ships with two additional tools:
|
||||
|
||||
- pyreverse_ (standalone tool that generates package and class diagrams.)
|
||||
- symilar_ (duplicate code finder that is also integrated in pylint)
|
||||
|
||||
.. _pyreverse: https://pylint.readthedocs.io/en/latest/additional_tools/pyreverse/index.html
|
||||
.. _symilar: https://pylint.readthedocs.io/en/latest/additional_tools/symilar/index.html
|
||||
|
||||
|
||||
.. This is used inside the doc to recover the end of the introduction
|
||||
|
||||
Contributing
|
||||
------------
|
||||
|
||||
.. This is used inside the doc to recover the start of the short text for contribution
|
||||
|
||||
We welcome all forms of contributions such as updates for documentation, new code, checking issues for duplicates or telling us
|
||||
that we can close them, confirming that issues still exist, `creating issues because
|
||||
you found a bug or want a feature`_, etc. Everything is much appreciated!
|
||||
|
||||
Please follow the `code of conduct`_ and check `the Contributor Guides`_ if you want to
|
||||
make a code contribution.
|
||||
|
||||
.. _creating issues because you found a bug or want a feature: https://pylint.readthedocs.io/en/latest/contact.html#bug-reports-feedback
|
||||
.. _code of conduct: https://github.com/pylint-dev/pylint/blob/main/CODE_OF_CONDUCT.md
|
||||
.. _the Contributor Guides: https://pylint.readthedocs.io/en/latest/development_guide/contribute.html
|
||||
|
||||
.. This is used inside the doc to recover the end of the short text for contribution
|
||||
|
||||
Show your usage
|
||||
-----------------
|
||||
|
||||
You can place this badge in your README to let others know your project uses pylint.
|
||||
|
||||
.. image:: https://img.shields.io/badge/linting-pylint-yellowgreen
|
||||
:target: https://github.com/pylint-dev/pylint
|
||||
|
||||
Learn how to add a badge to your documentation in `the badge documentation`_.
|
||||
|
||||
.. _the badge documentation: https://pylint.readthedocs.io/en/latest/user_guide/installation/badge.html
|
||||
|
||||
License
|
||||
-------
|
||||
|
||||
pylint is, with a few exceptions listed below, `GPLv2 <https://github.com/pylint-dev/pylint/blob/main/LICENSE>`_.
|
||||
|
||||
The icon files are licensed under the `CC BY-SA 4.0 <https://creativecommons.org/licenses/by-sa/4.0/>`_ license:
|
||||
|
||||
- `doc/logo.png <https://raw.githubusercontent.com/pylint-dev/pylint/main/doc/logo.png>`_
|
||||
- `doc/logo.svg <https://raw.githubusercontent.com/pylint-dev/pylint/main/doc/logo.svg>`_
|
||||
|
||||
Support
|
||||
-------
|
||||
|
||||
Please check `the contact information`_.
|
||||
|
||||
.. _`the contact information`: https://pylint.readthedocs.io/en/latest/contact.html
|
||||
|
||||
.. |tideliftlogo| image:: https://raw.githubusercontent.com/pylint-dev/pylint/main/doc/media/Tidelift_Logos_RGB_Tidelift_Shorthand_On-White.png
|
||||
:width: 200
|
||||
:alt: Tidelift
|
||||
|
||||
.. list-table::
|
||||
:widths: 10 100
|
||||
|
||||
* - |tideliftlogo|
|
||||
- Professional support for pylint is available as part of the `Tidelift
|
||||
Subscription`_. Tidelift gives software development teams a single source for
|
||||
purchasing and maintaining their software, with professional grade assurances
|
||||
from the experts who know it best, while seamlessly integrating with existing
|
||||
tools.
|
||||
|
||||
.. _Tidelift Subscription: https://tidelift.com/subscription/pkg/pypi-pylint?utm_source=pypi-pylint&utm_medium=referral&utm_campaign=readme
|
||||
@ -0,0 +1,10 @@
|
||||
coverage:
|
||||
status:
|
||||
patch:
|
||||
default:
|
||||
target: 100%
|
||||
project:
|
||||
default:
|
||||
target: 95%
|
||||
comment:
|
||||
layout: "reach, diff, flags, files"
|
||||
@ -0,0 +1,396 @@
|
||||
abc
|
||||
abcmeta
|
||||
abspath
|
||||
abstractproperty
|
||||
analyse
|
||||
analysed
|
||||
analysing
|
||||
arg
|
||||
argparse
|
||||
args
|
||||
argumentdefaultshelpformatter
|
||||
argumentparser
|
||||
argumentsparser
|
||||
argv
|
||||
ascii
|
||||
asend
|
||||
assignattr
|
||||
assignname
|
||||
AST
|
||||
ast
|
||||
astroid
|
||||
async
|
||||
asynccontextmanager
|
||||
attr
|
||||
attrib
|
||||
attrname
|
||||
backport
|
||||
BaseChecker
|
||||
basename
|
||||
behaviour
|
||||
bidi
|
||||
Bitbucket
|
||||
bla
|
||||
bom
|
||||
bool
|
||||
boolean
|
||||
booleaness
|
||||
boolop
|
||||
boundmethod
|
||||
builtins
|
||||
bw
|
||||
callables
|
||||
cardinality
|
||||
cd
|
||||
cfg
|
||||
changelog
|
||||
cheaders
|
||||
chroot
|
||||
chunker
|
||||
classdef
|
||||
classdiagram
|
||||
classmethod
|
||||
classmethod's
|
||||
classname
|
||||
classobj
|
||||
CLI
|
||||
cls
|
||||
cmp
|
||||
codebase
|
||||
codec
|
||||
codecs
|
||||
col's
|
||||
conf
|
||||
config
|
||||
const
|
||||
Const
|
||||
contextlib
|
||||
contextmanager
|
||||
contravariance
|
||||
contravariant
|
||||
cgroup
|
||||
CPython
|
||||
cpython
|
||||
csv
|
||||
CVE
|
||||
cwd
|
||||
cyclomatic
|
||||
dataclass
|
||||
dataclasses
|
||||
datetime
|
||||
debian
|
||||
deduplication
|
||||
deepcopy
|
||||
defaultdicts
|
||||
defframe
|
||||
defstmts
|
||||
deleter
|
||||
dependabot
|
||||
deque
|
||||
destructured
|
||||
destructuring
|
||||
diadefs
|
||||
diadefslib
|
||||
dictcomp
|
||||
dicts
|
||||
dir
|
||||
dirname
|
||||
docparams
|
||||
docstring
|
||||
docstrings
|
||||
dumpable
|
||||
dunder
|
||||
elif
|
||||
elif's
|
||||
elt
|
||||
emittable
|
||||
encodings
|
||||
endswith
|
||||
enum
|
||||
enums
|
||||
epilog
|
||||
epylint
|
||||
epytext
|
||||
erroring
|
||||
etree
|
||||
expr
|
||||
falsey
|
||||
favour
|
||||
filepath
|
||||
filestream
|
||||
finalbody
|
||||
# TODO Remove when we are able to remove our own symbols
|
||||
fixme
|
||||
Flymake
|
||||
fmt
|
||||
formatter
|
||||
formfeed
|
||||
fromlineno
|
||||
fullname
|
||||
func
|
||||
functiondef
|
||||
functiøn
|
||||
functools
|
||||
genexpr
|
||||
getattr
|
||||
globals
|
||||
globbing
|
||||
GPL
|
||||
graphname
|
||||
graphviz
|
||||
grey
|
||||
guido's
|
||||
gv
|
||||
hashable
|
||||
hmac
|
||||
html
|
||||
idgeneratormixin
|
||||
ifexpr
|
||||
igetattr
|
||||
importedname
|
||||
importfrom
|
||||
importnode
|
||||
importschecker
|
||||
InferenceError
|
||||
ini
|
||||
INI
|
||||
init
|
||||
initializer
|
||||
inlinevar
|
||||
instantiation
|
||||
isdir
|
||||
isfile
|
||||
isinstance
|
||||
isort
|
||||
iter
|
||||
iterable
|
||||
iterables
|
||||
itered
|
||||
iteritems
|
||||
iTerm
|
||||
jn
|
||||
jpg
|
||||
json
|
||||
jx
|
||||
jython
|
||||
# class is a reserved word
|
||||
klass
|
||||
kwarg
|
||||
kwargs
|
||||
kwonlyargs
|
||||
latin
|
||||
len
|
||||
lhs
|
||||
linecache
|
||||
lineno
|
||||
linenum
|
||||
lineset
|
||||
lineset's
|
||||
linesets
|
||||
linkers
|
||||
linter
|
||||
linux
|
||||
listcomp
|
||||
Logilab
|
||||
longstring
|
||||
lsp
|
||||
mapfile
|
||||
mapreduce
|
||||
maxsize
|
||||
maxsplit
|
||||
mcs
|
||||
mermaidjs
|
||||
metaclass
|
||||
metaclasses
|
||||
misdesign
|
||||
misdesigns
|
||||
mixin
|
||||
modname
|
||||
monkeypatch
|
||||
mro
|
||||
# Used so much that we need the abbreviation
|
||||
msg
|
||||
msg-template
|
||||
msgid
|
||||
msgids
|
||||
msgs
|
||||
mult
|
||||
multiline
|
||||
multiset
|
||||
multisets
|
||||
myattr
|
||||
myfunction
|
||||
mymain
|
||||
mymethod
|
||||
mymodule
|
||||
mypy
|
||||
namedtuple
|
||||
namespace
|
||||
newsfile
|
||||
newstyle
|
||||
nl
|
||||
nodename
|
||||
nodeng
|
||||
noinspection
|
||||
nonlocal
|
||||
nonlocals
|
||||
num
|
||||
numpy
|
||||
ok
|
||||
optdict
|
||||
optik
|
||||
optionals
|
||||
optiondict
|
||||
optname
|
||||
optparse
|
||||
optvalue
|
||||
orelse
|
||||
os
|
||||
outputfile
|
||||
overridable
|
||||
params
|
||||
paren
|
||||
parens
|
||||
passthru
|
||||
pathlib
|
||||
patternerror
|
||||
png
|
||||
positionals
|
||||
pragma
|
||||
pragma's
|
||||
pragmas
|
||||
pre
|
||||
preorder
|
||||
prepended
|
||||
proc
|
||||
py
|
||||
pyenchant
|
||||
pyfile
|
||||
pyi
|
||||
pylint
|
||||
pylint's
|
||||
pylintdict
|
||||
pylintrc
|
||||
pyproject
|
||||
pypy
|
||||
pyreverse
|
||||
pytest
|
||||
qname
|
||||
rawcheckers
|
||||
rc
|
||||
rcfile
|
||||
re-usable
|
||||
readlines
|
||||
recognise
|
||||
recurse
|
||||
recurses
|
||||
redef
|
||||
reportid
|
||||
rgx
|
||||
rheaders
|
||||
rhs
|
||||
roid
|
||||
rsplit
|
||||
rst
|
||||
rstrip
|
||||
rtype
|
||||
runtime
|
||||
se
|
||||
seaborn
|
||||
sep
|
||||
setcomp
|
||||
shortstrings
|
||||
singledispatch
|
||||
singledispatchmethod
|
||||
spammy
|
||||
sqlalchemy
|
||||
src
|
||||
starargs
|
||||
stateful
|
||||
staticmethod
|
||||
stderr
|
||||
stdin
|
||||
stdlib
|
||||
stdout
|
||||
stmt
|
||||
str
|
||||
stringified
|
||||
subclasses
|
||||
subcommands
|
||||
subdicts
|
||||
subgraphs
|
||||
sublists
|
||||
submodule
|
||||
submodules
|
||||
subparsers
|
||||
subparts
|
||||
subprocess
|
||||
subscriptable
|
||||
subscripted
|
||||
subtree
|
||||
supcls
|
||||
superclass
|
||||
symilar
|
||||
symlink
|
||||
symlinks
|
||||
sys
|
||||
tbump
|
||||
tempfile
|
||||
testcase
|
||||
testdata
|
||||
testoptions
|
||||
tmp
|
||||
tokencheckers
|
||||
tokeninfo
|
||||
tokenization
|
||||
tokenize
|
||||
tokenizer
|
||||
toml
|
||||
tomlkit
|
||||
toplevel
|
||||
towncrier
|
||||
tp
|
||||
truthey
|
||||
truthness
|
||||
truthy
|
||||
tryexcept
|
||||
txt
|
||||
typecheck
|
||||
typechecking
|
||||
typeddict
|
||||
typehint
|
||||
typeshed
|
||||
uid
|
||||
uml
|
||||
un
|
||||
unary
|
||||
unflattens
|
||||
unhandled
|
||||
unicode
|
||||
uninferable
|
||||
Uninferable
|
||||
unittest
|
||||
unraisablehook
|
||||
untriggered
|
||||
# prefix for string
|
||||
ur
|
||||
ureport
|
||||
ureports
|
||||
utf
|
||||
utils
|
||||
validator
|
||||
vararg
|
||||
varargs
|
||||
variadic
|
||||
variadics
|
||||
vcg
|
||||
vcg's
|
||||
vectorisation
|
||||
virtualized
|
||||
wc
|
||||
whitespaces
|
||||
xfails
|
||||
xml
|
||||
xyz
|
||||
yml
|
||||
yoda
|
||||
@ -0,0 +1,47 @@
|
||||
# You can set these variables from the command line, and also
|
||||
# from the environment for the first two.
|
||||
SPHINXOPTS ?=
|
||||
SPHINXBUILD ?= sphinx-build
|
||||
SOURCEDIR = .
|
||||
BUILDDIR = _build
|
||||
|
||||
# Put it first so that "make" without argument is like "make help".
|
||||
help:
|
||||
@$(SPHINXBUILD) -M help "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O)
|
||||
|
||||
.PHONY: help Makefile
|
||||
|
||||
# Catch-all target: route all unknown targets to Sphinx using the new
|
||||
# "make mode" option. $(O) is meant as a shortcut for $(SPHINXOPTS).
|
||||
%: Makefile
|
||||
@$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O)
|
||||
|
||||
# --------------------------------
|
||||
# This part is specific to pylint.
|
||||
#---------------------------------
|
||||
|
||||
# Set PYLINT_SPHINX_FATAL_WARNINGS= on the command line to restore the default.
|
||||
PYLINT_SPHINX_FATAL_WARNINGS = -W --keep-going
|
||||
|
||||
# Do not use O, we abuse it for internal purposes.
|
||||
O = -d $(BUILDDIR)/doctrees -T $(PYLINT_SPHINX_FATAL_WARNINGS) -n
|
||||
|
||||
.PHONY clean: remove-generated-messages
|
||||
remove-generated-messages:
|
||||
rm -rf user_guide/messages/convention user_guide/messages/error \
|
||||
user_guide/messages/fatal user_guide/messages/information user_guide/messages/refactor \
|
||||
user_guide/messages/warning
|
||||
|
||||
# Generated by exts/*.py but kept in the VCS for easier review of changes:
|
||||
.PHONY: distclean
|
||||
distclean: clean
|
||||
rm -f user_guide/checkers/extensions.rst user_guide/checkers/features.rst \
|
||||
user_guide/configuration/all-options.rst user_guide/messages/messages_overview.rst
|
||||
|
||||
# Set PIP=true on the command line to skip installation of dependencies.
|
||||
PIP = pip
|
||||
|
||||
.PHONY html: install-dependencies
|
||||
install-dependencies:
|
||||
@echo "Install dependencies"
|
||||
cd ../ && $(PIP) install -r doc/requirements.txt
|
||||
@ -0,0 +1,201 @@
|
||||
.. This file is auto-generated. Make any changes to the associated
|
||||
.. docs extension in 'doc/exts/pyreverse_configuration.py'.
|
||||
|
||||
|
||||
Usage
|
||||
#####
|
||||
|
||||
|
||||
``pyreverse`` is run from the command line using the following syntax::
|
||||
|
||||
pyreverse [options] <packages>
|
||||
|
||||
where ``<packages>`` is one or more Python packages or modules to analyze.
|
||||
|
||||
The available options are organized into the following categories:
|
||||
|
||||
* :ref:`filtering-and-scope` - Control which classes and relationships appear in your diagrams
|
||||
* :ref:`display-options` - Customize the visual appearance including colors and labels
|
||||
* :ref:`output-control` - Select output formats and set the destination directory
|
||||
* :ref:`project-configuration` - Define project settings like source roots and ignored files
|
||||
|
||||
|
||||
.. _filtering-and-scope:
|
||||
|
||||
Filtering and Scope
|
||||
===================
|
||||
|
||||
|
||||
--all-ancestors
|
||||
---------------
|
||||
*Show all ancestors of all classes in <projects>.*
|
||||
|
||||
**Default:** ``None``
|
||||
|
||||
|
||||
--all-associated
|
||||
----------------
|
||||
*Show all classes associated with the target classes, including indirect associations.*
|
||||
|
||||
**Default:** ``None``
|
||||
|
||||
|
||||
--class
|
||||
-------
|
||||
*Create a class diagram with all classes related to <class>; this uses by default the options -ASmy*
|
||||
|
||||
**Default:** ``None``
|
||||
|
||||
|
||||
--filter-mode
|
||||
-------------
|
||||
*Filter attributes and functions according to <mode>. Correct modes are:
|
||||
'PUB_ONLY' filter all non public attributes [DEFAULT], equivalent to PRIVATE+SPECIAL
|
||||
'ALL' no filter
|
||||
'SPECIAL' filter Python special functions except constructor
|
||||
'OTHER' filter protected and private attributes*
|
||||
|
||||
**Default:** ``PUB_ONLY``
|
||||
|
||||
|
||||
--max-depth
|
||||
-----------
|
||||
*Maximum depth of packages/modules to include in the diagram, relative to the deepest specified package. A depth of 0 shows only the specified packages/modules, while 1 includes their immediate children, etc. When specifying nested packages, depth is calculated from the deepest package level. If not specified, all packages/modules in the hierarchy are shown.*
|
||||
|
||||
**Default:** ``None``
|
||||
|
||||
|
||||
--show-ancestors
|
||||
----------------
|
||||
*Show <ancestor> generations of ancestor classes not in <projects>.*
|
||||
|
||||
**Default:** ``None``
|
||||
|
||||
|
||||
--show-associated
|
||||
-----------------
|
||||
*Show <association_level> levels of associated classes not in <projects>.*
|
||||
|
||||
**Default:** ``None``
|
||||
|
||||
|
||||
--show-builtin
|
||||
--------------
|
||||
*Include builtin objects in representation of classes.*
|
||||
|
||||
**Default:** ``False``
|
||||
|
||||
|
||||
--show-stdlib
|
||||
-------------
|
||||
*Include standard library objects in representation of classes.*
|
||||
|
||||
**Default:** ``False``
|
||||
|
||||
|
||||
|
||||
|
||||
.. _display-options:
|
||||
|
||||
Display Options
|
||||
===============
|
||||
|
||||
|
||||
--color-palette
|
||||
---------------
|
||||
*Comma separated list of colors to use for the package depth coloring.*
|
||||
|
||||
**Default:** ``('#77AADD', '#99DDFF', '#44BB99', '#BBCC33', '#AAAA00', '#EEDD88', '#EE8866', '#FFAABB', '#DDDDDD')``
|
||||
|
||||
|
||||
--colorized
|
||||
-----------
|
||||
*Use colored output. Classes/modules of the same package get the same color.*
|
||||
|
||||
**Default:** ``False``
|
||||
|
||||
|
||||
--max-color-depth
|
||||
-----------------
|
||||
*Use separate colors up to package depth of <depth>. Higher depths will reuse colors.*
|
||||
|
||||
**Default:** ``2``
|
||||
|
||||
|
||||
--module-names
|
||||
--------------
|
||||
*Include module name in the representation of classes.*
|
||||
|
||||
**Default:** ``None``
|
||||
|
||||
|
||||
--no-standalone
|
||||
---------------
|
||||
*Only show nodes with connections.*
|
||||
|
||||
**Default:** ``False``
|
||||
|
||||
|
||||
--only-classnames
|
||||
-----------------
|
||||
*Don't show attributes and methods in the class boxes; this disables -f values.*
|
||||
|
||||
**Default:** ``False``
|
||||
|
||||
|
||||
|
||||
|
||||
.. _output-control:
|
||||
|
||||
Output Control
|
||||
==============
|
||||
|
||||
|
||||
--output
|
||||
--------
|
||||
*Create a *.<format> output file if format is available. Available formats are: .dot, .puml, .plantuml, .mmd, .html. Any other format will be tried to be created by using the 'dot' command line tool, which requires a graphviz installation. In this case, these additional formats are available (see `Graphviz output formats <https://graphviz.org/docs/outputs/>`_).*
|
||||
|
||||
**Default:** ``dot``
|
||||
|
||||
|
||||
--output-directory
|
||||
------------------
|
||||
*Set the output directory path.*
|
||||
|
||||
**Default:** ``""``
|
||||
|
||||
|
||||
|
||||
|
||||
.. _project-configuration:
|
||||
|
||||
Project Configuration
|
||||
=====================
|
||||
|
||||
|
||||
--ignore
|
||||
--------
|
||||
*Files or directories to be skipped. They should be base names, not paths.*
|
||||
|
||||
**Default:** ``('CVS',)``
|
||||
|
||||
|
||||
--project
|
||||
---------
|
||||
*Set the project name. This will later be appended to the output file names.*
|
||||
|
||||
**Default:** ``""``
|
||||
|
||||
|
||||
--source-roots
|
||||
--------------
|
||||
*Add paths to the list of the source roots. Supports globbing patterns. The source root is an absolute path or a path relative to the current working directory used to determine a package namespace for modules located under the source root.*
|
||||
|
||||
**Default:** ``()``
|
||||
|
||||
|
||||
--verbose
|
||||
---------
|
||||
*Makes pyreverse more verbose/talkative. Mostly useful for debugging.*
|
||||
|
||||
**Default:** ``False``
|
||||
@ -0,0 +1,40 @@
|
||||
.. _pyreverse:
|
||||
|
||||
=========
|
||||
Pyreverse
|
||||
=========
|
||||
|
||||
``pyreverse`` is a powerful tool that creates UML diagrams from your Python code. It helps you visualize:
|
||||
|
||||
- Package dependencies and structure
|
||||
- Class hierarchies and relationships
|
||||
- Method and attribute organization
|
||||
|
||||
Output Formats
|
||||
==============
|
||||
|
||||
``pyreverse`` supports multiple output formats:
|
||||
|
||||
* Native formats:
|
||||
* ``.dot``/``.gv`` (Graphviz)
|
||||
* ``.puml``/``.plantuml`` (PlantUML)
|
||||
* ``.mmd``/``.html`` (MermaidJS)
|
||||
|
||||
* Additional formats (requires Graphviz installation):
|
||||
* All `Graphviz output formats <https://graphviz.org/docs/outputs/>`_ (PNG, SVG, PDF, etc.)
|
||||
* ``pyreverse`` first generates a temporary ``.gv`` file, which is then fed to Graphviz to generate the final image
|
||||
|
||||
Getting Started
|
||||
===============
|
||||
|
||||
Check out the :doc:`configuration` guide to learn about available options, or see :doc:`output_examples`
|
||||
for sample diagrams and common use cases.
|
||||
|
||||
.. toctree::
|
||||
:maxdepth: 2
|
||||
:caption: Pyreverse
|
||||
:titlesonly:
|
||||
:hidden:
|
||||
|
||||
configuration
|
||||
output_examples
|
||||
@ -0,0 +1,40 @@
|
||||
Example Output
|
||||
##############
|
||||
|
||||
Example diagrams generated with the ``.puml`` output format are shown below.
|
||||
|
||||
Package Diagram
|
||||
...............
|
||||
|
||||
.. image:: ../../media/pyreverse_example_packages.png
|
||||
:width: 344
|
||||
:height: 177
|
||||
:alt: Package diagram generated by pyreverse
|
||||
:align: center
|
||||
|
||||
Class Diagram
|
||||
.............
|
||||
|
||||
.. image:: ../../media/pyreverse_example_classes.png
|
||||
:width: 625
|
||||
:height: 589
|
||||
:alt: Class diagram generated by pyreverse
|
||||
:align: center
|
||||
|
||||
Creating Class Diagrams for Specific Classes
|
||||
''''''''''''''''''''''''''''''''''''''''''''
|
||||
|
||||
In many cases creating a single diagram depicting all classes in the project yields a rather unwieldy, giant diagram.
|
||||
While limiting the input path to a single package or module can already help greatly to narrow down the scope, the ``-c`` option
|
||||
provides another way to create a class diagram focusing on a single class and its collaborators.
|
||||
For example, running::
|
||||
|
||||
pyreverse -ASmy -c pylint.checkers.classes.ClassChecker pylint
|
||||
|
||||
will generate the full class and package diagrams for ``pylint``, but will additionally generate a file ``pylint.checkers.classes.ClassChecker.dot``:
|
||||
|
||||
.. image:: ../../media/ClassChecker_diagram.png
|
||||
:width: 757
|
||||
:height: 1452
|
||||
:alt: Package diagram generated by pyreverse
|
||||
:align: center
|
||||
@ -0,0 +1,37 @@
|
||||
.. _symilar:
|
||||
|
||||
Symilar
|
||||
-------
|
||||
|
||||
The console script ``symilar`` finds copy pasted block of text in a set of files. It provides a command line interface to check only the ``duplicate-code`` message.
|
||||
|
||||
It can be invoked with::
|
||||
|
||||
symilar [-d|--duplicates min_duplicated_lines] [-i|--ignore-comments] [--ignore-docstrings] [--ignore-imports] [--ignore-signatures] file1...
|
||||
|
||||
All files that shall be checked have to be passed in explicitly, e.g.::
|
||||
|
||||
symilar foo.py, bar.py, subpackage/spam.py, subpackage/eggs.py
|
||||
|
||||
``symilar`` produces output like the following::
|
||||
|
||||
17 similar lines in 2 files
|
||||
==tests/data/clientmodule_test.py:3
|
||||
==tests/data/suppliermodule_test.py:12
|
||||
class Ancestor:
|
||||
""" Ancestor method """
|
||||
cls_member = DoNothing()
|
||||
|
||||
def __init__(self, value):
|
||||
local_variable = 0
|
||||
self.attr = 'this method shouldn\'t have a docstring'
|
||||
self.__value = value
|
||||
|
||||
def get_value(self):
|
||||
""" nice docstring ;-) """
|
||||
return self.__value
|
||||
|
||||
def set_value(self, value):
|
||||
self.__value = value
|
||||
return 'this method shouldn\'t have a docstring'
|
||||
TOTAL lines=58 duplicates=17 percent=29.31
|
||||
@ -0,0 +1,310 @@
|
||||
# Licensed under the GPL: https://www.gnu.org/licenses/old-licenses/gpl-2.0.html
|
||||
# For details: https://github.com/pylint-dev/pylint/blob/main/LICENSE
|
||||
# Copyright (c) https://github.com/pylint-dev/pylint/blob/main/CONTRIBUTORS.txt
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
import os
|
||||
import sys
|
||||
from datetime import datetime
|
||||
|
||||
# Pylint documentation build configuration file, created by
|
||||
# sphinx-quickstart on Thu Apr 4 20:31:25 2013.
|
||||
#
|
||||
# This file is execfile()d with the current directory set to its containing dir.
|
||||
#
|
||||
# Note that not all possible configuration values are present in this
|
||||
# autogenerated file.
|
||||
#
|
||||
# All configuration values have a default; values that are commented out
|
||||
# serve to show the default.
|
||||
|
||||
|
||||
# If extensions (or modules to document with autodoc) are in another directory,
|
||||
# add these directories to sys.path here. If the directory is relative to the
|
||||
# documentation root, use 'os.path.abspath' to make it absolute, like shown here.
|
||||
sys.path.append(os.path.abspath("exts"))
|
||||
sys.path.append(os.path.abspath(".."))
|
||||
|
||||
# pylint: disable=wrong-import-position
|
||||
from pylint import __version__
|
||||
from pylint.__pkginfo__ import numversion
|
||||
|
||||
# pylint: enable=wrong-import-position
|
||||
|
||||
# -- General configuration -----------------------------------------------------
|
||||
|
||||
# If your documentation needs a minimal Sphinx version, state it here.
|
||||
# needs_sphinx = '1.0'
|
||||
|
||||
# Add any Sphinx extension module names here, as strings. They can be extensions
|
||||
# coming with Sphinx (named 'sphinx.ext.*') or your custom ones.
|
||||
extensions = [
|
||||
"pylint_features",
|
||||
"pylint_extensions",
|
||||
"pylint_messages",
|
||||
"pylint_options",
|
||||
"pyreverse_configuration",
|
||||
"sphinx.ext.autosectionlabel",
|
||||
"sphinx.ext.intersphinx",
|
||||
"sphinx_reredirects",
|
||||
]
|
||||
|
||||
|
||||
# Single file redirects are handled in this file and can be done by a pylint
|
||||
# contributor. We use the following extension:
|
||||
# https://documatt.gitlab.io/sphinx-reredirects/usage.html
|
||||
# Directory redirects are handled in ReadTheDoc admin interface and can only be done
|
||||
# by pylint maintainers at the following URL:
|
||||
# https://readthedocs.org/dashboard/pylint/redirects/
|
||||
redirects: dict[str, str] = {
|
||||
# "<source>": "<target>"
|
||||
"additional_commands/index": "../index.html",
|
||||
"development_guide/index": "api/index.html",
|
||||
"development_guide/contribute": "../development_guide/contributor_guide/index.html",
|
||||
"development_guide/contributor_guide": "contributor_guide/index.html",
|
||||
"development_guide/profiling": "../development_guide/contributor_guide/profiling.html",
|
||||
"development_guide/tests/index": "../contributor_guide/tests/index.html",
|
||||
"development_guide/tests/install": "../contributor_guide/tests/install.html",
|
||||
"development_guide/tests/launching_test": "../contributor_guide/tests/launching_test.html",
|
||||
# There was a typo in the original file, don't fix.
|
||||
"development_guide/tests/writting_test": "../contributor_guide/tests/writing_test.html",
|
||||
"development/testing": "tests/index.html",
|
||||
"how_tos/custom_checkers": "../development_guide/how_tos/custom_checkers.html",
|
||||
"how_tos/index": "../development_guide/how_tos/index.html",
|
||||
"how_tos/plugins": "../development_guide/how_tos/plugins.html",
|
||||
"how_tos/transform_plugins": "../development_guide/how_tos/transform_plugins.html",
|
||||
"intro": "index.html",
|
||||
"messages/messages_introduction": "../user_guide/messages/index.html",
|
||||
"messages/messages_list": "../user_guide/messages/messages_overview.html",
|
||||
"support": "contact.html",
|
||||
"technical_reference/c_extensions": "../user_guide/messages/error/no-member.html",
|
||||
"technical_reference/extensions": "../user_guide/checkers/extensions.html",
|
||||
"technical_reference/checkers": "../development_guide/technical_reference/checkers.html",
|
||||
"technical_reference/features": "../user_guide/checkers/features.html",
|
||||
"technical_reference/index": "../development_guide/technical_reference/index.html",
|
||||
"technical_reference/startup": "../development_guide/technical_reference/startup.html",
|
||||
"user_guide/configuration/naming-styles": "../user_guide/messages/convention/invalid-name.html",
|
||||
"user_guide/ide_integration/flymake-emacs": "../installation/ide_integration/flymake-emacs.html",
|
||||
"user_guide/ide_integration/ide-integration": "../installation/ide_integration/index.html",
|
||||
"user_guide/ide-integration": "installation.html",
|
||||
"user_guide/ide_integration/textmate": "../installation/ide_integration/textmate.html",
|
||||
"user_guide/index": "installation/index.html",
|
||||
"user_guide/message-control": "messages/message_control.html",
|
||||
"user_guide/options": "configuration/all-options.html",
|
||||
"user_guide/output": "usage/output.html",
|
||||
"user_guide/pre-commit-integration": "installation/pre-commit-integration.html",
|
||||
"user_guide/run": "usage/run.html",
|
||||
"pyreverse": "additional_tools/pyreverse/index.html",
|
||||
"symilar": "additional_tools/symilar/index.html",
|
||||
}
|
||||
|
||||
|
||||
# Add any paths that contain templates here, relative to this directory.
|
||||
templates_path = ["_templates"]
|
||||
|
||||
# The suffix of source filenames.
|
||||
source_suffix = ".rst"
|
||||
|
||||
# The encoding of source files.
|
||||
# source_encoding = 'utf-8-sig'
|
||||
|
||||
# The root toctree document.
|
||||
root_doc = "index"
|
||||
|
||||
# General information about the project.
|
||||
project = "Pylint"
|
||||
current_year = datetime.utcnow().year
|
||||
contributors = "Logilab and Pylint contributors"
|
||||
copyright = f"2003-{current_year}, {contributors}" # pylint: disable=redefined-builtin
|
||||
|
||||
# The version info for the project you're documenting, acts as replacement for
|
||||
# |version| and |release|, also used in various other places throughout the
|
||||
# built documents.
|
||||
# The short X.Y version.
|
||||
version = f"{numversion[0]}.{numversion[1]}"
|
||||
# The full version, including alpha/beta/rc tags.
|
||||
release = __version__
|
||||
|
||||
# The language for content autogenerated by Sphinx. Refer to documentation
|
||||
# for a list of supported languages.
|
||||
# language = None
|
||||
|
||||
# There are two options for replacing |today|: either, you set today to some
|
||||
# non-false value, then it is used:
|
||||
# today = ''
|
||||
# Else, today_fmt is used as the format for a strftime call.
|
||||
# today_fmt = '%B %d, %Y'
|
||||
|
||||
# List of patterns, relative to source directory, that match files and
|
||||
# directories to ignore when looking for source files.
|
||||
exclude_patterns = ["_build", "data/**", "whatsnew/fragments"]
|
||||
|
||||
# The reST default role (used for this markup: `text`) to use for all documents.
|
||||
# default_role = None
|
||||
|
||||
# If true, '()' will be appended to :func: etc. cross-reference text.
|
||||
# add_function_parentheses = True
|
||||
|
||||
# If true, the current module name will be prepended to all description
|
||||
# unit titles (such as .. function::).
|
||||
# add_module_names = True
|
||||
|
||||
# If true, sectionauthor and moduleauthor directives will be shown in the
|
||||
# output. They are ignored by default.
|
||||
# show_authors = False
|
||||
|
||||
# The name of the Pygments (syntax highlighting) style to use.
|
||||
pygments_style = "sphinx"
|
||||
|
||||
# A list of ignored prefixes for module index sorting.
|
||||
# modindex_common_prefix = []
|
||||
|
||||
|
||||
# -- Options for HTML output ---------------------------------------------------
|
||||
|
||||
# The theme to use for HTML and HTML Help pages. See the documentation for
|
||||
# a list of builtin themes.
|
||||
html_theme = "furo"
|
||||
|
||||
# Theme options are theme-specific and customize the look and feel of a theme
|
||||
# further. For a list of options available for each theme, see the
|
||||
# documentation.
|
||||
# Currently we use the default Furo configuration
|
||||
# html_theme_options = {}
|
||||
|
||||
# Add any paths that contain custom themes here, relative to this directory.
|
||||
# html_theme_path = []
|
||||
|
||||
# The name for this set of Sphinx documents. If None, it defaults to
|
||||
# "<project> v<release> documentation".
|
||||
# html_title = None
|
||||
|
||||
# A shorter title for the navigation bar. Default is the same as html_title.
|
||||
# html_short_title = None
|
||||
|
||||
# The name of an image file (relative to this directory) to place at the top
|
||||
# of the sidebar.
|
||||
# html_logo = None
|
||||
|
||||
# The name of an image file (within the static path) to use as favicon of the
|
||||
# docs. This file should be a Windows icon file (.ico) being 16x16 or 32x32
|
||||
# pixels large.
|
||||
# html_favicon = None
|
||||
|
||||
# Add any paths that contain custom static files (such as style sheets) here,
|
||||
# relative to this directory. They are copied after the builtin static files,
|
||||
# so a file named "default.css" will overwrite the builtin "default.css".
|
||||
# html_static_path = ['_static']
|
||||
|
||||
# If not '', a 'Last updated on:' timestamp is inserted at every page bottom,
|
||||
# using the given strftime format.
|
||||
html_last_updated_fmt = "%b %d, %Y"
|
||||
|
||||
smartquotes = False
|
||||
|
||||
# Custom sidebar templates, maps document names to template names.
|
||||
# Currently we use the default Furo Sidebar
|
||||
# html_sidebars = {}
|
||||
|
||||
# Additional templates that should be rendered to pages, maps page names to
|
||||
# template names.
|
||||
# html_additional_pages = {}
|
||||
|
||||
# If false, no module index is generated.
|
||||
# html_domain_indices = True
|
||||
|
||||
# If false, no index is generated.
|
||||
# html_use_index = True
|
||||
|
||||
# If true, the index is split into individual pages for each letter.
|
||||
# html_split_index = False
|
||||
|
||||
# If true, links to the reST sources are added to the pages.
|
||||
html_show_sourcelink = True
|
||||
|
||||
# If true, "Created using Sphinx" is shown in the HTML footer. Default is True.
|
||||
# html_show_sphinx = True
|
||||
|
||||
# If true, "(C) Copyright ..." is shown in the HTML footer. Default is True.
|
||||
# html_show_copyright = True
|
||||
|
||||
# If true, an OpenSearch description file will be output, and all pages will
|
||||
# contain a <link> tag referring to it. The value of this option must be the
|
||||
# base URL from which the finished HTML is served.
|
||||
# html_use_opensearch = ''
|
||||
|
||||
# This is the file name suffix for HTML files (e.g. ".xhtml").
|
||||
# html_file_suffix = None
|
||||
|
||||
# Output file base name for HTML help builder.
|
||||
htmlhelp_basename = "Pylintdoc"
|
||||
|
||||
|
||||
# -- Options for LaTeX output --------------------------------------------------
|
||||
|
||||
# The paper size ('letter' or 'a4').
|
||||
# latex_paper_size = 'letter'
|
||||
|
||||
# The font size ('10pt', '11pt' or '12pt').
|
||||
# latex_font_size = '10pt'
|
||||
|
||||
# Grouping the document tree into LaTeX files. List of tuples
|
||||
# (source start file, target name, title, author, documentclass [howto/manual]).
|
||||
latex_documents = [
|
||||
(
|
||||
"index",
|
||||
"Pylint.tex",
|
||||
"Pylint Documentation",
|
||||
contributors,
|
||||
"manual",
|
||||
)
|
||||
]
|
||||
|
||||
# The name of an image file (relative to this directory) to place at the top of
|
||||
# the title page.
|
||||
# latex_logo = None
|
||||
|
||||
# For "manual" documents, if this is true, then toplevel headings are parts,
|
||||
# not chapters.
|
||||
# latex_use_parts = False
|
||||
|
||||
# If true, show page references after internal links.
|
||||
# latex_show_pagerefs = False
|
||||
|
||||
# If true, show URL addresses after external links.
|
||||
# latex_show_urls = False
|
||||
|
||||
# Additional stuff for the LaTeX preamble.
|
||||
# latex_preamble = ''
|
||||
|
||||
# Documents to append as an appendix to all manuals.
|
||||
# latex_appendices = []
|
||||
|
||||
# If false, no module index is generated.
|
||||
# latex_domain_indices = True
|
||||
|
||||
|
||||
# -- Options for manual page output --------------------------------------------
|
||||
|
||||
# One entry per manual page. List of tuples
|
||||
# (source start file, name, description, authors, manual section).
|
||||
man_pages = [("index", "pylint", "Pylint Documentation", [contributors], 1)]
|
||||
|
||||
# pylint: disable-next=consider-using-namedtuple-or-dataclass
|
||||
intersphinx_mapping = {
|
||||
"astroid": ("https://pylint.readthedocs.io/projects/astroid/en/latest/", None),
|
||||
"python": ("https://docs.python.org/3", None),
|
||||
}
|
||||
|
||||
# Prevent label issues due to colliding section names
|
||||
# through including multiple documents
|
||||
autosectionlabel_prefix_document = True
|
||||
|
||||
# Permit duplicated titles in the resulting document.
|
||||
# See https://github.com/pylint-dev/pylint/issues/7362#issuecomment-1256932866
|
||||
autosectionlabel_maxdepth = 2
|
||||
|
||||
linkcheck_ignore = [
|
||||
"https://github.com/pylint-dev/pylint/blob/main/pylint/extensions/.*"
|
||||
]
|
||||
@ -0,0 +1,58 @@
|
||||
Contact
|
||||
=======
|
||||
|
||||
Bug reports, feedback
|
||||
---------------------
|
||||
.. _bug reports, feedback:
|
||||
|
||||
You think you have found a bug in Pylint? Well, this may be the case
|
||||
since Pylint and Python are under heavy development!
|
||||
|
||||
Please take the time to check if it is already in the issue tracker at
|
||||
https://github.com/pylint-dev/pylint
|
||||
|
||||
Note that the issue might also be reported in one of Pylint's major dependencies,
|
||||
astroid:
|
||||
|
||||
* https://github.com/pylint-dev/astroid
|
||||
|
||||
Discord server
|
||||
--------------
|
||||
|
||||
You can discuss your problem using the discord server:
|
||||
|
||||
https://discord.com/invite/Egy6P8AMB5
|
||||
|
||||
Mailing lists
|
||||
-------------
|
||||
|
||||
.. _Mailing lists:
|
||||
|
||||
The code-quality mailing list is shared with other tools that aim
|
||||
at improving the quality of python code.
|
||||
|
||||
You can subscribe to this mailing list at
|
||||
https://mail.python.org/mailman3/lists/code-quality.python.org/
|
||||
|
||||
Archives are available at
|
||||
https://mail.python.org/pipermail/code-quality/
|
||||
|
||||
Archives before April 2013 are not available anymore. At
|
||||
https://mail.python.org/pipermail/ it was under ``python-projects``.
|
||||
|
||||
Support
|
||||
-------
|
||||
|
||||
.. image:: media/Tidelift_Logos_RGB_Tidelift_Shorthand_On-White.png
|
||||
:height: 150
|
||||
:alt: Tidelift
|
||||
:align: left
|
||||
:class: tideliftlogo
|
||||
|
||||
Professional support for pylint is available as part of the `Tidelift
|
||||
Subscription`_. Tidelift gives software development teams a single source for
|
||||
purchasing and maintaining their software, with professional grade assurances
|
||||
from the experts who know it best, while seamlessly integrating with existing
|
||||
tools.
|
||||
|
||||
.. _Tidelift Subscription: https://tidelift.com/subscription/pkg/pypi-pylint?utm_source=pypi-pylint&utm_medium=referral&utm_campaign=readme
|
||||
@ -0,0 +1,10 @@
|
||||
import abc
|
||||
|
||||
|
||||
class Animal(abc.ABC):
|
||||
@abc.abstractmethod
|
||||
def make_sound(self):
|
||||
pass
|
||||
|
||||
|
||||
sheep = Animal() # [abstract-class-instantiated]
|
||||
@ -0,0 +1,15 @@
|
||||
import abc
|
||||
|
||||
|
||||
class Animal(abc.ABC):
|
||||
@abc.abstractmethod
|
||||
def make_sound(self):
|
||||
pass
|
||||
|
||||
|
||||
class Sheep(Animal):
|
||||
def make_sound(self):
|
||||
print("bhaaaaa")
|
||||
|
||||
|
||||
sheep = Sheep()
|
||||
@ -0,0 +1,11 @@
|
||||
import abc
|
||||
|
||||
|
||||
class WildAnimal:
|
||||
@abc.abstractmethod
|
||||
def make_sound(self):
|
||||
pass
|
||||
|
||||
|
||||
class Panther(WildAnimal): # [abstract-method]
|
||||
pass
|
||||
@ -0,0 +1,7 @@
|
||||
class Pet:
|
||||
def make_sound(self):
|
||||
raise NotImplementedError
|
||||
|
||||
|
||||
class Cat(Pet): # [abstract-method]
|
||||
pass
|
||||
@ -0,0 +1,12 @@
|
||||
import abc
|
||||
|
||||
|
||||
class WildAnimal:
|
||||
@abc.abstractmethod
|
||||
def make_sound(self):
|
||||
pass
|
||||
|
||||
|
||||
class Panther(WildAnimal):
|
||||
def make_sound(self):
|
||||
print("MEEEOW")
|
||||
@ -0,0 +1,8 @@
|
||||
class Pet:
|
||||
def make_sound(self):
|
||||
raise NotImplementedError
|
||||
|
||||
|
||||
class Cat(Pet):
|
||||
def make_sound(self):
|
||||
print("Meeeow")
|
||||
@ -0,0 +1,5 @@
|
||||
class Unicorn:
|
||||
def __init__(self, fluffiness_level):
|
||||
if self.fluffiness_level > 9000: # [access-member-before-definition]
|
||||
print("It's OVER-FLUFFYYYY ! *crush glasses*")
|
||||
self.fluffiness_level = fluffiness_level
|
||||
@ -0,0 +1,5 @@
|
||||
class Unicorn:
|
||||
def __init__(self, fluffiness_level):
|
||||
self.fluffiness_level = fluffiness_level
|
||||
if self.fluffiness_level > 9000:
|
||||
print("It's OVER-FLUFFYYYY ! *crush glasses*")
|
||||
@ -0,0 +1 @@
|
||||
string = "\z" # [syntax-error]
|
||||
@ -0,0 +1,6 @@
|
||||
``\z`` is same as ``\\z`` because there's no escape sequence for ``z``. But it is not clear
|
||||
for the reader of the code.
|
||||
|
||||
The only reason this is demonstrated to raise ``syntax-error`` is because
|
||||
pylint's CI now runs on Python 3.12, where this truly raises a ``SyntaxError``.
|
||||
We hope to address this discrepancy in the documentation in the future.
|
||||
@ -0,0 +1 @@
|
||||
string = "\\z"
|
||||
@ -0,0 +1 @@
|
||||
string = "\t"
|
||||
@ -0,0 +1 @@
|
||||
string = r"\z"
|
||||
@ -0,0 +1,2 @@
|
||||
- `String and Bytes literals <https://docs.python.org/3/reference/lexical_analysis.html#string-and-bytes-literals>`_
|
||||
- `Long form stackoverflow explanation <https://stackoverflow.com/a/19030982/2519059>`_
|
||||
@ -0,0 +1 @@
|
||||
print(b"\u%b" % b"0394") # [syntax-error]
|
||||
@ -0,0 +1 @@
|
||||
print(b"\\u%b" % b"0394")
|
||||
@ -0,0 +1,8 @@
|
||||
class Drink:
|
||||
def mix(self, fluid_one, fluid_two):
|
||||
return fluid_one + fluid_two
|
||||
|
||||
|
||||
class Cocktail(Drink):
|
||||
def mix(self, fluid_one, fluid_two, alcoholic_fluid): # [arguments-differ]
|
||||
return fluid_one + fluid_two + alcoholic_fluid
|
||||
@ -0,0 +1,9 @@
|
||||
``argument-differ`` denotes an issue with the Liskov Substitution Principle.
|
||||
This means that the code in question violates an important design principle which does not have
|
||||
one single solution. We recommend to search online for the best solution in your case.
|
||||
|
||||
To give some examples of potential solutions:
|
||||
|
||||
* Add the argument to the parent class
|
||||
* Remove the inheritance completely
|
||||
* Add default arguments to the child class
|
||||
@ -0,0 +1,20 @@
|
||||
"""
|
||||
Here we assume that drink and cocktail are the same thing and should actually
|
||||
inherit from each over. We also assume that 'Drink' are 'Cocktail' without
|
||||
alcohol (we added the alcohol option in the base class).
|
||||
|
||||
This permit to not have to modify the cocktails calls downstream but the case where
|
||||
an alcohol is mixed in a soft drink will need to be handled.
|
||||
"""
|
||||
|
||||
|
||||
class Drink:
|
||||
def mix(self, fluid_one, fluid_two, alcoholic_fluid=None):
|
||||
# if alcoholic_fluid is not None:
|
||||
# raise Exception(f"This soft drink has {alcoholic_fluid} in it !")
|
||||
return fluid_one + fluid_two
|
||||
|
||||
|
||||
class Cocktail(Drink):
|
||||
def mix(self, fluid_one, fluid_two, alcoholic_fluid):
|
||||
return fluid_one + fluid_two + alcoholic_fluid
|
||||
@ -0,0 +1,18 @@
|
||||
"""
|
||||
Here we assume that drink and cocktail are the same thing and should actually
|
||||
inherit from each over. We also assume that any Cocktail can be treated like
|
||||
a Drink (if you add beer to it).
|
||||
|
||||
This permit to not have to modify the calls downstream and causes the least
|
||||
amount of disturbance at the cost of making cocktails beer-based implicitly.
|
||||
"""
|
||||
|
||||
|
||||
class Drink:
|
||||
def mix(self, fluid_one, fluid_two):
|
||||
return fluid_one + fluid_two
|
||||
|
||||
|
||||
class Cocktail(Drink):
|
||||
def mix(self, fluid_one, fluid_two, alcoholic_fluid="Beer"):
|
||||
return fluid_one + fluid_two + alcoholic_fluid
|
||||
@ -0,0 +1,19 @@
|
||||
"""
|
||||
Here we assume that 'Drink' and 'Cocktail' are different things and should
|
||||
not be treated together like if they were the same thing.
|
||||
|
||||
This will force some downstream changes and force the API user to make a
|
||||
conscious decision about the alcoholic content of its drink when using the
|
||||
API. For example, it's impossible to create a mojito with beer without
|
||||
explicitly wanting to, or to add an alcohol to a soft-drink.
|
||||
"""
|
||||
|
||||
|
||||
class Drink:
|
||||
def mix(self, fluid_one, fluid_two):
|
||||
return fluid_one + fluid_two
|
||||
|
||||
|
||||
class Cocktail:
|
||||
def mix(self, fluid_one, fluid_two, alcoholic_fluid):
|
||||
return fluid_one + fluid_two + alcoholic_fluid
|
||||
@ -0,0 +1 @@
|
||||
- `Liskov Substitution Principle <https://en.wikipedia.org/wiki/Liskov_substitution_principle>`_
|
||||
@ -0,0 +1,13 @@
|
||||
def function_3_args(first_argument, second_argument, third_argument):
|
||||
"""Three arguments function"""
|
||||
return first_argument, second_argument, third_argument
|
||||
|
||||
|
||||
def args_out_of_order():
|
||||
first_argument = 1
|
||||
second_argument = 2
|
||||
third_argument = 3
|
||||
|
||||
function_3_args( # [arguments-out-of-order]
|
||||
first_argument, third_argument, second_argument
|
||||
)
|
||||
@ -0,0 +1,11 @@
|
||||
def function_3_args(first_argument, second_argument, third_argument):
|
||||
"""Three arguments function"""
|
||||
return first_argument, second_argument, third_argument
|
||||
|
||||
|
||||
def args_out_of_order():
|
||||
first_argument = 1
|
||||
second_argument = 2
|
||||
third_argument = 3
|
||||
|
||||
function_3_args(first_argument, second_argument, third_argument)
|
||||
@ -0,0 +1,15 @@
|
||||
class Fruit:
|
||||
def brew(self, ingredient_name: str):
|
||||
print(f"Brewing a {type(self)} with {ingredient_name}")
|
||||
|
||||
|
||||
class Apple(Fruit): ...
|
||||
|
||||
|
||||
class Orange(Fruit):
|
||||
def brew(self, flavor: str): # [arguments-renamed]
|
||||
print(f"Brewing an orange with {flavor}")
|
||||
|
||||
|
||||
for fruit, ingredient_name in [[Orange(), "thyme"], [Apple(), "cinnamon"]]:
|
||||
fruit.brew(ingredient_name=ingredient_name)
|
||||
@ -0,0 +1,15 @@
|
||||
class Fruit:
|
||||
def brew(self, ingredient_name: str):
|
||||
print(f"Brewing a {type(self)} with {ingredient_name}")
|
||||
|
||||
|
||||
class Apple(Fruit): ...
|
||||
|
||||
|
||||
class Orange(Fruit):
|
||||
def brew(self, ingredient_name: str):
|
||||
print(f"Brewing an orange with {ingredient_name}")
|
||||
|
||||
|
||||
for fruit, ingredient_name in [[Orange(), "thyme"], [Apple(), "cinnamon"]]:
|
||||
fruit.brew(ingredient_name=ingredient_name)
|
||||
@ -0,0 +1,3 @@
|
||||
def test_division():
|
||||
a = 9 / 3
|
||||
assert "No ZeroDivisionError were raised" # [assert-on-string-literal]
|
||||
@ -0,0 +1,4 @@
|
||||
Directly asserting a string literal will always pass. The solution is to
|
||||
test something that could fail, or not assert at all.
|
||||
|
||||
For ``unittest`` assertions there is the similar :ref:`redundant-unittest-assert` message.
|
||||
@ -0,0 +1,3 @@
|
||||
def test_division():
|
||||
a = 9 / 3
|
||||
assert a == 3
|
||||
@ -0,0 +1,3 @@
|
||||
- `Tests without assertion <https://stackoverflow.com/a/137418/2519059>`_
|
||||
- `Testing that there is no error raised <https://stackoverflow.com/questions/20274987>`_
|
||||
- `Parametrizing conditional raising <https://docs.pytest.org/en/latest/example/parametrize.html#parametrizing-conditional-raising>`_
|
||||
@ -0,0 +1 @@
|
||||
assert (1, None) # [assert-on-tuple]
|
||||
@ -0,0 +1,4 @@
|
||||
Directly asserting a non-empty tuple will always pass. The solution is to
|
||||
test something that could fail, or not assert at all.
|
||||
|
||||
For ``unittest`` assertions there is the similar :ref:`redundant-unittest-assert` message.
|
||||
@ -0,0 +1,3 @@
|
||||
x, y = (1, None)
|
||||
assert x
|
||||
assert y
|
||||
@ -0,0 +1,10 @@
|
||||
class Student:
|
||||
__slots__ = ("name",)
|
||||
|
||||
def __init__(self, name, surname):
|
||||
self.name = name
|
||||
self.surname = surname # [assigning-non-slot]
|
||||
self.setup()
|
||||
|
||||
def setup(self):
|
||||
pass
|
||||
@ -0,0 +1,10 @@
|
||||
class Student:
|
||||
__slots__ = ("name", "surname")
|
||||
|
||||
def __init__(self, name, surname):
|
||||
self.name = name
|
||||
self.surname = surname
|
||||
self.setup()
|
||||
|
||||
def setup(self):
|
||||
pass
|
||||
@ -0,0 +1,5 @@
|
||||
def add(x, y):
|
||||
print(x + y)
|
||||
|
||||
|
||||
value = add(10, 10) # [assignment-from-no-return]
|
||||
@ -0,0 +1,5 @@
|
||||
def add(x, y):
|
||||
return x + y
|
||||
|
||||
|
||||
value = add(10, 10)
|
||||
@ -0,0 +1,5 @@
|
||||
def function():
|
||||
return None
|
||||
|
||||
|
||||
f = function() # [assignment-from-none]
|
||||
@ -0,0 +1,5 @@
|
||||
def function():
|
||||
return None
|
||||
|
||||
|
||||
f = function() if function() else 1
|
||||
@ -0,0 +1,2 @@
|
||||
This is a message linked to an internal problem in pylint. There's nothing to change in your code,
|
||||
but maybe in pylint's configuration or installation.
|
||||
@ -0,0 +1,10 @@
|
||||
from contextlib import asynccontextmanager
|
||||
|
||||
|
||||
@asynccontextmanager
|
||||
async def async_context():
|
||||
yield
|
||||
|
||||
|
||||
with async_context(): # [async-context-manager-with-regular-with]
|
||||
print("This will cause an error at runtime")
|
||||
@ -0,0 +1,12 @@
|
||||
import asyncio
|
||||
from contextlib import asynccontextmanager
|
||||
|
||||
|
||||
@asynccontextmanager
|
||||
async def async_context():
|
||||
yield
|
||||
|
||||
|
||||
async def main():
|
||||
async with async_context():
|
||||
print("This works correctly")
|
||||
@ -0,0 +1,2 @@
|
||||
- `PEP 492 - Coroutines with async and await syntax <https://peps.python.org/pep-0492/>`_
|
||||
- `contextlib.asynccontextmanager <https://docs.python.org/3/library/contextlib.html#contextlib.asynccontextmanager>`_
|
||||
@ -0,0 +1,3 @@
|
||||
class Student:
|
||||
def register(self):
|
||||
self.is_registered = True # [attribute-defined-outside-init]
|
||||
@ -0,0 +1,6 @@
|
||||
class Student:
|
||||
def __init__(self):
|
||||
self.is_registered = False
|
||||
|
||||
def register(self):
|
||||
self.is_registered = True
|
||||
@ -0,0 +1,5 @@
|
||||
import asyncio
|
||||
|
||||
|
||||
def main():
|
||||
await asyncio.sleep(1) # [await-outside-async]
|
||||
@ -0,0 +1,5 @@
|
||||
import asyncio
|
||||
|
||||
|
||||
async def main():
|
||||
await asyncio.sleep(1)
|
||||
@ -0,0 +1 @@
|
||||
- `PEP 492 <https://peps.python.org/pep-0492/#await-expression>`_
|
||||
@ -0,0 +1,2 @@
|
||||
numbers = list(map(lambda x: 2 * x, [1, 2, 3])) # [bad-builtin]
|
||||
print(numbers)
|
||||
@ -0,0 +1,2 @@
|
||||
numbers = [2 * x for x in [1, 2, 3]]
|
||||
print(numbers)
|
||||
@ -0,0 +1,2 @@
|
||||
[MAIN]
|
||||
load-plugins = pylint.extensions.bad_builtin
|
||||
@ -0,0 +1,7 @@
|
||||
shop = {
|
||||
# animal: (specie, descriptions)
|
||||
"parrot": ("Norvegian blue", ("restin'", "remarkable", "beautiful plumage")),
|
||||
}
|
||||
|
||||
if "parrot" in shop is "restin'": # [bad-chained-comparison]
|
||||
print("Hellooooo, Pooolllllyyy ! WAAAAKEEY, WAKKEEEY !")
|
||||
@ -0,0 +1,5 @@
|
||||
def xor_check(*, left=None, right=None):
|
||||
if left is None != right is None: # [bad-chained-comparison]
|
||||
raise ValueError(
|
||||
"Either both left= and right= need to be provided or none should."
|
||||
)
|
||||
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in new issue