How do I edit a form with Imagefield without updating Photo?

Viewed 35

I've tried numerous ways to fix this error and I can't seem to solve it. I have a form for a user profile, the profile automatically gets created when the user registers and they receive a default photo until they upload their own. When they upload the photo it works just fine including the profile information. However, if they only edit the profile information after already having their own profile photo and do not change the photo I get a MultiValueDictKeyError and the exception value for 'image'

below is my views..


    def editProfile(request):
        if 'user_id' not in request.session:
            return redirect('/')
        user = User.objects.get(id=request.session['user_id'])
        context = {
            'user': user,
        }
        return render(request, 'editProfile.html', context)
    
    # updates edited information on profile and updates new image photo.
    
    
    def updateProfile(request, user_id):
        userProfile = User.objects.get(id=request.session['user_id'])
        userProfile.profile.location = request.POST['location']
        userProfile.profile.favorite = request.POST['favorite']
        userProfile.profile.about = request.POST['about']
        userProfile.profile.image = request.FILES['image']
        userProfile.save()
    
        return redirect(f'/userProfile')

this is my models:


   class User(models.Model):
       first_name = models.CharField(max_length=45, null=True)
       last_name = models.CharField(max_length=45, null=True)
       username = models.CharField(max_length=255, null=True)
       email = models.EmailField(unique=True)
       password = models.CharField(max_length=45)
       confirm_pw = models.CharField(max_length=45)
       objects = UserManager()
       date_created = models.DateTimeField(auto_now_add=True)
       date_updated = models.DateTimeField(auto_now=True)
   
       def __str__(self):
           return self.username
   
   
   class Profile(models.Model):
       user = models.OneToOneField(User, unique=True, on_delete=models.CASCADE)
       location = models.CharField(max_length=45, null=True)
       favorite = models.CharField(max_length=255, null=True)
       about = models.TextField(null=True)
       image = models.ImageField(default='default.jpg', upload_to='profile_pics', blank=True)
   
       def __str__(self):
           return f'{self.user.username} Profile'

the html:


     <Section>
                <label for='image'> <a style="cursor: pointer;"><em class="fa fa-upload"></em> Change Profile Image</a></label> 
                <input type='file' name='image' id='profilePic' class='form-control' style='display:none;' >
            </Section>
            </div>
            <button id='btn' type='submit'> Update </button>

Everything else works just fine, The photo saves to the database when a user adds a photo and is rendering in all required places. I appreciate those who can help thank you.

2 Answers

If you're using a regular HTML <form> and not the one that Django generates, have a look at the value of the name attribute on the <img> tag.

When you execute this line:

userProfile.profile.image = request.FILES['image']

The key for request.FILES should be the same as the name for the <img> tag. Otherwise you'll get a MultiValueDictKeyError. Dont use image as the key just because that was what you have named it in the model.

If you are using a ModelForm, then this is not an issue, because Django automatically assigns names to fields based on their names in their models.

It was simply just an if statement before userProfile.profile.image

``` if 'image' in request.FILES
userProfile.profile.image = request.FILES['image']```

so if anyone else has this issue I hope this helps. I was stuck on it for 2 days.

Related