我正在将系统保存的用户数据保存到模型中。我想在views.py中编写一部分逻辑,并在serializer中编写一部分保存数据。我想将系统密码更改为hash.Now我写的views.py中的代码,
class InfoViews(viewsets.ModelViewSet):
queryset = Info.objects.all()
serializer_class = InfoSerializer
lookup_field = 'id'
def create(self,request, *args, **kwargs):
user = Info()
passwd = request.data['password']
md5 = hashlib.md5()
md5.update(passwd.encode('utf-8'))
user.password = md5.hexdigest()
user.save()
return JsonResponse({"data":"data"})
在serializer.py
中class InfoSerializer(serializers.ModelSerializer):
created_time = serializers.DateTimeField(required=False)
class Meta:
model = Info
fields = '__all__'
def create(self, validated_data):
user = Info(
email=validated_data['email'],
username=validated_data['username'],
)
user.set_password(validated_data['password'])
user.save()
return user
在models.py
中class Info(models.Model):
username = custom_fields.NotEmptyCharField(max_length=100, unique=True)
email = models.EmailField()
password = custom_fields.NotEmptyCharField(max_length=100)
class Meta:
db_table = 'info'
def __str__(self):
return '%s: %s' % (self.username, self.email)
现在当我试图将用户数据保存到模型时,django.core.exceptions.ValidationError:['不能为空!']错误发生。我的代码出了什么问题?我搜索http://www.django-rest-framework.org/api-guide/serializers/。怎么办?我解决了这个问题?
答案 0 :(得分:1)
您收到验证错误,因为email
是必填字段。当您运行user.save()
时,不会发送email
值,因此会发送ValidationError
。
你绝对应该保存视图中的所有内容,而Serialiser只是一种改变DRF数据呈现方式的方法。
另外,你真的不应该使用md5来保存你的密码。只需使用内置的Django方法:user.set_password(password)
- Django将为您提供更安全的哈希处理。
答案 1 :(得分:1)
您没有使用InfoSerializer()
序列化程序,因此,从中删除create()
方法,然后按照以下方式更改views.py
,
class InfoViews(ModelViewSet):
queryset = Info.objects.all()
serializer_class = InfoSerializer
lookup_field = 'id'
def create(self, request, *args, **kwargs):
serializer = InfoSerializer(request.data).data
serializer.pop('created_time', None)
passwd = serializer['password']
md5 = hashlib.md5()
md5.update(passwd.encode('utf-8'))
serializer['password'] = md5.hexdigest()
Info.objects.create(**serializer)
return JsonResponse({"data": "data"})
我的友好建议
我不认为这是一个很好的方法来实现,所以下面的改变会做得更好(我想是这样);)
的 views.py 强>
class InfoViews(ModelViewSet):
queryset = Info.objects.all()
serializer_class = InfoSerializer
lookup_field = 'id'
的 serializer.py 强>
import hashlib
class InfoSerializer(serializers.ModelSerializer):
created_time = serializers.DateTimeField(required=False)
def set_password(self, raw_pwd):
md5 = hashlib.md5()
md5.update(raw_pwd.encode('utf-8'))
return md5.hexdigest()
class Meta:
model = Info
fields = '__all__'
def create(self, validated_data):
validated_data['password'] = self.set_password(validated_data['password'])
return super().create(validated_data)
的更新强>
序列化程序的替代create()
,
def create(self, validated_data):
validated_data['password'] = self.set_password(validated_data['password'])
user = Info.objects.create(
email=validated_data['email'],
username=validated_data['username'],
password=validated_data['password']
)
# you can avoid large number of assignment statements (as above) by simply calling "super()" method
return user