непроверенная электронная почта Аллаута остается непроверенной, когда истекает срок - PullRequest
0 голосов
/ 14 февраля 2020

У меня есть пользовательская модель. и я использую Django rest auth для обработки аутентификации пользователей. проблема заключается в том, что после регистрации при отправке электронного письма. если пользователь не проверяет электронную почту до истечения срока ее действия, кажется, что он застрял так до бесконечности. Я ожидал, что письмо с подтверждением будет отправлено снова, поскольку в моих настройках ACCOUNT_EMAIL_VERIFICATION = "mandatory", из документации предполагается, что сообщение с подтверждением будет повторно отправлено по умолчанию, но этого не происходит. Я заблудился относительно того, что еще делать, и я не могу найти какой-либо ресурс, который помогает.

ниже моя модель

models.py

class User(AbstractBaseUser, PermissionsMixin):
    username = None
    email = models.EmailField(max_length=254, unique=True)
    name = models.CharField(max_length=250)
    is_staff = models.BooleanField(default=False)
    is_superuser = models.BooleanField(default=False)
    is_active = models.BooleanField(default=True)
    last_login = models.DateTimeField(null=True, blank=True)
    date_joined = models.DateTimeField(auto_now_add=True)
    slug = models.SlugField(max_length=255, unique=True, blank=True)

    USERNAME_FIELD = 'email'
    REQUIRED_FIELDS = ['name']

в моем settings.py срок годности пользователя составляет 2 дня

ACCOUNT_AUTHENTICATED_LOGIN_REDIRECTS = True
ACCOUNT_AUTHENTICATION_METHOD = "email"
ACCOUNT_CONFIRM_EMAIL_ON_GET = True
ACCOUNT_EMAIL_CONFIRMATION_AUTHENTICATED_REDIRECT_URL = None #or "api/authenticated/"
ACCOUNT_EMAIL_CONFIRMATION_EXPIRE_DAYS = 1
ACCOUNT_EMAIL_CONFIRMATION_HMAC = False
ACCOUNT_EMAIL_REQUIRED = True
ACCOUNT_USERNAME_REQUIRED = False
ACCOUNT_USER_MODEL_USERNAME_FIELD = None
ACCOUNT_EMAIL_VERIFICATION = "mandatory"
EMAIL_VERIFICATION = "mandatory"
ACCOUNT_DEFAULT_HTTP_PROTOCOL = "http"
ACCOUNT_EMAIL_CONFIRMATION_COOLDOWN = 3600
ACCOUNT_LOGIN_ATTEMPTS_LIMIT = 5
ACCOUNT_LOGIN_ATTEMPTS_TIMEOUT = 180
ACCOUNT_LOGIN_ON_EMAIL_CONFIRMATION = False
ACCOUNT_LOGOUT_ON_GET = True
ACCOUNT_LOGOUT_ON_PASSWORD_CHANGE = True
ACCOUNT_LOGIN_ON_PASSWORD_RESET = False
ACCOUNT_LOGOUT_REDIRECT_URL = "api/login/"
ACCOUNT_SESSION_REMEMBER = True
ACCOUNT_SIGNUP_EMAIL_ENTER_TWICE = False
ACCOUNT_UNIQUE_EMAIL = True
ACCOUNT_USER_MODEL_EMAIL_FIELD = "email"

Ответы [ 2 ]

1 голос
/ 18 февраля 2020

Прежде всего, вы упомянули, что используете django-rest-auth, что не так, и, вероятно, вы используете django-allauth.

Согласно документации django-allauth:

ACCOUNT_EMAIL_VERIFICATION :

Если установлено «обязательное», пользователь блокируется для входа в систему до проверки адреса электронной почты. Выберите «опционально» или «нет», чтобы разрешить вход в систему с непроверенным адресом электронной почты. В случае «опционально», электронное письмо с подтверждением по-прежнему отправляется, тогда как в случае «нет» письма с подтверждением по электронной почте не отправляются.

Таким образом, о пересылке ничего не упоминается. отправка письма с подтверждением, если срок действия первого истек. Для достижения sh того, что вы хотите, у вас должен быть запущен скрипт job, проверяющий токены expired и повторно отправляющий письма с подтверждением вручную.

Вы должны создать скрипт, который будет выглядеть примерно так: this:

from time import sleep
from django.utils import timezone
from django_allauth.account.models import EmailConfirmation

while True:
    def_expired = timezone.now() - datetime.timedelta(days=app_settings.EMAIL_CONFIRMATION_EXPIRE_DAYS)
    expired_tokens = EmailConfirmation.objects.filter(sent__lte=def_expired)
    for token in expired_tokens:
        token.send()
    sleep(2)

И продолжайте работу этого скрипта, используя любой планировщик, который вам нравится (supervisor, pm2, cronjob, et c).

Нижняя строка, django-allauth не имеет / не может иметь нужную вам функциональность. Эту работу необходимо выполнить вручную.

0 голосов
/ 19 февраля 2020

В конце концов я смог решить эту проблему по-другому, я создал представление и URL-адрес, который запрашивает электронную почту пользователя, а затем отправляет ссылку на него, если они не проверены.

views.py

from allauth.account.utils import send_email_confirmation
from allauth.account.admin import EmailAddress
from rest_framework.exceptions import APIException


class EmailConfirmation(APIView):
    permission_classes = [AllowAny] 

    def post(self, request):
        user = get_object_or_404(User, email=request.data['email'])
        emailAddress = EmailAddress.objects.filter(user=user, verified=True).exists()

        if emailAddress:
            return Response({'message': 'This email is already verified'}, status=status.HTTP_400_BAD_REQUEST)
        else:
            try:
                send_email_confirmation(request, user=user)
                return Response({'message': 'Email confirmation sent'}, status=status.HTTP_201_CREATED)
            except APIException:
                return Response({'message': 'This email does not exist, please create a new account'}, status=status.HTTP_403_FORBIDDEN)

urls.py

path('verify-email/again/', qv.EmailConfirmation.as_view(), name='resend-email-confirmation'),
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...