Skip to content

Remove Python 3.8 & Django 5.0 #1202

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 9 commits into from
May 26, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 5 additions & 9 deletions .github/workflows/main.yml
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,11 @@ jobs:
python: '3.13'
allow_failure: false

# Explicitly test min pytest.
- name: py313-dj52-sqlite-pytestmin-coverage
python: '3.13'
allow_failure: false

- name: py313-dj52-postgres-xdist-coverage
python: '3.13'
allow_failure: false
Expand Down Expand Up @@ -131,15 +136,6 @@ jobs:
python: '3.11'
allow_failure: false

- name: py38-dj42-sqlite-xdist-coverage
python: '3.8'
allow_failure: false

# Explicitly test min pytest.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should keep one job testing the pytestmin. Best to just bump this one to py39.

- name: py38-dj42-sqlite-pytestmin-coverage
python: '3.8'
allow_failure: false

# pypy3: not included with coverage reports (much slower then).
- name: pypy3-dj42-postgres
python: 'pypy3.9'
Expand Down
4 changes: 2 additions & 2 deletions README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,9 @@ pytest-django allows you to test your Django project/applications with the
<https://pytest-django.readthedocs.io/en/latest/contributing.html>`_
* Version compatibility:

* Django: 4.2, 5.0, 5.1, 5.2 and latest main branch (compatible at the time
* Django: 4.2, 5.1, 5.2 and latest main branch (compatible at the time
of each release)
* Python: CPython>=3.8 or PyPy 3
* Python: CPython>=3.9 or PyPy 3
* pytest: >=7.0

For compatibility with older versions, use previous pytest-django releases.
Expand Down
6 changes: 3 additions & 3 deletions docs/contributing.rst
Original file line number Diff line number Diff line change
Expand Up @@ -140,10 +140,10 @@ writing), running them all will take a long time. All valid configurations can
be found in `tox.ini`. To test against a few of them, invoke tox with the `-e`
flag::

$ tox -e py38-dj32-postgres,py310-dj41-mysql
$ tox -e py39-dj42-postgres,py310-dj52-mysql

This will run the tests on Python 3.8/Django 3.2/PostgeSQL and Python
3.10/Django 4.1/MySQL.
This will run the tests on Python 3.9/Django 4.2/PostgeSQL and Python
3.10/Django 5.2/MySQL.


Measuring test coverage
Expand Down
4 changes: 1 addition & 3 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ build-backend = "setuptools.build_meta"
name = "pytest-django"
description = "A Django plugin for pytest."
readme = "README.rst"
requires-python = ">=3.8"
requires-python = ">=3.9"
dynamic = ["version"]
authors = [
{ name = "Andreas Pelme", email = "andreas@pelme.se" },
Expand All @@ -22,14 +22,12 @@ classifiers = [
"Development Status :: 5 - Production/Stable",
"Framework :: Django",
"Framework :: Django :: 4.2",
"Framework :: Django :: 5.0",
"Framework :: Django :: 5.1",
"Framework :: Django :: 5.2",
"Intended Audience :: Developers",
"License :: OSI Approved :: BSD License",
"Operating System :: OS Independent",
"Programming Language :: Python",
"Programming Language :: Python :: 3.8",
"Programming Language :: Python :: 3.9",
"Programming Language :: Python :: 3.10",
"Programming Language :: Python :: 3.11",
Expand Down
3 changes: 2 additions & 1 deletion pytest_django/asserts.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,9 @@

from __future__ import annotations

from collections.abc import Sequence
from functools import wraps
from typing import TYPE_CHECKING, Any, Callable, Sequence
from typing import TYPE_CHECKING, Any, Callable

from django import VERSION
from django.test import LiveServerTestCase, SimpleTestCase, TestCase, TransactionTestCase
Expand Down
28 changes: 7 additions & 21 deletions pytest_django/fixtures.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,24 +3,10 @@
from __future__ import annotations

import os
from contextlib import contextmanager
from collections.abc import Generator, Iterable, Sequence
from contextlib import AbstractContextManager, contextmanager
from functools import partial
from typing import (
TYPE_CHECKING,
AbstractSet,
Any,
Callable,
ContextManager,
Generator,
Iterable,
List,
Literal,
Optional,
Protocol,
Sequence,
Tuple,
Union,
)
from typing import TYPE_CHECKING, Any, Callable, Literal, Optional, Protocol, Union

import pytest

Expand All @@ -37,9 +23,9 @@


_DjangoDbDatabases = Optional[Union[Literal["__all__"], Iterable[str]]]
_DjangoDbAvailableApps = Optional[List[str]]
_DjangoDbAvailableApps = Optional[list[str]]
# transaction, reset_sequences, databases, serialized_rollback, available_apps
_DjangoDb = Tuple[bool, bool, _DjangoDbDatabases, bool, _DjangoDbAvailableApps]
_DjangoDb = tuple[bool, bool, _DjangoDbDatabases, bool, _DjangoDbAvailableApps]


__all__ = [
Expand Down Expand Up @@ -157,7 +143,7 @@ def _get_databases_for_test(test: pytest.Item) -> tuple[Iterable[str], bool]:

def _get_databases_for_setup(
items: Sequence[pytest.Item],
) -> tuple[AbstractSet[str], AbstractSet[str]]:
) -> tuple[set[str], set[str]]:
"""Get the database aliases that need to be setup, and the subset that needs
to be serialized."""
# Code derived from django.test.utils.DiscoverRunner.get_databases().
Expand Down Expand Up @@ -736,7 +722,7 @@ def __call__(
*,
using: str = ...,
execute: bool = ...,
) -> ContextManager[list[Callable[[], Any]]]:
) -> AbstractContextManager[list[Callable[[], Any]]]:
pass # pragma: no cover


Expand Down
10 changes: 6 additions & 4 deletions pytest_django/plugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,10 @@
import pathlib
import sys
import types
from collections.abc import Generator
from contextlib import AbstractContextManager
from functools import reduce
from typing import TYPE_CHECKING, ContextManager, Generator, List, NoReturn
from typing import TYPE_CHECKING, NoReturn

import pytest

Expand Down Expand Up @@ -259,7 +261,7 @@ def _get_boolean_value(
) from None


report_header_key = pytest.StashKey[List[str]]()
report_header_key = pytest.StashKey[list[str]]()


@pytest.hookimpl()
Expand Down Expand Up @@ -837,13 +839,13 @@ def _blocking_wrapper(*args, **kwargs) -> NoReturn:
'"db" or "transactional_db" fixtures to enable it.'
)

def unblock(self) -> ContextManager[None]:
def unblock(self) -> AbstractContextManager[None]:
"""Enable access to the Django database."""
self._save_active_wrapper()
self._dj_db_wrapper.ensure_connection = self._real_ensure_connection
return _DatabaseBlockerContextManager(self)

def block(self) -> ContextManager[None]:
def block(self) -> AbstractContextManager[None]:
"""Disable access to the Django database."""
self._save_active_wrapper()
self._dj_db_wrapper.ensure_connection = self._blocking_wrapper
Expand Down
3 changes: 2 additions & 1 deletion pytest_django/runner.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
from argparse import ArgumentParser
from typing import Any, Iterable
from collections.abc import Iterable
from typing import Any


class TestRunner:
Expand Down
2 changes: 1 addition & 1 deletion pytest_django_test/db_helpers.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
import os
import sqlite3
import subprocess
from typing import Mapping
from collections.abc import Mapping

import pytest
from django.conf import settings
Expand Down
2 changes: 1 addition & 1 deletion tests/test_database.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
from __future__ import annotations

from typing import Generator
from collections.abc import Generator

import pytest
from django.db import connection, transaction
Expand Down
2 changes: 1 addition & 1 deletion tests/test_fixtures.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@
"""

import socket
from collections.abc import Generator
from contextlib import contextmanager
from typing import Generator
from urllib.error import HTTPError
from urllib.request import urlopen

Expand Down
2 changes: 1 addition & 1 deletion tests/test_runner.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@


@pytest.mark.parametrize(
"kwargs, expected",
("kwargs", "expected"),
[
({}, call(["tests"])),
({"verbosity": 0}, call(["--quiet", "tests"])),
Expand Down
7 changes: 3 additions & 4 deletions tox.ini
Original file line number Diff line number Diff line change
@@ -1,11 +1,10 @@
[tox]
envlist =
py313-dj{main,52,51}-postgres
py312-dj{main,52,51,50,42}-postgres
py311-dj{main,52,51,50,42}-postgres
py310-dj{main,52,51,50,42}-postgres
py312-dj{main,52,51,42}-postgres
py311-dj{main,52,51,42}-postgres
py310-dj{main,52,51,42}-postgres
py39-dj42-postgres
py38-dj42-postgres
linting

[testenv]
Expand Down