Search code examples
pythondjangosocial-media

Image field gets cleared off in django when i submit it


I am trying to create a social media app similar to Instagram however for some reason when I load the picture into the image field and submit it, the image gets cleared, and says that the field is required.

Before submission

After submission

In Django, the code for views.py

@login_required
def new_post(request):
    if request.method == 'POST':
        form = CreateNewPost(request.POST)
        if form.is_valid():
            messages.success(request, "Post has been created")
            form.save()
            return redirect('home')
    else:
        form = CreateNewPost()
    return render (request, "posts/post_form.html", {"form":form})

I have kept the default user to none temporarily as it insisted me to choose one when I created the models initially. Is that the reason for this problem? If so how do I get rid of it.

Html code...

    <form method="POST" enctype="multipart/form-data">
        {% csrf_token %}
        <fieldset class="form-group">
            <legend class="border-bottom mb-4">Add a Post!</legend>
            {{ form | crispy }}
        </fieldset>
        <div class="form-group">
            <button class="btn btn-outline-info" type="submit">Post</button>                
        </div>
    </form>

models.py

class Post(models.Model):
    image = models.ImageField(upload_to='post_images')
    caption = models.CharField(blank=True, max_length=254)
    date_posted = models.DateTimeField(auto_now_add=timezone.now)
    author = models.ForeignKey(User, on_delete = models.CASCADE)

    def save(self):
        super().save()
        img = Image.open(self.image.path)
        width, height = img.size
        ratio = width/height
        if img.height > 500:
            outputsize = (500, (height/ratio))
            img.thumbnail(outputsize)
            img.save(self.image.path)

forms.py

class CreateNewPost(forms.ModelForm):
    class Meta:
        model = Post
        fields = ["image","caption"]

and just in case, urls.py

urlpatterns = [
    path('', views.home, name='home'),
    path('new_post/', views.new_post, name="new_post"),
]

I have also tried using class-based views which gave me the same error


Solution

  • You need to pass request.FILES [Django-doc] to the form, this is a dictionary-like object that contains the UploadedFile objects for the files uploaded:

    @login_required
    def new_post(request):
        if request.method == 'POST':
            form = CreateNewPost(request.POST, request.FILES)
            if form.is_valid():
                form.instance.author = request.user
                form.save()
                messages.success(request, 'Post has been created')
                return redirect('home')
        else:
            form = CreateNewPost()
        return render (request, 'posts/post_form.html', {'form':form})

    Note: It is normally better to make use of the settings.AUTH_USER_MODEL [Django-doc] to refer to the user model, than to use the User model [Django-doc] directly. For more information you can see the referencing the User model section of the documentation.