Search code examples
pythondjangoauthenticationdjango-modelsdjango-authentication

Django: ImportError: cannot import name 'get_user_model' from 'django.contrib.auth.models'


I have a problem using Djangos Default user from django.contrib.auth.models but trying to use it with my custom User model, using from django.contrib.auth.models import AbstractUser.

Following those articles:

So here is my User model:

from django.db import models
from django.contrib.auth.models import AbstractUser
# from django.conf import settings
from django_countries.fields import CountryField
# https://github.com/SmileyChris/django-countries


class User(AbstractUser):
    """auth/login-related fields"""
    is_a = models.BooleanField('a status', default=False)
    is_o = models.BooleanField('o status', default=False)

    def __str__(self):
        return "{} {}".format(self.first_name, self.last_name)

and here is my Profile model:

from django.db import models
from django_countries.fields import CountryField # https://github.com/SmileyChris/django-countries
from django.contrib.auth.models import get_user_model
User = get_user_model()
# https://medium.com/swlh/best-practices-for-starting-a-django-project-with-the-right-user-model-290a09452b88

from django.db.models.signals import post_save 
from django.dispatch import receiver



class Profile(models.Model):
    """non-auth-related/cosmetic fields"""
    user = models.OneToOneField(User, on_delete=models.CASCADE)
    birth_date = models.DateTimeField(auto_now=False, auto_now_add=False, null=True)
    nationality = CountryField(null=True)

    GENDER_CHOICES = (
        ('M', 'Male'),
        ('F', 'Female'),
    )
    gender = models.CharField(max_length=1, choices=GENDER_CHOICES, null=True)

    def __str__(self):
        return f'{self.user.username} Profile'

"""receivers to add a Profile for newly created users"""
@receiver(post_save, sender=User) 
def create_user_profile(sender, instance, created, **kwargs):
     if created:
         Profile.objects.create(user=instance)
@receiver(post_save, sender=User) 
def save_user_profile(sender, instance, **kwargs):
     instance.profile.save()

and in my settings.py I added AUTH_USER_MODEL = 'mysite.User'

settings.py:

AUTH_USER_MODEL = 'mysite.User'

INSTALLED_APPS = [
    'mysite.apps.MysiteConfig',
    'django_countries',
    'djmoney',
    'rest_framework',
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
]

But when I'm trying to make my migrations i get the error:

ImportError: cannot import name 'get_user_model' from 'django.contrib.auth.models'

And I've looked for answers but I'm only getting on topics speaking of Django needing to be version 1.5 or higher, and I'm using Django 3.0.2

The typical posts i find is this:

Does anyone know what am I missing? or doing wrong?

Thanks!

UPDATE 1:

Here is my User views, with my User serializers:

views_user.py:

from rest_framework import generics
from django.contrib.auth import get_user_model
from ..models.model_user import *
from ..serializers.serializers_user import *


class UserIndex(generics.ListAPIView):
    """List all users, or create a new user."""

    queryset = User.objects.all().order_by('id')
    serializer_class = UserIndexSerializer

class UserCreate(generics.CreateAPIView):
    """List all art pieces, or create a new art piece."""

    queryset = User.objects.all()
    serializer_class = UserCreateSerializer

class UserDetails(generics.RetrieveUpdateDestroyAPIView):
    """Retrieve, update or delete a user instance."""

    queryset = User.objects.all()
    serializer_class = UserDetailsSerializer

serializers_user.py

from rest_framework import serializers
from django.contrib.auth import get_user_model
from ..models.model_user import *


class UserIndexSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        fields = [
            'id',
            'first_name',
            'last_name',
            'email',
            'age',
            # 'nationality',
            'gender',
            'profession'
        ]

class UserCreateSerializer(serializers.ModelSerializer):

    class Meta:
        model = User
        fields = [
            'first_name',
            'last_name',
            'email',
            'profession'
        ]

class UserDetailsSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        fields = '__all__'

Solution

  • Your import in the Profile model from django.contrib.auth.models import get_user_model is wrong.

    You should do from django.contrib.auth import get_user_model, note there is no .models at the end.

    According to documentation and examples in Django docs: https://docs.djangoproject.com/en/3.0/topics/auth/customizing/#django.contrib.auth.get_user_model