OK... urgh. I don't think there's a perfect answer here.
As you say Tim, assuming the "support unless EOL before the Django version's EOL" we end up dropping the Python version before the LTS, which is going to be just as "premature" as we have now, but for the x.0.
If I've not counted wrong (again) the 4.2 LTS, for example, due April 2023, would drop Python 3.8 and 3.9, which have until Oct 2024 and 2025 to run.
So we'd be trading extra life here for probably more complaints there.
I've played around with various variations of the cut-off date without any real ground being made.
Thus, we probably need to stick as we are, in the main.
A last option would be to say that the x.0 will support one extra older version after the LTS, in cases like this where the otherwise dropped version is supported for the whole lifetime of the x.0 release.
That I think would look like this, assuming we backport support for new versions within the mainstream support period:
4.0 : 3.7, 3.8, 3.9, 3.10
4.1 : 3.8, 3.9, 3.10, 3.11
4.2 LTS : 3.8, 3.9, 3.10, 3.11, 3.12
4.2 is in danger of taking 3.13 as well, but that's released after 4.2 leave mainstream support.
It's akin for what we did for Django 2.2 and Python 3.9
That's independent of whether we keep support for 3.7 a bit longer.
Having looked it through now, I think, fully, that's my final thought.
I'd need to think about the __exact wording, but I hope the idea is clear.
I take Claude's point about contributing but, for me, the desire to support slightly more versions if we can is for beginners, picking up a couple of year old laptop, with SOME version of Python on it, and being able to get going, with hopefully the latest version. I appreciate they can install an older version, but it's hard enough to get started without hitting subtle version changes. I'd like to support that use-case as best we can.
The current policy begins, "Typically...". I'd suggest supporting Python 3.7 for Django 4.0 is merely leveraging that. 🙂
We should decide. I'd be +1 to maintain the current policy but keep 3.7 support for Django 4.0, dropping it at Django 4.1.
Thanks all, and especially you Tim for taking the time to explain and explore the options.