dotty
dotty

Reputation: 41433

django MultiValueDictKeyError error, how do I deal with it

I'm trying to save a object to my database, but it's throwing a MultiValueDictKeyError error.

The problems lies within the form, the is_private is represented by a checkbox. If the check box is NOT selected, obviously nothing is passed. This is where the error gets chucked.

How do I properly deal with this exception, and catch it?

The line is

is_private = request.POST['is_private']

Upvotes: 261

Views: 468951

Answers (10)

Shah Wali
Shah Wali

Reputation: 27

1: use if request.POST in your function. 2: check html form method is equal .

def function_name(request):
    if request.POST:
       is_private = request.POST['is_private']

Upvotes: 1

bairavand
bairavand

Reputation: 357

This will insert NULL value if the name is not present in the request

name = request.data.get('name')

Upvotes: 0

Rubel Biswas
Rubel Biswas

Reputation: 1434

I got 'MultiValueDictKeyError' error while using ajax with Django. Just because of not putting '#' while selecting an element. Like this.

data:{ name : $('id_name').val(),},

then I put the '#' with the id and the problem is solved.

data:{ name : $('#id_name').val(),},

Upvotes: -1

TNT
TNT

Reputation: 490

For me, this error occurred in my django project because of the following:

  1. I inserted a new hyperlink in my home.html present in templates folder of my project as below:

    <input type="button" value="About" onclick="location.href='{% url 'about' %}'">

  2. In views.py, I had the following definitions of count and about:

   def count(request):
           fulltext = request.GET['fulltext']
           wordlist = fulltext.split()
           worddict = {}
           for word in wordlist:
               if word in worddict:
                   worddict[word] += 1
               else:
                   worddict[word] = 1
                   worddict = sorted(worddict.items(), key = operator.itemgetter(1),reverse=True)
           return render(request,'count.html', 'fulltext':fulltext,'count':len(wordlist),'worddict'::worddict})

   def about(request): 
       return render(request,"about.html")
  1. In urls.py, I had the following url patterns:
    urlpatterns = [
        path('admin/', admin.site.urls),
        path('',views.homepage,name="home"),
        path('eggs',views.eggs),
        path('count/',views.count,name="count"),
        path('about/',views.count,name="about"),
    ]

As can be seen in no. 3 above,in the last url pattern, I was incorrectly calling views.count whereas I needed to call views.about. This line fulltext = request.GET['fulltext'] in count function (which was mistakenly called because of wrong entry in urlpatterns) of views.py threw the multivaluedictkeyerror exception.

Then I changed the last url pattern in urls.py to the correct one i.e. path('about/',views.about,name="about"), and everything worked fine.

Apparently, in general a newbie programmer in django can make the mistake I made of wrongly calling another view function for a url, which might be expecting different set of parameters or passing different set of objects in its render call, rather than the intended behavior.

Hope this helps some newbie programmer to django.

Upvotes: 5

Leo
Leo

Reputation: 469

Another thing to remember is that request.POST['keyword'] refers to the element identified by the specified html name attribute keyword.

So, if your form is:

<form action="/login/" method="POST">
  <input type="text" name="keyword" placeholder="Search query">
  <input type="number" name="results" placeholder="Number of results">
</form>

then, request.POST['keyword'] and request.POST['results'] will contain the value of the input elements keyword and results, respectively.

Upvotes: 9

PBH
PBH

Reputation: 1078

First check if the request object have the 'is_private' key parameter. Most of the case's this MultiValueDictKeyError occurred for missing key in the dictionary-like request object. Because dictionary is an unordered key, value pair “associative memories” or “associative arrays”

In another word. request.GET or request.POST is a dictionary-like object containing all request parameters. This is specific to Django.

The method get() returns a value for the given key if key is in the dictionary. If key is not available then returns default value None.

You can handle this error by putting :

is_private = request.POST.get('is_private', False);

Upvotes: 4

Edson Dota
Edson Dota

Reputation: 383

Why didn't you try to define is_private in your models as default=False?

class Foo(models.Models):
    is_private = models.BooleanField(default=False)

Upvotes: 5

Silver Light
Silver Light

Reputation: 45902

Choose what is best for you:

1

is_private = request.POST.get('is_private', False);

If is_private key is present in request.POST the is_private variable will be equal to it, if not, then it will be equal to False.

2

if 'is_private' in request.POST:
    is_private = request.POST['is_private']
else:
    is_private = False

3

from django.utils.datastructures import MultiValueDictKeyError
try:
    is_private = request.POST['is_private']
except MultiValueDictKeyError:
    is_private = False

Upvotes: 108

adamnfish
adamnfish

Reputation: 11255

Use the MultiValueDict's get method. This is also present on standard dicts and is a way to fetch a value while providing a default if it does not exist.

is_private = request.POST.get('is_private', False)

Generally,

my_var = dict.get(<key>, <default>)

Upvotes: 381

Joe
Joe

Reputation: 47609

You get that because you're trying to get a key from a dictionary when it's not there. You need to test if it is in there first.

try:

is_private = 'is_private' in request.POST

or

is_private = 'is_private' in request.POST and request.POST['is_private']

depending on the values you're using.

Upvotes: 15

Related Questions