我正在DRF中进行自定义身份验证.用户应发送3个字段(phone, email, password).

我一直在遵循这个答案

我用的是源代码https://github.com/jazzband/djangorestframework-simplejwt/blob/master/rest_framework_simplejwt/serializers.py

Problem:对于下面的请求,我收到了一个空响应{},但预期是令牌或错误消息

{
    "email": "admin1@admin2.ru",
    "password": "admin123456",
    "phone_number": "123132"
}

我的密码:views.py

class CustomTokenObtainPairView(TokenObtainPairView):
    serializer_class = CustomTokenObtainPairSerializer

serializers.py

class CustomTokenObtainPairSerializer(TokenObtainPairSerializer):
    username_field = CustomUser.USERNAME_FIELD

    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)

        self.fields[self.username_field] = serializers.CharField()
        self.fields['password'] = PasswordField()
        self.fields['phone_number'] = serializers.CharField() # authentication requires 3 fields

    def validate(self, attrs):
        authenticate_kwargs = {
            self.username_field: attrs[self.username_field],
            'password': attrs['password'],
            'phone_number': attrs['phone_number']
        }
        try:
            authenticate_kwargs["request"] = self.context["request"]
        except KeyError:
            pass

        self.user = authenticate(**authenticate_kwargs)

        if not api_settings.USER_AUTHENTICATION_RULE(self.user):
            raise exceptions.AuthenticationFailed(
                self.error_messages["no_active_account"],
                "no_active_account",
            )

        return {}

推荐答案

让我们try 手动登录并生成令牌:

serializers.py

from rest_framework import serializer


class LoginUserSerializer(serializers.Serializer):
    email = serializers.EmailField()
    phone_number = serializers.CharField()
    password = serializers.CharField(write_only=True)

views.py

from django.contrib.auth import authenticate

from rest_framework import status, serializers
from rest_framework.response import Response
from rest_framework.views import APIView

from rest_framework_simplejwt.tokens import RefreshToken


class LoginUserApi(APIView):

    def post(self, request):
        serializer = LoginUserSerializer(data=request.data)
        serializer.is_valid(raise_exception=True)
        data = serializer.validated_data # Fetch the data form serializer

        user = authenticate(email=data['email'], password=data['password']) # check for email and password
        if not user or user.phone_number != data['phone_number']: # check for phone
            raise serializers.ValidationError({'detail':'Incorrect email, phone, or password'})

        # Generate Token
        refresh = RefreshToken.for_user(user)

        return Response(
            {
                'access': str(refresh.access_token),
                'refresh': str(refresh)
            }
            , status=status.HTTP_200_OK
            )

如何从简单的JWT docs手动创建令牌

Python相关问答推荐

如何获取TFIDF Transformer中的值?

pyscript中的压痕问题

如何将一个动态分配的C数组转换为Numpy数组,并在C扩展模块中返回给Python

在Python中,从给定范围内的数组中提取索引组列表的更有效方法

计算分布的标准差

如何使regex代码只适用于空的目标单元格

Matplotlib中的字体权重

如何按row_id/row_number过滤数据帧

用两个字符串构建回文

Pandas 数据帧中的枚举,不能在枚举列上执行GROUP BY吗?

仅使用预先计算的排序获取排序元素

极点替换值大于组内另一个极点数据帧的最大值

为什么我只用exec()函数运行了一次文件,而Python却运行了两次?

极点用特定值替换前n行

如何在Python中实现高效地支持字典和堆操作的缓存?

将数据从一个单元格保存到Jupyter笔记本中的下一个单元格

按列表分组到新列中

使用Scikit的ValueError-了解

将Pandas DataFrame中的列名的长文本打断/换行为_STRING输出?

使用Django标签显示信息