Django 如何在SlugRelatedField中使用相关字段?
我有以下结构Django 如何在SlugRelatedField中使用相关字段?,django,django-rest-framework,Django,Django Rest Framework,我有以下结构 class State(models.Model): label = models.CharField(max_length=128) .... class ReviewState(models.Model): state = models.ForeignKey(State, on_delete=models.CASCADE) ... class MySerializer(serializers.HyperlinkedModelSerialize
class State(models.Model):
label = models.CharField(max_length=128)
....
class ReviewState(models.Model):
state = models.ForeignKey(State, on_delete=models.CASCADE)
...
class MySerializer(serializers.HyperlinkedModelSerializer):
state = serializers.SlugRelatedField(queryset=ReviewState.objects.all(), slug_field='state__label', required=False)
class Meta:
model = MyModel
fields = [
'id',
'state', # this points to a ReviewState object
....
]
我尝试使用状态对象的标签作为字段。但djangorestframework似乎不喜欢使用\uuuu
查找slug字段。有可能这样做吗?如果是:
class MySerializer(serializers.HyperlinkedModelSerializer):
state = serializers.SlugRelatedField(queryset=State.objects.all(), slug_field='label', required=False)
这不会有问题,但我正在尝试使用ReviewState。我还试图避免使用ReviewStateSerializer,因为生成的json如下所示
{...
'state': {'state': 'Pending'}}
}
这个问题很有趣,而且说得很好 使用
SlugRelatedField('state\uu label',queryset=…)
可以很好地工作,但有一点需要注意:它只是调用queryset.get(state\uu label=“x”)
如果没有精确的匹配,会出现哪些错误
1)编写自定义字段?
从SlugRelatedField
继承并重写到\u internal\u value()
,可以通过调用.first()
而不是.get()
,或者调用您需要的任何其他逻辑
2)重新评估这种关系,也许是一对一?选择字段?
我对这一切是如何工作的有点困惑,因为您可以使用状态
=>查看状态
“1对多”。当出现多个匹配时,默认查找(如果不执行#1)将抛出错误
也许这是模型的一对一情况?也许ReviewState可以使用选项字段
而不是状态表
也许“标签”可以是状态
表的主键,也可以是段塞字段
,而不是非唯一的字符字段
3)为列表
和创建
案例编写不同的序列化程序
DRF并没有为我们提供一种内置的方法来实现这一点,但这种依赖“一个序列化程序来完成所有工作”的做法是我看到的许多问题的原因。对于不同的情况,如果没有不同的序列化程序,就很难得到您想要的。使用自己的mixin来实现这一点并不难,但下面是一个使用覆盖的示例:
from rest_framework import serializers as s
class MyCreateSerializer(s.ModelSerializer):
state = s.SlugRelatedField(...)
...
class MyListSerializer(s.ModelSerializer):
# use dotted notation, serializers read *object* attributes
state = s.CharField(source="state.state.label")
...
class MyViewSet(ModelViewSet):
queryset = MyModel.objects.select_related('state__state')
...
def get_serializer_class(self):
if self.action == "create":
return MyCreateSerializer
else:
return MyListSerializer
双下划线符号对我不起作用。我有一个TeamMember模型,它是用户模型(一对一)的概要扩展。团队成员的自然密钥是“用户用户名”(这很好)。我现在有了一个任务模型,它的ForeignKey字段是team_member(到TeamMember模型)。在序列化程序中,我使用slug\u field=“user\uu username”定义了SlugRelatedField(还尝试了“user.username”和“username”),但我得到了“'TeamMember'对象没有属性‘user\uu username”。”