I am building a Django app that has a main dashboard with a bunch of on/off toggles. My goal would be to allow the user to toggle their settings on or off and have their changes automatically saved to the database.
So I followed this tutorial to leverage Ajax form submissions in my Django app so that the user would not have to reload the page. The problem that I am having (I think) is that the checkbox values are being POSTed to my Django views as 'on' whereas they should be POSTed as 'True'.
I think that this is the cause of the error, because I see this in my error logs:
Exception Type: IntegrityError at /update_usersettings/
Exception Value: dataplan_usersettings.normalize_person_name_proper may not be NULL
...
POST:
id_normalize_person_name_proper = u'on'
id_normalize_company_name_proper = u'on'
My existing JavaScript and Django views.py are here: https://gist.github.com/joefusaro/25b6221536291c1ba0d1
Update: I've added the relevant Django template and forms code here. Not that I am using widget_tweaks for form rendering. The form renders like so:
<form action="/update_usersettings/" method="POST" id="usersettings_form">
<input checked="checked" class="bootstrap-switch-default" id="id_normalize_person_name_proper" name="bootstrap-switch" type="checkbox" />
<input checked="checked" class="bootstrap-switch-default" id="id_normalize_company_name_proper" name="bootstrap-switch" type="checkbox" />
<input type="submit" value="Post">
FINAL UPDATE
Thanks to Animesh for a great starting point. Here is the final Ajax code required. Special thanks to Victor K. for his help figuring this out!
Here is the final Ajax code:
$(function() {
// Submit post on submit
$('#usersettings_form').on('submit', function(event){
event.preventDefault();
console.log("Form submitted...") // sanity check
save_usersettings();
});
$('input[type="checkbox"]').on('switchChange.bootstrapSwitch', function(event, state) {
$('#usersettings_form').submit();
});
// AJAX for posting.
function get_post_data() {
var data = {};
$('input:checkbox').each(function () {
var $this = $(this);
var id = $this.attr('id');
data[id.replace('id_', '')] = $this.is(':checked');
});
return data;
}
function save_usersettings() {
console.log("Saving user settings...") // sanity check
$.ajax({
url : "update_usersettings/", // the endpoint
type : "POST", // http method
data : get_post_data(),
// handle a successful response
success : function(json) {
console.log(json); // log the returned json to the console
// $("#talk").prepend("<li><strong>"+json.text+"</strong> - <em> "+json.author+"</em> - <span> "+json.created+
// "</span> - <a id='delete-post-"+json.postpk+"'>delete me</a></li>");
console.log("Successfully saved user settings."); // another sanity check
},
// handle a non-successful response
error : function(xhr,errmsg,err) {
// $('#results').html("<div class='alert-box alert radius' data-alert>Oops! We have encountered an error: "+errmsg+
// " <a href='#' class='close'>×</a></div>"); // add the error to the dom
console.log(xhr.status + ": " + xhr.responseText); // provide a bit more info about the error to the console
}
});
};
And here is the final views.py:
class UpdateUserSettings(LoginRequiredMixin, UpdateView):
model = UserSettings
form = UserSettingsForm
def post(self, request, *args, **kwargs):
if request.method=='POST':
response_data = {}
form = UserSettingsForm({})
us = UserSettings.objects.get(user=1)
VALUE_MAP = {
'false': False,
'true': True
}
for name, field in form.fields.items():
if isinstance(field, BooleanField):
if request.POST.get(name):
if request.POST[name] in VALUE_MAP.keys():
setattr(
us,
name,
VALUE_MAP[request.POST[name]]
)
us.save()
response_data['result'] = 'Update successful!'
return HttpResponse(
json.dumps(response_data),
content_type="application/json"
)
else:
return HttpResponse(
json.dumps({"nothing to see": "this isn't happening"}),
content_type="application/json"
)