How to POST nested Data that contains a File with Django Rest Framework?

Viewed 680

I've been trying to post a nested object with one file and some data via django drf for a few days now. The goal is to create a story together with some images, one of these images being the title image of the story. Basically, I am able to post the story successfully with postman (see picture below). However, when I use my react js frontend for sending, I am not able to create the form data in a way that Django understands it. Django always returns the error story_media field is required. I suppose this is because Django does not understand the incoming data correctly.

class Story (models.Model):
    title = models.CharField(max_length=100,blank=True)
    author = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE, null=True)

class Story_Media (models.Model):
    story = models.ForeignKey(Story,on_delete=models.CASCADE, null=True, related_name = 'story_media', related_query_name = 'story_media')
    file = models.FileField(upload_to='story_media/', null=True)
    isTitlePicture = models.BooleanField(blank=False, null=True) 
# Story  Story Media Serializer
class Story_Media_Serializer (serializers.ModelSerializer):

    class Meta:
        model = Story_Media
        fields =  ('id','file','isTitlePicture',)


# Story  Serializer
class StoryCreateUpdateSerializer (serializers.ModelSerializer):
    story_media = Story_Media_Serializer(many=True)

    class Meta:
        model = Story
        fields =  ('title','story_media',)

    def create(self, validated_data):
        current_user = self.context["request"].user
        story_media = validated_data.pop('story_media')
        
        story_instance = Story.objects.create(author=current_user, **validated_data)

        for story_media_data in story_media:
            Story_Media.objects.create(**story_media_data, story=story_instance)

# Story  Create View Set
class StoryCreateUpdateViewSet(viewsets.ModelViewSet):
    serializer_class = StoryCreateUpdateSerializer
    queryset = Story.objects.all()

This is how i create my form data in react js. In this example story_media_array contains only a single image object.

    // array that stores all the images
    let story_media_array = [];
 
    // single image object
    var image_object ={
     file: this.state.file[0], // some file
     isTitlePicture: "True"
    }
    
    // push image object in array
    story_media.push(image_object);

    let formdata = new FormData();
    
    // title
    formdata.append('title', "Test")
    // image
    formData.append('story_media', story_media_array)

However, as I wrote above, I am not able to create the form with the above code, it returns 'story_media field is required'. But it works with postman. I'm a bit lost at the moment, so I'm glad for any help.

enter image description here

0 Answers
Related