无法编辑- Django

rvpgvaaj  于 2023-03-09  发布在  Go
关注(0)|答案(1)|浏览(106)

我在创建一个简单的REST API
目前,分组的结果是:
我现在的设备结果

[
    {
        "id": "8079bf12-bb58-4ea0-a810-58a223d84be7",
        "name": "Cozinha"
    }
]

我的models.py

from uuid import uuid4
from django.db import models

class Options(models.Model):
    id = models.UUIDField(primary_key=True, default=uuid4, editable=False)
    name = models.CharField(max_length=255)
    identifier = models.CharField(max_length=255)

    class Meta:
        ordering = ['name']

    def __str__(self):
        return self.name

class Groups(models.Model):
    id = models.UUIDField(primary_key=True, default=uuid4, editable=False)
    name = models.CharField(max_length=255)

    class Meta:
        ordering = ['name']

    def __str__(self):
        return self.name

class Devices(models.Model):
    id = models.UUIDField(primary_key=True, default=uuid4, editable=False)
    name = models.CharField(max_length=255)
    identifier = models.CharField(max_length=255)
    options = models.ManyToManyField(Options)
    group = models.ForeignKey(Groups, on_delete=models.CASCADE, default="")

视图集

from rest_framework import viewsets
from devices.api import serializers
from devices import models

class DevicesViewsets(viewsets.ModelViewSet):
    serializer_class = serializers.DevicesSerializer
    queryset = models.Devices.objects.all()

    def perform_create(self, serializer):
        serializer.save()
    
class OptionsViewsets(viewsets.ModelViewSet):
    serializer_class = serializers.OptionsSerializer
    queryset = models.Options.objects.all()

class GroupsViewsets(viewsets.ModelViewSet):
    serializer_class = serializers.GroupsSerializer
    queryset = models.Groups.objects.all()

串化器

from rest_framework import serializers
from devices import models

class OptionsSerializer(serializers.ModelSerializer):
    class Meta:
        model = models.Options
        fields = '__all__'

class GroupsSerializer(serializers.ModelSerializer):
    class Meta:
        model = models.Groups
        fields = '__all__'

class DevicesSerializer(serializers.ModelSerializer):
    group = GroupsSerializer()
    options = OptionsSerializer(many=True)

    class Meta:
        model = models.Devices
        fields = '__all__'
    
    def create(self, validated_data):
        group_data = validated_data.pop('group')
        options_data = validated_data.pop('options')
        group, _ = models.Groups.objects.get_or_create(**group_data)
        options = [models.Options.objects.create(**option_data) for option_data in options_data]
        device = models.Devices.objects.create(group=group, **validated_data)
        device.options.set(options)
        return device

我向“http://localhost:8000/groups/”发送POST以编辑组

{
        "id": "8079bf12-bb58-4ea0-a810-58a223d84be7",
        "name": "Cozinha 123"
 }

但是这会在表中创建一个新项,而不是编辑带有这个id的行,我知道我需要在序列化器中添加一些东西,但是我还不了解,我还在学习中

我尝试了互联网上的一些解决方案,但都不成功,有人能帮我吗?

e7arh2l6

e7arh2l61#

TLDR

简单的答案是,您可以调用PATCH或PUT来更新Groups模型,而不是调用POST方法,原因并不完全在于POST方法本身,而是视图集如何处理POST、PUT和PATCH。

详细答案

创建新实体的原因不是因为您使用了POST方法,而是因为泛型视图集处理POST方法的方式。
如果你看一下CreateModelMixin的源代码,我们可以看到在序列化器初始化过程中,只有请求数据被传递给它。所以当序列化器调用它的保存方法时,它不知道那个示例是否已经存在,link for reference和视图集使用这个create函数来处理post请求。
如果你看一下UpdateModelMixin的源代码,你会发现在序列化器初始化的过程中也传递了示例(正在被更新),这个update函数在PATCH和PUT的过程中被调用。
如果你是死在使用后更新你的模型(你不应该),你总是可以

  • 更新模型的保存方法。
  • 创建您自己的自定义视图集

相关问题