Python Django Rest框架嵌套可写字段混合drf\u可写\u嵌套

Python Django Rest框架嵌套可写字段混合drf\u可写\u嵌套,python,django,django-rest-framework,django-views,mixins,Python,Django,Django Rest Framework,Django Views,Mixins,我当前正尝试使用来执行当前db架构的更新和创建,但我遇到了以下错误: .create方法默认情况下不支持可写嵌套字段。 为序列化程序trvl.serializers.StatisticsSerializer编写显式.create方法,或在嵌套序列化程序字段上设置read_only=True 主要型号: class Statistics(models.Model): """Instance: {airport_code, carrier_code, month, year, flight,

我当前正尝试使用来执行当前db架构的更新和创建,但我遇到了以下错误:

.create方法默认情况下不支持可写嵌套字段。 为序列化程序trvl.serializers.StatisticsSerializer编写显式.create方法,或在嵌套序列化程序字段上设置read_only=True

主要型号:

class Statistics(models.Model):
    """Instance: {airport_code, carrier_code, month, year, flight, delay_count, delay_time}"""
    airport = models.ForeignKey(Airport, on_delete=models.CASCADE)
    carrier = models.ForeignKey(Carrier, on_delete=models.CASCADE)
    month = models.IntegerField(
        validators=[MinValueValidator(1), MaxValueValidator(12)])
    year = models.IntegerField(validators=[MinValueValidator(
        1900, message='Invalid year: year < 1900.')])
    # statistics linkage
    flight = models.ForeignKey(
        FlightStatistics, on_delete=models.DO_NOTHING)
    delay_count = models.ForeignKey(
        DelayCountStatistics, on_delete=models.DO_NOTHING)
    delay_time = models.ForeignKey(
        DelayTimeStatistics, on_delete=models.DO_NOTHING)

    # Guaranteeing the "primary key" of the tuple
    class Meta:
        unique_together = ('airport', 'carrier', 'month', 'year')

    def __str__(self):
        return '%s_%s_%s_%s' % (self.airport, self.carrier, self.month, self.year)
视图:

有效载荷示例:

{
    "airport": "ATL",
    "carrier": "AA",
    "month": 7,
    "year": 2008,
    "flight": {
        "cancelled": 2,
        "on_time": 30,
        "total": 100l,
        "delayed": 303,
        "diverted": 121
    },
    "delaytime": {
        "late_aircraft": 21,
        "weather": 2121,
        "security": 2121,
        "national_aviation_system": 21212,
        "carrier": 22
    },
    "delaycount": {
        "late_aircraft": 1212,
        "weather": 1212,
        "security": 1221,
        "national_aviation_system": 1221,
        "carrier": 1212
    }
}
此视图的Django HTML表单:

您是否尝试执行错误消息中的建议

class StatisticsSerializer(WritableNestedModelSerializer):
    # Using nest serializer for handling get and post
    # Using serializers instead of the model fields
    flight = FlightStatisticsSerializer(read_only=True)         # <--
    delaycount = DelayCountStatisticsSerializer(read_only=True) # <--
    delaytime = DelayTimeStatisticsSerializer(read_only=True)   # <--

    class Meta:
        model = models.Statistics
        fields = ('airport', 'carrier', 'month', 'year',
                  'flight', 'delaytime', 'delaycount')
更新

我决定实现自己的嵌套序列化程序:

class StatisticsSerializer(WritableNestedModelSerializer):
    # Using nest serializer for handling get and post
    # Using serializers instead of the model fields
    flight = FlightStatisticsSerializer()
    delaycount = DelayCountStatisticsSerializer()
    delaytime = DelayTimeStatisticsSerializer()

    class Meta:
        model = models.Statistics
        fields = ('airport', 'carrier', 'month', 'year',
                  'flight', 'delaytime', 'delaycount')
class StatisticsSerializer(serializers.ModelSerializer):
    # Using nest serializer for handling get and post
    # Using serializers instead of the model fields
    url = serializers.HyperlinkedIdentityField(view_name='statistics-detail')
    flight = FlightStatisticsSerializer(allow_null=True)
    delay_count = DelayCountStatisticsSerializer(allow_null=True)
    delay_time = DelayTimeStatisticsSerializer(allow_null=True)

    class Meta:
        model = models.Statistics
        fields = ('url','airport', 'carrier', 'month', 'year',
                  'flight', 'delay_time', 'delay_count')

    def create(self, validated_data):
        flight_statistics = models.FlightStatistics.objects.create(
            **(validated_data.pop('flight')))
        delay_time_statistics = models.DelayTimeStatistics.objects.create(
            **(validated_data.pop('delay_time')))
        delay_count_statistics = models.DelayCountStatistics.objects.create(
            **(validated_data.pop('delay_count')))
        print(flight_statistics)

        statistics = models.Statistics.objects.create(**validated_data, flight=flight_statistics,
                                                      delay_time=delay_time_statistics, delay_count=delay_count_statistics)

        return statistics

    def update(self, instance, validated_data):
        flight, _ = models.FlightStatistics.objects.update_or_create(id=instance.flight.id, defaults=validated_data.pop('flight'))
        delay_time, _ = models.DelayTimeStatistics.objects.update_or_create(id=instance.delay_time.id, defaults=validated_data.pop('delay_time'))
        delay_count, _ = models.DelayCountStatistics.objects.update_or_create(id=instance.delay_count.id, defaults=validated_data.pop('delay_count'))
        new_instance, _ = models.Statistics.objects.update_or_create(id=instance.id, defaults=validated_data)

        return new_instance
class StatisticsSerializer(serializers.ModelSerializer):
    # Using nest serializer for handling get and post
    # Using serializers instead of the model fields
    url = serializers.HyperlinkedIdentityField(view_name='statistics-detail')
    flight = FlightStatisticsSerializer(allow_null=True)
    delay_count = DelayCountStatisticsSerializer(allow_null=True)
    delay_time = DelayTimeStatisticsSerializer(allow_null=True)

    class Meta:
        model = models.Statistics
        fields = ('url','airport', 'carrier', 'month', 'year',
                  'flight', 'delay_time', 'delay_count')

    def create(self, validated_data):
        flight_statistics = models.FlightStatistics.objects.create(
            **(validated_data.pop('flight')))
        delay_time_statistics = models.DelayTimeStatistics.objects.create(
            **(validated_data.pop('delay_time')))
        delay_count_statistics = models.DelayCountStatistics.objects.create(
            **(validated_data.pop('delay_count')))
        print(flight_statistics)

        statistics = models.Statistics.objects.create(**validated_data, flight=flight_statistics,
                                                      delay_time=delay_time_statistics, delay_count=delay_count_statistics)

        return statistics

    def update(self, instance, validated_data):
        flight, _ = models.FlightStatistics.objects.update_or_create(id=instance.flight.id, defaults=validated_data.pop('flight'))
        delay_time, _ = models.DelayTimeStatistics.objects.update_or_create(id=instance.delay_time.id, defaults=validated_data.pop('delay_time'))
        delay_count, _ = models.DelayCountStatistics.objects.update_or_create(id=instance.delay_count.id, defaults=validated_data.pop('delay_count'))
        new_instance, _ = models.Statistics.objects.update_or_create(id=instance.id, defaults=validated_data)

        return new_instance