我一直试图改变Django REST框架管理面板的表单字段的价值,并且出于某种原因,改变永远不会发生。我有下面的序列化器
class SomeView(ModelViewSet):
queryset = MyModel.objects.all()
serializer_class = MyModelSerializer
# I Want to override this and change the POST data
def perform_create(self, serializer):
user = self.request.user.id
# this was a form field where I manually entered the user ID
# I now want it to default to the logged in user
serializer.data['user'] = user
# This returns the original user that was entered into the form field
print serializer.data
我使用dir()
检查了serializer.data,它只是一个python词典,因此我无法弄清楚为什么我无法修改该值。作为测试,我尝试添加额外的值,但这不起作用
# this doesnt work
serializer.data['some_new_field'] = 'test'
修改
另一方面,我可以复制数据并对其进行编辑
fake_data = serializer.data.copy()
fake_data['old_value'] = 'new value'
但是,它始终无法验证
serializer = MyModelSerializer(data=fake_data)
serializer.is_valid() # returns false
编辑编辑:
好的,因此验证错误是由Django返回SimpleLazyObject引起的。当我执行数据副本时,现在一切正常,但我真的很好奇为什么我不能直接编辑serializer.data
而不复制它。这个问题现在已经解决了,但如果有人能够仅仅因为好奇而提供有关问题的见解,那就太棒了。
答案 0 :(得分:7)
我用dir()检查了serializer.data,它只是一个python词典,所以我无法弄清楚为什么我不能修改这个值。
虽然从Serializer.data
返回的值确实是字典,但Serializer.data
不是简单的实例变量。
如果你看rest_framework/serializers.py
:
class Serializer(BaseSerializer):
# [...]
@property
def data(self):
ret = super(Serializer, self).data
return ReturnDict(ret, serializer=self)
ReturnDict
继承自OrderedDict
,但每次访问Serializer.data
时,您仍会获得新字典。
真实的数据位于_data
,但正如下划线所示,您可能不想修改它,因为它不是公开的。这些值由Serializer.to_representation()
填充,您可以在视图集上覆盖。
至于第二部分:ModelViewSet
定义get_serializer()
,使用请求POST数据调用以创建要修改的序列化程序。我建议尝试在创建序列化程序之前更改输入数据。