How to upload images to django REST api?

I’m creating a backend with DRF to upload json data that I later consume with a REACT frontend. By now it’s pretty standard and simple. My django model has an ImageField that is serialized as a string in the form of “http://127.0.0.1:8000/media/example-randomcharacters.png”.

(I define the media folder in the settings.py in django).

As expected, there is now a new file in the media folder with the name shown in the API, but when I try to get the image from the url it returns this:

Of course it can’t be used by react or any other external tool since the url doesn’t provide the image. What am I doing wrong?

Here is the django code:

models.py:

from django.db import models

class Project(models.Model):

"""Programming related project to show on my website. """

title = models.CharField(max_length=100)
description = models.TextField()
cover = models.ImageField()
link = models.URLField()
date_started = models.DateField(auto_now_add=True)
last_edited = models.DateField(auto_now=True)

def _str_(self):
    return self.title

serializers.py:

   from rest_framework import serializers
   from .models import Project


   class    ProjectSerializer(serializers.ModelSerializer):
    class Meta:
        model = Project
        fields = '__all__'

Answer

Most of the time I do this way,

In models.py add your image field

image = models.ImageField(null=True, blank=True)

Configure your project settings.py

STATIC_URL = '/static/'
MEDIA_URL = '/images/'

STATICFILES_DIRS = [
    BASE_DIR / 'static',
    BASE_DIR / 'frontend/build/static' #Unnecessary if you just need Backend Setup for Image Upload. It's just to Load React Project Static Files
]

MEDIA_ROOT = BASE_DIR / 'static/images'
STATIC_ROOT = BASE_DIR / 'staticfiles'

Configure project.urls.py

from django.conf import settings
from django.conf.urls.static import static
urlpatterns = [
    path('admin/', admin.site.urls), 
    #Your Project URL's....
]
urlpatterns += static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)#imp for what you want to achieve.
urlpatterns += static(settings.STATIC_URL, document_root=settings.STATIC_ROOT)

Now when you upload your image file from Admin it will be accessible with the following URL pattern HTTP://localhost:8000/images/ImageFileName.png

If you want to upload from outside Django you can follow this approach…

 @api_view(['POST'])
 def uploadImage(request):
    data = request.data

    obj_id = data['obj_id']
    obj= Project.objects.get(id=obj_id)

    obj.image = request.FILES.get('image')
    obj.save()

    return Response('Image was uploaded')

Associated URL

path('upload/', views.uploadImage, name="image-upload"),

Note: Highlight your concern regarding this solution in the comment. I’ll be happy to listen. Thanks!