我有一对父子模型/序列化/视图集 - 工具和工具输入:
models.py:
class Tool(models.Model):
id = models.CharField(max_length=10000, primary_key=True, default=uuid.uuid4, editable=False)
base_command = jsonfield.JSONField(verbose_name="baseCommand")
class ToolInput(models.Model):
tool = models.ForeignKey(Tool, related_name="inputs", on_delete=models.CASCADE)
id = models.CharField(max_length=10000, primary_key=True)
label = models.CharField(max_length=10000, null=True, blank=True)
description = models.CharField(max_length=10000, null=True, blank=True)
type = jsonfield.JSONField()
serializers.py
class ToolSerializer(WritableNestedModelSerializerMixin,
serializers.HyperlinkedModelSerializer):
id = serializers.CharField()
inputs = ToolInputSerializer(many=True)
baseCommand = serializers.JSONField(source="base_command")
class Meta:
model = Tool
fields = ('id', 'inputs', 'baseCommand')
class ToolInputSerializer(WritableNestedModelSerializerMixin,
serializers.HyperlinkedModelSerializer):
class Meta:
model = ToolInput
fields = ('id', 'label', 'description', 'type')
views.py:
class ToolViewSet(viewsets.ModelViewSet):
queryset = Tool.objects.all()
lookup_field = 'id'
serializer_class = ToolSerializer
class ToolInputViewSet(viewsets.ModelViewSet):
lookup_field = 'id'
serializer_class = ToolInputSerializer
def get_queryset(self):
tool_id = self.kwargs['tool_id']
return ToolInput.objects.filter(tool_id=tool_id)
def get_serializer_context(self):
context = super(ToolInputViewSet, self).get_serializer_context()
context["tool"] = Tool.objects.get(id=self.kwargs['tool_id'])
return context
如您所见,我使用ToolInputSerializer
作为ToolInputViewSet
的独立序列化程序和ToolViewSet
中的嵌套序列化程序。
当ToolInputSerializer
用作ToolViewSet
中的嵌套序列化程序时,它会以某种方式自动接收tool
参数的值,并将其分配给ToolInput
模型的tool
领域(顺便说一下,从架构的角度来看,我认为这是一个完全错误的行为 - tool
上根本没有ToolInputSerializer
这样的领域,而DRF正在填补相应模型的领域 - 它应该拯救IMO出现Field Does Not Exist
错误,并且至少需要序列化程序上的只写字段tool
。
但是当我在ToolInputViewSet
中将其用作独立序列化程序时,我想将ToolInput
模型的tool
字段的值分配给Tool
实例,由{tool_id
确定1}} url参数,由ToolInputViewSet
在kwargs中接收。
我正在尝试使用序列化程序上下文传递该字段的值,覆盖ToolInputViewSet.get_serializer_context()
方法,但它无法正常工作。怎么做得好?
旁注:我已经厌倦了DRF的上下文处理的混乱和不一致,非均匀的自动化,这些处理可以穿透Model-Serializer-Field-View架构的各个层次。它确实需要更明确和可定制。
答案 0 :(得分:0)
至于背景,我仍然不知道如何使其发挥作用。
至于嵌套序列化程序的工作方式,这很糟糕:正如您所看到的,我从自定义WritableNestedModelSerializerMixin
继承了所有ViewSet,我已覆盖create()
和{{1使用嵌套数据结构的方法,所以这是我的修补。
因此,作为一种解决方法,我创建了一个单独的update()
并修改了ToolInputViewSet,将缺少的StandaldonToolInputSerializer
字段添加到序列化程序,并使用工具参考自动修补tool
:
request.data
serializers.py
class StandaloneToolInputSerializer(serializers.HyperlinkedModelSerializer):
tool = serializers.PrimaryKeyRelatedField(
write_only=True,
many=False,
queryset=Tool.objects.all()
)
inputBinding = serializers.JSONField(source="input_binding")
class Meta:
model = ToolInput
fields = ('id', 'tool', 'label', 'description', 'type', 'inputBinding')
views.py