【问题标题】:Custom serializer output for nested relationship field in DRF serializer classDRF 序列化程序类中嵌套关系字段的自定义序列化程序输出
【发布时间】:2015-08-18 17:34:10
【问题描述】:

在使用 Django-Rest-Framework(DRF) 开发 Web api 时我遇到了一点麻烦。

问题陈述

我有两个模型UserReview

models.py

# Consider User model as `django.contrib.auth.models.User`
from django.contrib.auth.models import User
from django.db import models

# Review model
class Review(models.Model):
    head = models.CharField()
    content = models.CharField()
    user = models.ForeignKey(User)
    is_deleted = models.BooleanField(default=False)

而且,我有两个这样的端点:

    /users/      - list of all users
    /users/<pk>  - detail of user
    /review/     - list of all reviews
    /review/<pk> - detail of review

我想要这样的输出:

# /users/ 
[
    {
        "url": "http://localhost:8000/users/1",
        "fisrt_name": "Adolf",
        "last_name": "Hitler",
        "email": "adolfhilter@xyz.com",
        "is_staff": false
        ........ # other fields
    },
    .........
    .........
]

# /reviews/
[
    {
        "url": "http://localhost:8000/reviews/1",
        "head": "Head of Review",
        "content": "Content of Review",
        "user": {
            "url": "http://localhost:8000/users/1",
            "first_name": "Adolf",
            "last_name": "Hitler"
        },
        "is_deleted": false
    },
    .........
    .........
]

我的解决方案

为了实现这种形式的输出,我创建了三个序列化程序类,一个是UserSerializer class,第二个是ReviewSerializer,第三个是 id ReviewUserSerializer。这些类如下:

serializers.py

from rest_framework import serializers
from .models import Review
from django.contrib.auth.models import User

class UserSerializer(serializers.HyperlinkedModelSerializer):
    class Meta:
        model = User
        fields = ('url', 'first_name', 'last_name', 'email', 'is_staff', .....)

class ReviewUserSerializer(serializers.HyperlinkedModelSerializer):
    class Meta:
        model = User
        fields = ('url', 'first_name', 'last_name')

class ReviewSerializer(serializers.HyperlinkedModelSerializer):
    user = ReviewUserSerializer()
    class Meta:
        model = Review
        fields = ('url', 'head', 'content', 'user')

所以,现在我想知道,

有没有其他方法可以避免为这些类型的情况创建一个额外的单独的序列化程序类(这里是ReviewUserSerializer)?

如果是,请建议我使用正确代码 sn-ps 的解决方案。

【问题讨论】:

    标签: python django serialization django-rest-framework


    【解决方案1】:

    您是否尝试过使用 SerializerMethodField?

    from rest_framework import serializers
    from .models import Review
    from django.contrib.auth.models import User
    
    class UserSerializer(serializers.HyperlinkedModelSerializer):
        class Meta:
            model = User
            fields = ('url', 'first_name', 'last_name', 'email', 'is_staff', .....)
    
    class ReviewSerializer(serializers.HyperlinkedModelSerializer):
        user = serializers.SerializerMethodField(read_only=True)
        class Meta:
            model = Review
            fields = ('url', 'head', 'content', 'user')
    
        def get_user(self, obj) :
            request = self.context['request']
            return {
              'url': reverse('user-detail',
                           kwargs={'pk': obj.user.id}, request=request),
              'first_name': obj.user.first_name,
              'last_name': obj.user.last_name,
            }
    

    【讨论】:

    • 我不知道它确实有效,但 url 字段在 get_user() 中无效。 AttributeError: 'User' 对象没有属性 'url'
    • 已更新。用户反向获取网址。传递请求允许它获取完整的 url。
    猜你喜欢
    • 1970-01-01
    • 2016-01-28
    • 2019-02-19
    • 1970-01-01
    • 2019-07-12
    • 1970-01-01
    • 2018-10-06
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多