I am trying to upload an HTML form via AJAX (just JS, no jQuery). The form is assembled by my template by adding three components: The csrf token, a ModelForm and a regular Django form (forms.Form). The model form {{ form.as_p}} comprises the visible parts of the form whereas the form {{ order_form }} comprises some hidden fields. The form section of my template looks like this:
<form id="{{ form_id }}" action="javascript:submitThisForm('{{ form_id }}', '/submit_blog_entry/')" method='POST' enctype='multipart/form-data'>
{% csrf_token %}
{{ form.as_p }}
{{ other_form }}
<input type='submit' value='SAVE changes' />
</form>
I already tried to remove enctype from the <form>
tag (I read in a reply to another question that FormData() adds this automatically), but to no avail.
When the submit button is pressed, the JS function submitBlodEntryForm() is called, passing the form ID and the url to use for the AJAX request. The code of that JS function is here:
function submitThisForm(form_ID, url){
var submit_form = document.getElementById(form_ID);
var formData = new FormData(document.getElementById(form_ID));
httpRequest = new XMLHttpRequest();
if (!httpRequest){
alert("Giving up, cannot create an XMLHTTP instance.");
return false;
};
var url = "/submit_blog_entry/";
var sendCSRFtoken = "csrfmiddlewaretoken="+String(getCookie('csrftoken'));
var sendContent = sendCSRFtoken+"&"+formData;
httpRequest.onreadystatechange = alertContents;
httpRequest.open('POST', url, true);
httpRequest.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
//httpRequest.send();
httpRequest.send(sendContent);
// alternatively: httpRequest.send(formData);
}
The AJAX request is submitted to and received by the server (a Django view). If I do not manually add the csrf token as shown in the JS code above (variable sendContent) and just send formData, I get a 403 error, apparently because the server does not find the token. It should be part of the form, though...
When I try binding the received data to the respective form, the validation fails:
form = ThisForm(request.POST)
if form.is_valid():
#do something
If I print what is in request.POST, I get the following in the Terminal:
<QueryDict: {'[object FormData]': [''], 'csrfmiddlewaretoken': ['token goes here']}>
Apparently, the FormData object is empty. I also assume this because I get the two following errors for two required fields in my form (by using form.errors.as_data()):
[ValidationError(['This field is required.'])]
What is going wrong? Did I mess up the template such that FormData() does not produce useful data? Am I incorrectly creating the AJAX request? Or is the problem on the server side (although I am hardly doing anything there so far)?
Thank you, any help is greatly appreciated!