Django - How to properly receive multi-image upload via POST?

Viewed 44

I have this view.py and models.py files below that supposed to support uploading multiple images. I have tests that work and do generate images, but the images are attached to the POST request as a ByteIO format. I'd like this endpoint to receive a POST request from a React Native front-end containing an image and I don't know if it'll be in ByteIO format. I tried sending an image in byte format by doing

    with open('./media/test.png', 'rb') as f:
        image = f.read()

But it turns the QueryDict that is request.data into an immutable dict for some reason. As you can see below that's an issue as I do change it. Is the way I've implemented it correct for receiving multiple image uploads from React Native?

view.py

class PostView(APIView):

    def post(self, request):
        post_body = request.data['body']
        hash_tags_list = extract_hashtags(post_body)
        hash_tags = [HashTag.objects.get_or_create(
            hash_tag=ht)[0].hash_tag for ht in hash_tags_list]
        request.data['hash_tags'] = hash_tags
        serializer = PostSerializer(data=request.data)
        if serializer.is_valid():
            try:
                post_obj = serializer.save()

                if 'images' in request.FILES.keys():
                    for img in request.FILES.getlist('images'):
                        Photo.objects.create(post_id=post_obj, image=img)

            except django.db.utils.InternalError as e:
                return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)

            return Response(serializer.data, status=status.HTTP_201_CREATED)
        else:
            return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)

models.py

class Post(AbstractBaseModel):
    creator_id = models.ForeignKey(
        User, on_delete=models.CASCADE, related_name="post_creator_id")
    goal_id = models.ForeignKey(Goal, on_delete=models.CASCADE)
    body = models.CharField(max_length=511, validators=[MinLengthValidator(5)])
    hash_tags = models.ManyToManyField(HashTag)


def directory_path(instance, filename):
    _, extension = os.path.splitext(filename)
    return 'images/user_{0}/{1}'.format(instance.post_id.creator_id.uuid, str(instance.uuid) + extension)


class Photo(AbstractBaseModel):
    post_id = models.ForeignKey(Post, on_delete=models.CASCADE)
    image = models.ImageField(upload_to=directory_path)
0 Answers
Related