首页 > 后端开发 > Python教程 > Django 帐户管理应用程序(忘记密码和帐户详细信息

Django 帐户管理应用程序(忘记密码和帐户详细信息

Mary-Kate Olsen
发布: 2024-11-25 20:17:10
原创
893 人浏览过

从这篇文章中可以期待什么?

我们在之前的文章中开始开发帐户应用程序,本文将以此为基础。它将涵盖

  • 用于忘记密码、重新发送代码和帐户详细信息的序列化程序。
  • 相同 API 的视图。
  • 当然还有网址。

我会尽力介绍尽可能多的细节,以免让您感到无聊,但我仍然希望您熟悉 Python 和 Django 的某些方面。

最终版本的源代码可以在https://github.com/saad4software/alive-diary-backend

系列订购

感兴趣的话可以查看之前的文章!

  1. 从头开始的人工智能项目、创意、Alive 日记
  2. 用 Google AI Studio 证明它是可行的
  3. Django API 项目设置
  4. Django账户管理(一)、注册与激活
  5. Django账户管理(二)、登录及修改密码
  6. 带有 Swagger 的 Django Rest 框架
  7. Django 帐户管理 (3) 忘记密码和帐户详细信息(您在这里?)

它是如何运作的?

忘记密码请求如何运作?流程应遵循以下步骤

  • 用户显然忘记了他的密码?我真傻。
  • 用户输入他/她的电子邮件地址。
  • 一封带有验证码的邮件发送至邮箱。
  • 用户可以使用电子邮件和激活码来设置新密码。

因此,我们需要一个 API 来获取电子邮件地址、创建激活码并将其发送给用户,与重新发送代码 API 相同。
我们还需要另一个 API 来获取电子邮件、激活码和新密码来重置密码。
从重新发送代码 API 开始现在听起来是个好主意。

重新发送代码 API

一如既往,让我们从序列化器开始

class SendCodeSerializer(serializers.Serializer):
    username = serializers.CharField(required=True)

    def validate_username(self, value):
        if not is_valid_email(value):
            raise serializers.ValidationError("invalid_email")

        verification_query = get_user_model().objects.filter(username=value).exists()
        if not verification_query:
            raise serializers.ValidationError("invalid_username")

        return value

登录后复制
登录后复制

app_account/serializers.py

这是一个通用序列化程序,只有一个字段,即用户名,我们正在检查以确保它是有效的电子邮件地址,并且用户已在系统中注册。

现在来看看

class AccountSendCodeView(APIView):
    permission_classes = ()
    renderer_classes = [CustomRenderer, BrowsableAPIRenderer]


    @swagger_auto_schema(request_body=SendCodeSerializer)
    def post(self, request, *args, **kwargs):
        serializer = SendCodeSerializer(data=request.data)

        if not serializer.is_valid():
            raise APIException(serializer.errors)

        user = get_user_model().objects.filter(username=serializer.validated_data.get("username")).first()
        code = VerificationCode(user=user, email=user.username)
        code.save()

        send_mail(
            'Password Reset Code',
            'Your password reset code is ' + str(code.code),
            f'AliveDiary<{settings.EMAIL_SENDER}>',
            [user.username],
            fail_silently=False,
        )

        return Response("success")
登录后复制
登录后复制

app_account/views.py

视图首先验证请求,然后获取用户并为其创建代码实例。最后通过电子邮件将代码发送给用户。
最后是网址

urlpatterns = [
    path('register/', AccountRegisterView.as_view()),
    path('activate/', AccountActivateView.as_view()),

    path('login/', AccountLoginView.as_view()),
    path('refresh/', AccountRefreshTokenView.as_view()),

    path('code/', AccountSendCodeView.as_view()), #new

    path('password/', AccountChangePasswordView.as_view()),
]
登录后复制
登录后复制

app_account/urls.py

我们现在可以在 swagger 上测试它

Django accounts management app ( forgot password and account details

重置密码API

序列化器应包含用户名、发送的代码和新密码;它应该检查以确保它是有效的用户名和代码,有点像

class ForgotPasswordSerializer(serializers.Serializer):
    username = serializers.CharField(required=True)
    code = serializers.CharField(required=True)
    new_password = serializers.CharField(required=True)

    def validate(self, data):
        verification_query = VerificationCode.objects.filter(
            user__username=data['username'],
        ).order_by('-id')

        if not verification_query.exists():
            raise serializers.ValidationError("no_code")

        code = verification_query[0]
        if str(code.code) != str(data['code']):
            raise serializers.ValidationError("invalid_code")

        return data
登录后复制
登录后复制

app_account/serializers.py

所有字段都是必需的,我们使用验证函数来同时验证用户名和代码。如果该用户没有即时代码,我们会引发验证错误,如果发送的代码与即时代码值不匹配,我们会通过引发“invalid_code”验证错误来通知用户。

对于视图,我们需要首先验证序列化器

class SendCodeSerializer(serializers.Serializer):
    username = serializers.CharField(required=True)

    def validate_username(self, value):
        if not is_valid_email(value):
            raise serializers.ValidationError("invalid_email")

        verification_query = get_user_model().objects.filter(username=value).exists()
        if not verification_query:
            raise serializers.ValidationError("invalid_username")

        return value

登录后复制
登录后复制

app_account/views.py

如果序列化器无效,我们会引发一个带有序列化器错误的 API 异常,如果有效,我们将使用序列化器数据查询验证瞬间。请注意,此查询始终存在,并且发送的代码与验证即时代码值相同,因为此查询已经通过了序列化器检查。
然后我们从数据库中删除验证实例,并使用序列化器中的“new_password”值更新用户密码

最后,让我们更新 URL 文件

class AccountSendCodeView(APIView):
    permission_classes = ()
    renderer_classes = [CustomRenderer, BrowsableAPIRenderer]


    @swagger_auto_schema(request_body=SendCodeSerializer)
    def post(self, request, *args, **kwargs):
        serializer = SendCodeSerializer(data=request.data)

        if not serializer.is_valid():
            raise APIException(serializer.errors)

        user = get_user_model().objects.filter(username=serializer.validated_data.get("username")).first()
        code = VerificationCode(user=user, email=user.username)
        code.save()

        send_mail(
            'Password Reset Code',
            'Your password reset code is ' + str(code.code),
            f'AliveDiary<{settings.EMAIL_SENDER}>',
            [user.username],
            fail_silently=False,
        )

        return Response("success")
登录后复制
登录后复制

app_account/urls.py

账户详情API

让我们首先为用户模型创建一个序列化器,它看起来像这样

urlpatterns = [
    path('register/', AccountRegisterView.as_view()),
    path('activate/', AccountActivateView.as_view()),

    path('login/', AccountLoginView.as_view()),
    path('refresh/', AccountRefreshTokenView.as_view()),

    path('code/', AccountSendCodeView.as_view()), #new

    path('password/', AccountChangePasswordView.as_view()),
]
登录后复制
登录后复制

app_account/serializers.py

它是一个模型序列化器,我们选择了用户模型并列出了要序列化的字段。

转向视图,我们需要一个允许用户通过 GET 请求获取用户详细信息并通过 POST 请求更新用户详细信息的视图,它看起来有点像

class ForgotPasswordSerializer(serializers.Serializer):
    username = serializers.CharField(required=True)
    code = serializers.CharField(required=True)
    new_password = serializers.CharField(required=True)

    def validate(self, data):
        verification_query = VerificationCode.objects.filter(
            user__username=data['username'],
        ).order_by('-id')

        if not verification_query.exists():
            raise serializers.ValidationError("no_code")

        code = verification_query[0]
        if str(code.code) != str(data['code']):
            raise serializers.ValidationError("invalid_code")

        return data
登录后复制
登录后复制

app_account/views.py

和网址

class AccountForgotPasswordView(APIView):
    permission_classes = ()
    renderer_classes = [CustomRenderer, BrowsableAPIRenderer]

    @swagger_auto_schema(request_body=ForgotPasswordSerializer)
    def post(self, request, *args, **kwargs):
        serializer = ForgotPasswordSerializer(data=request.data)
        if not serializer.is_valid():
            raise APIException(serializer.errors)

        verification_query = VerificationCode.objects.filter(
            user__username=serializer.validated_data.get('username'),
            code=serializer.validated_data.get('code')
        ).order_by('-id')

        verification_query.delete()

        user = get_user_model().objects.filter(
            username=serializer.validated_data.get('username'),
        ).first()
        user.set_password(serializer.validated_data.get('new_password'))
        user.save()
        return Response("success")
登录后复制

app_account/urls.py

就是这样!让我们用 Swagger 来测试一下,打开 http://localhost:8555/swagger/ 并使用登录名来获取有效的令牌。为了测试任何授权请求,我们必须单击锁定 ?图标,任何 swagger 中的锁图标,并为令牌提供“Bearer”前缀,有点像“Bearer eyJhbGc...”

Django accounts management app ( forgot password and account details

现在测试详细信息 API 应返回如图所示的帐户详细信息

Django accounts management app ( forgot password and account details

就是这样!恭喜,您拥有一个功能齐全的帐户管理应用程序,只需进行最少的修改即可在任何 Django 应用程序中使用

您认为它还需要其他功能吗?请提出建议!

我们将在下一篇文章中回到主应用程序,所以

敬请期待?

以上是Django 帐户管理应用程序(忘记密码和帐户详细信息的详细内容。更多信息请关注PHP中文网其他相关文章!

来源:dev.to
本站声明
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
作者最新文章
热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板