Я использую Django All Auth для аутентификации пользователя, но мне нужно использовать номер телефона или поле электронной почты при входе в систему. Я расширил пользовательский класс следующим образом:
class User(AbstractUser):
phone_number = models.CharField(max_length=10, unique=True)
def __unicode__(self):
return self.username
Моя форма регистрации выглядит так:
class SignupForm(forms.Form):
phone_number = forms.CharField(max_length=10,label='phone_number')
def signup(self, request, user):
user.phone_number = self.cleaned_data['phone_number']
user.save()
Номер телефона сохраняется в бэкэнде с использованием этого, но мне нужно аутентифицировать пользователя, если он вводит либо адрес электронной почты, либо номер телефона. Какой класс мне нужно расширить для Django All Auth. Я прочитал много вопросов, но не смог найти ничего хорошего.
Если я добавлю ACCOUNT_USER_MODEL_USERNAME_FIELD = 'phone_number' в settings.py, он будет аутентифицироваться по телефону, но не по электронной почте.
РЕДАКТ. 1:
Я создал файл backends.py и написал этот код
class PhoneNumberBackend(object):
"""
Custom Phone Number Backend to perform authentication via phone number
"""
def authenticate(self, username=None, password=None):
my_user_model = get_user_model()
try:
user = my_user_model.objects.get(phone_number=username)
if user.check_password(password):
return user # return user on valid credentials
except my_user_model.DoesNotExist:
return None # return None if custom user model does not exist
except:
return None # return None in case of other exceptions
def get_user(self, user_id):
my_user_model = get_user_model()
try:
return my_user_model.objects.get(pk=user_id)
except my_user_model.DoesNotExist:
return None
Settings.py теперь выглядит так:
AUTHENTICATION_BACKENDS = (
# 'userauth.backends.PhoneNumberBackend',
# Needed to login by username in Django admin, regardless of `allauth`
'django.contrib.auth.backends.ModelBackend',
# `allauth` specific authentication methods, such as login by e-mail
'allauth.account.auth_backends.AuthenticationBackend',
)
Он должен проходить проверку подлинности с использованием номера телефона, а если нет, то переходить на другие способы проверки подлинности, верно? Это так не работает.