Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Django custom user model in admin, relation "auth_user" does not exist

Tags:

django

model

I have a custom user model as below:

class User(AbstractUser):
    subscribe_newsletters = models.BooleanField(default=True)
    old_id = models.IntegerField(null=True, blank=True)
    old_source = models.CharField(max_length=25, null=True, blank=True)

And using the builtin UserAdmin

admin.site.register(User, UserAdmin)

While editing the user record works fine, but when I add a user, I get the following error

Exception Value: 
relation "auth_user" does not exist
LINE 1: ...user"."is_active", "auth_user"."date_joined" FROM "auth_user...
like image 893
James Lin Avatar asked Jun 06 '13 03:06

James Lin


2 Answers

After some digging around I found this

https://docs.djangoproject.com/en/1.5/topics/auth/customizing/#custom-users-and-the-built-in-auth-forms

The culprit is a function clean_username inside UserCreationForm inside django.contrib.auth.forms.py. A few tickets have been created, but apparently the maintainers don't think it's a defect:

https://code.djangoproject.com/ticket/20188

https://code.djangoproject.com/ticket/20086

def clean_username(self):
        # Since User.username is unique, this check is redundant,
        # but it sets a nicer error message than the ORM. See #13147.
        username = self.cleaned_data["username"]
        try:
            User._default_manager.get(username=username)
        except User.DoesNotExist:
            return username
        raise forms.ValidationError(self.error_messages['duplicate_username'])

The User in this file is directly referencing to the builtin user model.

To fix it, I created my custom forms

from models import User #you can use get_user_model
from django.contrib.auth.forms import UserCreationForm
from django.contrib.auth.admin import UserAdmin
from django.contrib.auth import forms

class MyUserCreationForm(UserCreationForm):
    def clean_username(self):
        # Since User.username is unique, this check is redundant,
        # but it sets a nicer error message than the ORM. See #13147.
        username = self.cleaned_data["username"]
        try:
            User._default_manager.get(username=username)
        except User.DoesNotExist:
            return username
        raise forms.ValidationError(self.error_messages['duplicate_username'])

    class Meta(UserCreationForm.Meta):
        model = User

class MyUserAdmin(UserAdmin):  
    add_form = MyUserCreationForm   

admin.site.register(User,MyUserAdmin)

Or you can try monkey patching the original UserCreationForm to replace the User variable.

like image 185
James Lin Avatar answered Sep 27 '22 16:09

James Lin


Django 1.8

If your app is not yet using migrations then this could also be the problem, as contrib.auth uses them. Enabling migrations for my app solved it for me.

$ ./manage.py makemigrations <my_app>
$ ./manage.py migrate
like image 26
Risadinha Avatar answered Sep 27 '22 16:09

Risadinha