django rest framework 多个外键序列化
django rest framework multiple foreign keys serializing
一开始看起来很简单,现在一头雾水。我写了数据结构,现在正在努力获得它。到目前为止我有:
class Area(models.Model):
name = models.CharField(max_length=128)
...
class Category(models.Model):
name = models.CharField(max_length=128)
....
class Venue(models.Model):
name = models.CharField(max_length=128)
category = models.ForeignKey(Category, related_name='venues')
area = models.ForeignKey(Area, related_name='venues')
我需要基于 Area
pk 获取其中包含场地的类别。是否可以使用 django rest 框架这样做?结果应该类似于:
{
"pk": 1,
"name": "London",
"categories": [
{
"pk": 1,
"name": "Bars",
"venues": [
{
"pk": 1,
"name": "Cool bar"
},
{
"pk": 2,
"name": "Cooler bar"
},
{
"pk": 3,
"name": "Coldest bar"
},
]
}
]
}
理想情况下我需要这样的东西:
class VenueSerializer(serializers.ModelSerializer):
.....
class CategorySerializer(serializers.ModelSerializer):
venues = VenueSerializer(read_only=True, many=True)
class Meta:
model = Category
fields = ('pk', 'name', 'venues', )
class AreaSerializer(serializers.ModelSerializer):
categories = CategorySerializer(read_only=True, many=True)
class Meta:
model = Area
fields = ('pk', 'name', 'categories', )
但这当然行不通,因为 Area
与 Category
没有 直接 相关。所以我的问题是,是否可以在不改变数据结构的情况下做到这一点?
有点难看,但是如果你设置在对象模型上,你可以使用DRF's SerializerMethodField。
您的 Area 序列化程序将类似于:
class AreaSerializer(serializers.ModelSerializer):
categories = SerializerMethodField()
def get_categories(self, obj):
# this will find all categories with a venue in given area
categories = Category.objects.filter(venues__area=obj)
serializer = CategorySerializer(categories, many=True)
return serializer.data
class Meta:
model = Area
fields = ('pk', 'name', 'categories', )
如果不进行优化,此结构将生成大量数据库查询。我建议使用 Django's prefetch_related 操作来减少冗余查询的数量。
一开始看起来很简单,现在一头雾水。我写了数据结构,现在正在努力获得它。到目前为止我有:
class Area(models.Model):
name = models.CharField(max_length=128)
...
class Category(models.Model):
name = models.CharField(max_length=128)
....
class Venue(models.Model):
name = models.CharField(max_length=128)
category = models.ForeignKey(Category, related_name='venues')
area = models.ForeignKey(Area, related_name='venues')
我需要基于 Area
pk 获取其中包含场地的类别。是否可以使用 django rest 框架这样做?结果应该类似于:
{
"pk": 1,
"name": "London",
"categories": [
{
"pk": 1,
"name": "Bars",
"venues": [
{
"pk": 1,
"name": "Cool bar"
},
{
"pk": 2,
"name": "Cooler bar"
},
{
"pk": 3,
"name": "Coldest bar"
},
]
}
]
}
理想情况下我需要这样的东西:
class VenueSerializer(serializers.ModelSerializer):
.....
class CategorySerializer(serializers.ModelSerializer):
venues = VenueSerializer(read_only=True, many=True)
class Meta:
model = Category
fields = ('pk', 'name', 'venues', )
class AreaSerializer(serializers.ModelSerializer):
categories = CategorySerializer(read_only=True, many=True)
class Meta:
model = Area
fields = ('pk', 'name', 'categories', )
但这当然行不通,因为 Area
与 Category
没有 直接 相关。所以我的问题是,是否可以在不改变数据结构的情况下做到这一点?
有点难看,但是如果你设置在对象模型上,你可以使用DRF's SerializerMethodField。
您的 Area 序列化程序将类似于:
class AreaSerializer(serializers.ModelSerializer):
categories = SerializerMethodField()
def get_categories(self, obj):
# this will find all categories with a venue in given area
categories = Category.objects.filter(venues__area=obj)
serializer = CategorySerializer(categories, many=True)
return serializer.data
class Meta:
model = Area
fields = ('pk', 'name', 'categories', )
如果不进行优化,此结构将生成大量数据库查询。我建议使用 Django's prefetch_related 操作来减少冗余查询的数量。