"<Model> with this <field> already exist" on PUT call - Django REST Framework
<p>I'm doing a HTTP PUT call to update the data of an object with a <strong>nested relationship</strong>, and I'm met by the following error:</p>
<blockquote>
<p>HTTP 400 Bad Request</p>
<p>&quot;AttributeChoice with this slug already exists.&quot;</p>
</blockquote>
<p>The reason why this is confusing is because I'm doing a <code>HTTP PUT</code> call and I expect it to treat it as an <code>UPDATE</code> and not a <code>CREATE</code>.</p>
<p>My Models look like this:</p>
<pre><code>class Attribute(models.Model):
    name        = models.CharField(max_length=100)
    text_input  = models.BooleanField(default=False)
    slug        = models.SlugField(unique=True)

class AttributeChoice(models.Model):
    attribute   = models.ForeignKey(Attribute)
    value       = models.CharField(max_length=100)
    slug        = models.SlugField(unique=True)
</code></pre>
<p>My Serializers look like this:</p>
<pre><code>class AttributeChoiceSerializer(serializers.ModelSerializer):
    class Meta:
        model = AttributeChoice
        fields = '__all__'
        extra_kwargs = {'id': {'read_only': False}}

class AttributeSerializer(serializers.ModelSerializer):
    attributechoice_set = AttributeChoiceSerializer(many=True)
    class Meta:
        model = Attribute
        fields = ('id', 'name', 'text_input', 'slug', 'attributechoice_set')

    def update(self, instance, validated_data):
        choice_data = validated_data.pop('attributechoice_set') 
        for choice in choice_data:
        
            # If id is within the call, then update the object with matching id
            if 'id' in choice:
                try:
                    choice_obj = AttributeChoice.objects.get(pk=choice['id'])
                    choice_obj.value = choice['value']
                    choice_obj.slug = choice['slug']
                    choice_obj.attribute = instance
                # If ID is not found, then create a new object
                except AttributeChoice.DoesNotExist:
                    choice_obj = AttributeChoice(**choice)
            # If no ID within the call, create a new object.
            else:
                choice_obj = AttributeChoice(**choice)

            choice_obj.save()

        return instance
</code></pre>
<p><strong>Debug:</strong>
Even if I remove the <code>update()</code> function, I still get the same error. I believe the error is reported from when <code>.is_valid()</code> is called in the ViewSet. So it's not the <code>update()</code> that causes it.</p>
<p>Also, if I remove <code>attributechoice_set = AttributeChoiceSerializer(many=True)</code> and just include the <code>attributechoice_set</code> in the <code>fields = ()</code>, the error disappears, but I need that line for the rest of the code to work.</p>