Repository: jazzband/django-oauth-toolkit (language: python)

Issue:
Django 4.0 compatibility
**Describe the bug**
When used with Django 4.0, there are reports of a missing migration. For example:
```
Migrations for 'oauth2_provider':
  /usr/local/lib/python3.8/dist-packages/oauth2_provider/migrations/0005_alter_accesstoken_user_alter_application_user_and_more.py
    - Alter field user on accesstoken
    - Alter field user on application
    - Alter field user on grant
    - Alter field user on idtoken
    - Alter field user on refreshtoken
```
By default, of course, normal users cannot write such a file, and applying migrations without causes warnings like this:
```
 Your models in app(s): 'oauth2_provider' have changes that are not yet reflected in a migration, and so won't be applied.
  Run 'manage.py makemigrations' to make new migrations, and then re-run 'manage.py migrate' to apply them.
```
I note that Django 4.0 release notes mention the possibility of some no-op migrations being needed...I am not sure if this is the root cause.

**To Reproduce**
Run "./manage.py makemigrations" in a project which uses this package.

**Expected behavior**
Any needed migration should be provided.

**Version**
- [x] I have tested with the latest published release and it's still a problem.
- [ ] I have tested with the master branch and it's still a problem.

**Additional context**





Discussion / hints:
Looks like https://docs.djangoproject.com/en/4.0/releases/4.0/#migrations-autodetector-changes is to blame for the migration. In my project, the generated migration is altering the `user` ForeignKey on all the models like `models.ForeignKey(...identical..., to='auth.user')`. My `settings.AUTH_USER_MODEL` is `auth.User`, so I suspect this difference in capitalization is causing the migration.

Fix patch:
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 2d369884c..dbf5eee2e 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -16,51 +16,33 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
 
 ## [Unreleased]
 
-## [1.6.0] - 2021-12-14
+## [1.6.0] 2021-12-19
 ### Added
-* #712, #636, #808. Calls to `django.contrib.auth.authenticate()` now pass a `request`
-  to provide compatibility with backends that need one.
-* #950 Add support for RSA key rotation.
-* #968 Add support for Django 3.2
-* #949 Provide django.contrib.auth.authenticate() with a request for compatibiity with more backends.
-* #953 Allow loopback redirect URIs using ports as described in RFC8252
-* #972 Add Farsi/fa language support
-* #978 Multiple rsa keys
-* #967 OpenID: Add claims to Well know
-* #1019 #1024 #1026 #1030 #1033 #1036 [pre-commit.ci] pre-commit autoupdate
-* #1021 Jazzband: Synced file(s) with jazzband/.github
-* #1041 Admin: make extensive fields raw_id, add search fields
+* #949 Provide django.contrib.auth.authenticate() with a `request` for compatibiity with more backends (like django-axes).
+* #968, #1039 Add support for Django 3.2 and 4.0.
+* #953 Allow loopback redirect URIs using random ports as described in [RFC8252 section 7.3](https://datatracker.ietf.org/doc/html/rfc8252#section-7.3).
+* #972 Add Farsi/fa language support.
+* #978 OIDC: Add support for [rotating multiple RSA private keys](https://django-oauth-toolkit.readthedocs.io/en/latest/oidc.html#rotating-the-rsa-private-key).
+* #978 OIDC: Add new [OIDC_JWKS_MAX_AGE_SECONDS](https://django-oauth-toolkit.readthedocs.io/en/latest/settings.html#oidc-jwks-max-age-seconds) to improve `jwks_uri` caching.
+* #967 OIDC: Add [additional claims](https://django-oauth-toolkit.readthedocs.io/en/latest/oidc.html#adding-claims-to-the-id-token) beyond `sub` to the id_token.
+* #1041 Add a search field to the Admin UI (e.g. for search for tokens by email address).
 
 ### Changed
-* #1022 Replaced pkg_resources usage with importlib.metadata
-* #981 Require redirect_uri if multiple URIs are registered
-* #963 Handles ValueErrors with invalid hex values in query strings (#954)
-* #989 Change remaining HttpResponse to JsonResponse
-* #988 Optimize DB access in AccessTokenAdmin
-* #973 Use django-cors-headers in docs
-* #1009 Add missing space in assertion error
-* #1025 Moved version info from setup.cfg into package
-* #991 Update settings.rst with text
-* #956 doc: missing argument to get_userinfo_claims
-* #985 Documentation grammar
-* #977 doc: Add missing import
-* #1014 Update tutorial_03.rst to use arrays instead of tuples in the settings.py file
-
-### Fixed
-* #948 Fix #524 - Restrict usage of timezone aware expire dates to Django projects with USE_TZ set to True
-* #957 Fix double oauth2_provider mountpoint in oidc view
-* #524 Restrict usage of timezone aware expire dates to Django projects with USE_TZ set to True.
-* #953 Allow loopback redirect URIs with random ports using http scheme, localhost address and no explicit port
-  configuration in the allowed redirect_uris for Oauth2 Applications (RFC8252)
-* #954 Query strings with invalid hex values now raise a SuspiciousOperation exception
-* #955 Avoid doubling of `oauth2_provider` urls mountpath in json response for OIDC view `ConnectDiscoveryInfoView`.
-  Breaks existing OIDC discovery output
+* #981 Require redirect_uri if multiple URIs are registered per [RFC6749 section 3.1.2.3](https://datatracker.ietf.org/doc/html/rfc6749#section-3.1.2.3)
+* #991 Update documentation of [REFRESH_TOKEN_EXPIRE_SECONDS](https://django-oauth-toolkit.readthedocs.io/en/latest/settings.html#refresh-token-expire-seconds) to indicate it may be `int` or `datetime.timedelta`.
+* #977 Update [Tutorial](https://django-oauth-toolkit.readthedocs.io/en/stable/tutorial/tutorial_01.html#) to show required `include`.
 
 ## Removed
-* #968 Remove support for Django 3.0
+* #968 Remove support for Django 3.0 & 3.1 and Python 3.6
 * #1035 Removes default_app_config for Django Deprecation Warning
 * #1023 six should be dropped
 
+### Fixed
+* #963 Fix handling invalid hex values in client query strings with a 400 error rather than 500.
+* #973 [Tutorial](https://django-oauth-toolkit.readthedocs.io/en/latest/tutorial/tutorial_01.html#start-your-app) updated to use `django-cors-headers`.
+* #956 OIDC: Update documentation of [get_userinfo_claims](https://django-oauth-toolkit.readthedocs.io/en/latest/oidc.html#adding-information-to-the-userinfo-service) to add the missing argument.
+
+
 ## [1.5.0] 2021-03-18
 
 ### Added
diff --git a/README.rst b/README.rst
index fe435987f..06ca3dce7 100644
--- a/README.rst
+++ b/README.rst
@@ -49,8 +49,8 @@ Please report any security issues to the JazzBand security team at <security@jaz
 Requirements
 ------------
 
-* Python 3.6+
-* Django 2.2+
+* Python 3.7+
+* Django 2.2, 3.2, or >=4.0.1
 * oauthlib 3.1+
 
 Installation
diff --git a/docs/index.rst b/docs/index.rst
index d2d4e8c3c..fdd8131b7 100644
--- a/docs/index.rst
+++ b/docs/index.rst
@@ -21,8 +21,8 @@ If you need help please submit a `question <https://github.com/jazzband/django-o
 Requirements
 ------------
 
-* Python 3.6+
-* Django 2.2+
+* Python 3.7+
+* Django 2.2, 3.2, 4.0.1+
 * oauthlib 3.1+
 
 Index
diff --git a/setup.cfg b/setup.cfg
index b72ad7275..4a8de4569 100644
--- a/setup.cfg
+++ b/setup.cfg
@@ -13,16 +13,16 @@ classifiers =
 	Environment :: Web Environment
 	Framework :: Django
 	Framework :: Django :: 2.2
-	Framework :: Django :: 3.1
 	Framework :: Django :: 3.2
+	Framework :: Django :: 4.0
 	Intended Audience :: Developers
 	License :: OSI Approved :: BSD License
 	Operating System :: OS Independent
 	Programming Language :: Python :: 3
-	Programming Language :: Python :: 3.6
 	Programming Language :: Python :: 3.7
 	Programming Language :: Python :: 3.8
 	Programming Language :: Python :: 3.9
+	Programming Language :: Python :: 3.10
 	Topic :: Internet :: WWW/HTTP
 
 [options]
@@ -32,7 +32,7 @@ zip_safe = False
 # jwcrypto has a direct dependency on six, but does not list it yet in a release
 # Previously, cryptography also depended on six, so this was unnoticed
 install_requires =
-	django >= 2.2
+	django >= 2.2, != 4.0.0
 	requests >= 2.13.0
 	oauthlib >= 3.1.0
 	jwcrypto >= 0.8.0
diff --git a/tox.ini b/tox.ini
index ebd9ffb6e..23a84d805 100644
--- a/tox.ini
+++ b/tox.ini
@@ -2,15 +2,17 @@
 envlist =
     flake8,
     docs,
-    py{36,37,38,39}-dj{32,31,22},
-    py{38,39}-djmain,
+    py{37,38,39}-dj22,
+    py{37,38,39,310}-dj32,
+    py{38,39,310}-dj40,
+    py{38,39,310}-djmain,
 
 [gh-actions]
 python =
-    3.6: py36
     3.7: py37
     3.8: py38, docs, flake8
     3.9: py39
+    3.10: py310
 
 [pytest]
 django_find_project = false
@@ -33,8 +35,8 @@ setenv =
     PYTHONWARNINGS = all
 deps =
     dj22: Django>=2.2,<3
-    dj31: Django>=3.1,<3.2
     dj32: Django>=3.2,<3.3
+    dj40: Django>=4.0.0,<4.1
     djmain: https://github.com/django/django/archive/main.tar.gz
     djangorestframework
     oauthlib>=3.1.0
@@ -49,7 +51,7 @@ deps =
 passenv =
     PYTEST_ADDOPTS
 
-[testenv:py{38,39}-djmain]
+[testenv:py{38,39,310}-djmain]
 ignore_errors = true
 ignore_outcome = true
 


Test patch:
diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml
index f1f734271..08d2ddc77 100644
--- a/.github/workflows/test.yml
+++ b/.github/workflows/test.yml
@@ -9,7 +9,7 @@ jobs:
       fail-fast: false
       max-parallel: 5
       matrix:
-        python-version: ['3.6', '3.7', '3.8', '3.9']
+        python-version: ['3.7', '3.8', '3.9', '3.10']
 
     steps:
     - uses: actions/checkout@v2