In some sections of django.contrib.auth.forms.py, when referring to the
User model, Django wisely uses get_user_model(), so whether we decide to
use the built-in User model, extend it, or use our own, we always get the
right user when importing these forms.
However, in the UserCreationForm for example, Django instead explicitly
refers to the built-in user found at django.contrib.auth.models.
This causes some forms to work and some forms to fail when using a custom
or extended User model, even though extending the built-in User model is
suggested in the Django documentation.
This is an easy fix and would require all forms in
django.contrib.auth.forms to refer to get_user_model() as opposed to the
imported built-in User. In the case where a custom User model is not being
utilized, get_user_model() will automatically refer to the built-in User.
--
Ticket URL: <https://code.djangoproject.com/ticket/32599>
Django <https://code.djangoproject.com/>
The Web framework for perfectionists with deadlines.
Old description:
> == Inconsistent Reference
>
> In some sections of django.contrib.auth.forms.py, when referring to the
> User model, Django wisely uses get_user_model(), so whether we decide to
> use the built-in User model, extend it, or use our own, we always get the
> right user when importing these forms.
>
> However, in the UserCreationForm for example, Django instead explicitly
> refers to the built-in user found at django.contrib.auth.models.
>
> This causes some forms to work and some forms to fail when using a custom
> or extended User model, even though extending the built-in User model is
> suggested in the Django documentation.
>
> This is an easy fix and would require all forms in
> django.contrib.auth.forms to refer to get_user_model() as opposed to the
> imported built-in User. In the case where a custom User model is not
> being utilized, get_user_model() will automatically refer to the built-in
> User.
New description:
== Inconsistent Reference
In some sections of `django.contrib.auth.forms.py`, when referring to the
User model, Django wisely uses `get_user_model()`, so whether we decide to
use the built-in User model, extend it, or use our own, we always get the
right user when importing these forms.
However, in the `UserCreationForm` for example, Django instead explicitly
refers to the built-in user found at `django.contrib.auth.models`.
This causes some forms to work and some forms to fail when using a custom
or extended User model, even though extending the built-in User model is
suggested in the Django documentation.
This is an easy fix and would require all forms in
`django.contrib.auth.forms` to refer to `get_user_model()` as opposed to
the imported built-in `User`. In the case where a custom User model is not
being utilized, `get_user_model()` will automatically refer to the built-
in User.
To reproduce:
1. Start a new Django project and initiate an app.
2. In `models.py` of your app, sub-class `AbstractUser` by importing it
from `django.contrib.auth.models`.
3. In settings.py, add `AUTH_USER_MODEL=yourapp.YourSubClassedUser` (this
is all standard).
{{{
from django.contrib.auth.models import AbstractUser
class User(AbstractUser):
pass
}}}
4. Register a view and associated url to render a `UserCreationForm`,
perhaps using `CreateView` or `FormView`.
{{{
from django.shortcuts import render
from .models import User
from django.contrib.auth.forms import UserCreationForm
from django.views.generic.edit import FormView, CreateView
class RegisterView(CreateView):
model = User
form_class = UserCreationForm
template_name = 'users/register.html
}}}
5. Render the form in a template, and run migrations for the first time.
6. Attempt to start the server. This will throw the following error:
{{{
AttributeError: Manager isn't available; 'auth.User' has been swapped for
'users.User'
}}}
In the documentation, Django claims that sub-classing the built-in User is
not only recommended, but that it will behave exactly like the built-in
User model. Patching `django.contrib.auth.forms.py` would ensure this.
--
--
Ticket URL: <https://code.djangoproject.com/ticket/32599#comment:1>
* status: assigned => closed
* resolution: => duplicate
* easy: 1 => 0
Comment:
Duplicate of #28608. This is also a
[https://docs.djangoproject.com/en/stable/topics/auth/customizing/#custom-
users-and-the-built-in-auth-forms documented] behavior.
--
Ticket URL: <https://code.djangoproject.com/ticket/32599#comment:2>