Often people try to determine if the HTTP request is a POST request by checking request.POST
. The view thus looks like:
def my_view(request):
if request.POST:
# …
# …
Why is it a problem?
Because POST requests do not per se carry data. By checking if request.POST
, we are checking the truthiness of the request.POST
. This is a QueryDict
[Django-doc]. A QueryDict
has as truthiness False
, if the QueryDict
is empty. But not all POST requests have "payload". For example it is possible that a confirm box to confirm deleting an object makes a POST request, but without any data as payload. In that case the if request.POST
check will fail, but request.method
will still be 'POST'
.
What can be done to resolve the problem?
One should check the request method with:
def my_view(request):
if request.method == 'POST':
# …
# …
In a class-based view, the "routing" is handled by the view, and thus it will, based on the request method trigger the .get(…)
, .post(…)
, etc. methods.
Extra tips
One can also limit the methods that have access to a certain view with the @require_http_methods(…)
decorator [Django-doc] or related decorators. It is often better not only to check what method is used, but also block requests with a request method that is not foreseen.