1

I am trying to change the way the user do log in by changing from username to email.

I put in settings.py:

AUTHENTICATION_BACKENDS = ['apps.myapp.ModelBackend']

In myapp I created the file backends.py with the code:

from django.contrib.auth import backends, get_user_model
from django.db.models import Q
UserModel = get_user_model()


class ModelBackend(backends.ModelBackend):

    def authenticate(self, request, username=None, password=None, **kwargs):
        if username is None:
            username = kwargs.get(UserModel.USERNAME_FIELD)
        try:
            # user = UserModel._default_manager.get_by_natural_key(username)
            # You can customise what the given username is checked against, here I compare to both username and email fields of the User model
            user = UserModel.objects.get(Q(username__iexact=username) | Q(email__iexact=username))
        except UserModel.DoesNotExist:
            # Run the default password hasher once to reduce the timing
            # difference between an existing and a nonexistent user (#20760).
            UserModel().set_password(password)
        else:
            if user.check_password(password) and self.user_can_authenticate(user):
                return user
        return super().authenticate(request, username, password, **kwargs)

And on myapp in models.py I did:

from django.db import models
from django.contrib.auth.models import AbstractUser


class User(AbstractUser):
    USERNAME_FIELD = 'email'
    email = models.EmailField(unique=True, name='email address')
    REQUIRED_FIELDS = []

But when I run makemigrations I get the following error:

SystemCheckError: System check identified some issues:

ERRORS:
auth.User.groups: (fields.E304) Reverse accessor for 'User.groups' clashes with reverse accessor for 'User.groups'.
    HINT: Add or change a related_name argument to the definition for 'User.groups' or 'User.groups'.
auth.User.user_permissions: (fields.E304) Reverse accessor for 'User.user_permissions' clashes with reverse accessor for 'User.user_permissions'.
    HINT: Add or change a related_name argument to the definition for 'User.user_permissions' or 'User.user_permissions'.
core.User.groups: (fields.E304) Reverse accessor for 'User.groups' clashes with reverse accessor for 'User.groups'.
    HINT: Add or change a related_name argument to the definition for 'User.groups' or 'User.groups'.
core.User.user_permissions: (fields.E304) Reverse accessor for 'User.user_permissions' clashes with reverse accessor for 'User.user_permissions'.
    HINT: Add or change a related_name argument to the definition for 'User.user_permissions' or 'User.user_permissions'.

I am using Django 2.2.

What do I have to do for the user to login with email and password?

Update :

I put AUTH_USER_MODEL = "myapp.User" in settings.py.

But when a run the makemigrations I recive this warning :

myapp.User: (auth.W004) 'User.email' is named as the 'USERNAME_FIELD', but it is not unique.
    HINT: Ensure that your authentication backend(s) can handle non-unique usernames.
No changes detected

I create the app myusers and in the model I do :

from django.db import models
from django.contrib.auth import get_user_model
class Usuario(models.Model):
    name = models.CharField(max_length=40, help_text='user name')
    user = models.OneToOneField(get_user_model(), on_delete=models.PROTECT)

When I run the server I can not access the admin, I get the error:

ImportError at / admin / login /

Module "apps.myapp" does not set the "ModelBackend" attribute / class
Beto
  • 579
  • 1
  • 5
  • 15
  • 1
    Do you have the flag AUTH_USER_MODEL in you settings.py anywhere? – Joshua Oct 19 '19 at 19:19
  • Oh and possible duplicate of [Django Reverse accessor error](https://stackoverflow.com/questions/40843365/django-reverse-accessor-error?noredirect=1&lq=1) – Joshua Oct 19 '19 at 19:29

0 Answers0