Add mypy plugin support to stubtest configuration (#13948)

This commit is contained in:
Huy Nguyen
2025-05-11 19:45:30 +07:00
committed by GitHub
parent 0933303ff0
commit a8fa1ab0d9
6 changed files with 61 additions and 5 deletions
+17
View File
@@ -196,6 +196,23 @@ that stubtest reports to be missing should necessarily be added to the stub.
For some implementation details, it is often better to add allowlist entries
for missing objects rather than trying to match the runtime in every detail.
### Support for mypy plugins in stubtest
For stubs that require mypy plugins to check correctly (such as Django), stubtest
supports configuring mypy plugins through the METADATA.toml file. This allows stubtest to
leverage type information provided by these plugins when validating stubs.
To use this feature, add the following configuration to the `tool.stubtest` section in your METADATA.toml:
```toml
mypy_plugins = ["mypy_django_plugin.main"]
mypy_plugins_config = { "django-stubs" = { "django_settings_module" = "@tests.django_settings" } }
```
For Django stubs specifically, you'll need to create a `django_settings.py` file in your `@tests` directory
that contains the Django settings required by the plugin. This file will be referenced by the plugin
configuration to properly validate Django-specific types during stubtest execution.
## typecheck\_typeshed.py
Run using
+7 -1
View File
@@ -27,6 +27,10 @@ extension_descriptions = {".pyi": "stub", ".py": ".py"}
# consistent CI runs.
linters = {"mypy", "pyright", "pytype", "ruff"}
ALLOWED_PY_FILES_IN_TESTS_DIR = {
"django_settings.py" # This file contains Django settings used by the mypy_django_plugin during stubtest execution.
}
def assert_consistent_filetypes(
directory: Path, *, kind: str, allowed: set[str], allow_nonidentifier_filenames: bool = False
@@ -81,7 +85,9 @@ def check_stubs() -> None:
def check_tests_dir(tests_dir: Path) -> None:
py_files_present = any(file.suffix == ".py" for file in tests_dir.iterdir())
py_files_present = any(
file.suffix == ".py" and file.name not in ALLOWED_PY_FILES_IN_TESTS_DIR for file in tests_dir.iterdir()
)
error_message = f"Test-case files must be in an `{TESTS_DIR}/{TEST_CASES_DIR}` directory, not in the `{TESTS_DIR}` directory"
assert not py_files_present, error_message
+1 -1
View File
@@ -97,7 +97,7 @@ def run_stubtest(
return False
mypy_configuration = mypy_configuration_from_distribution(dist_name)
with temporary_mypy_config_file(mypy_configuration) as temp:
with temporary_mypy_config_file(mypy_configuration, stubtest_settings) as temp:
ignore_missing_stub = ["--ignore-missing-stub"] if stubtest_settings.ignore_missing_stub else []
packages_to_check = [d.name for d in dist.iterdir() if d.is_dir() and d.name.isidentifier()]
modules_to_check = [d.stem for d in dist.iterdir() if d.is_file() and d.suffix == ".pyi"]