django delete object using AJAX or javascript with confirm - javascript

hello I want to delete a Django object using AJAX or JavaScript with confirm message on clicking delete but I don't know how to complete AJAX request.
views.py
def delete(request,id):
try:
inta = work.objects.get(pk=id)
inta.delete()
except:
pass
return HttpResponseRedirect(reverse('home'))
urls.py
url(r'^delete/(?P<id>\d+)/$',views.delete, name='delete')
html :
{& for app in apps &}
<p>{{ app.item0 }}</p>
<p>{{ app.item1 }}</p>
<p>{{ app.item2 }}</p>
<button data-object-id="{{ app.id }}">remove</button>
{% endfor %}
$('button').on('click', function(){
var confirmation = confirm("are you sure you want to remove the item?");
if (confirmation) {
// execute ajax
alert('removed');
}
})

There is more convinient way to write AJAX code:
$('button').on('click', function(){
let confirmation = confirm("are you sure you want to remove the item?");
if (confirmation) {
let object_id = $(this).attr('data-object-id');
let url = `delete/${object_id}/`;
$.ajax({
url: "example.html/my/example",
data: {
'csrfmiddlewaretoken': "{{ csrf_token }}"
},
type: "DELETE",
dataType: "json"
}).done(
function(){alert("Deleted");}
).fail(
function(){alert("Error");}
)
});
}
})

Assuming that
The delete view excepts a DELETE request
The javascript code is contained in the HTML
$('button').on('click', function(){
let confirmation = confirm("are you sure you want to remove the item?");
if (confirmation) {
let object_id = $(this).attr('data-object-id');
let url = `delete/${object_id}/`;
$.delete(url, {csrfmiddlewaretoken: '{{ csrf_token }}'}, function(){
alert('removed');
})
}
})
If the javascript code is in a separate file you will have to find another way to get the csrf-token, perhaps from a hidden input somewhere on the page.

Related

Why Is Anchor Tag Not Working After Ajax Refresh of HTML?

I've searched all afternoon...but am a bit confused by now. Lots of information on this topic...but not specific to how I'm doing it. I may be doing it incorrectly for this use case...but with no further ado...
My HTML...
<div class="spacer282" id="upvote-count">
{{ suggestion_detail.total_upvotes }}
</div>
My AJAX...
$(document).on("click",'.button',function(e){
e.preventDefault();
var $this = $(this);
$.ajax({
type: "POST",
url: $this.data("href"),
dataType: "json",
csrfmiddlewaretoken: "{{ csrf_token }}",
beforeSend: function(xhr) {
xhr.setRequestHeader("X-CSRFToken", "{{ csrf_token }}");
},
success: function(response){
document.getElementById('upvote-count').innerHTML = response['total_upvotes'];
},
});
return false;
});
This works fine...but after the first replace...the anchor tag is no longer clickable...I know that generally I need to reset the listener for this event...but because it's an anchor tag...I can't quite work out the best way to handle this.
Per the request...this is being done via Django and JSON Response...when the user clicks a button I do a refresh of the {{ suggestion_detail.total_upvotes }} via JSON...
class SuggestionLikeView(LoginRequiredMixin,View):
def post(self, request, pk, *args, **kwargs):
suggestion = Suggestion.objects.get(pk=pk)
is_upvote = False
for upvote in suggestion.upvotes.all():
if upvote == request.user:
is_upvote = True
break
if is_upvote:
suggestion.upvotes.remove(request.user)
return JsonResponse({'total_upvotes': suggestion.total_downvotes,"message":"success"})
This is working fine...again when the replace happens....the anchor no longer works unless I click on the refresh page...then the anchor starts working again.
As Daedalus point out to me....I needed to move my replace from the div to the anchor portion of my HTML....
<div class="spacer282" id="upvote-count">
{{ suggestion_detail.total_upvotes }}
</div>
And then updating this line of code...
document.getElementById('upvote-url').innerHTML = response['total_upvotes'];
Did the trick.

foreign key showing undefined django ajax

in this scenario when put the name of foreign key in p tag with js, it is showing undefined but its getting the inpuput as the proper user but not not able to show it because it is saying undefined
js code
$(document).ready(function(){
// $('#submit').onclick(function(){
// $('#message').val=''
// })
$(document).on('submit','#post_form',function(e){
e.preventDefault();
$.ajax({
type: 'POST',
url:"{% url 'create' %}",
data:{
message: $('#message').val(),
csrfmiddlewaretoken:$('input[name=csrfmiddlewaretoken]').val(),
},
success:function(){
window.location = url;
}
});
});
setInterval(function()
{
$.ajax({
type:'GET',
url:"{% url 'comments' %}",
success:function(response){
$('.display').empty();
for(var key in response.comments){
this is where it shows undefined, is there any way to convert it to string
console.log(response.comments[key].user);
var temp = "<div class='message_area'><p id='messagetext'>"+response.comments[key].message+"</p></div>"
$(".display").append(temp);
}
},
error:function(response){
console.log("no data found")
}
});
}, 500);
});
views.py
def create(request):
if request.method == "POST":
author = request.user
message = request.POST['message']
message = comments(user=author,message=message)
message.save()
models
class comments(models.Model):
userId = models.AutoField(primary_key=True)
user = models.ForeignKey(User,on_delete=models.CASCADE)
message = models.CharField(max_length=100,blank=False)
date = models.TimeField(auto_now_add=True)
def __str__(self):
return f'{self.user} comments'
using Django template syntax in the js codes is not wrong but it could be better if we don't do that.
instead of data:{ message: $('#message').val(); csrfmiddlewaretoken:$('input[name=csrfmiddlewaretoken]').val(),},
it could be writing in the html, inside the form part. and the js could be:
<form id="form_id" ......>
{% csrf_token %}
<!-- other fields of the form -->
</form>
$.ajax({
type: 'POST',
url:"{% url 'create' %}",
data:$("#form_id").serialize();
success:function(){
window.location = url;
}
});
well, thats not enough for your case, you have problem in another part of the code. you didn't provide the views function which returns the comments and it seems that the problem is there, at this time you could use console.log(response.comments[key]); to figure out what data is returned then use the information to correct the code

Way to distinguish different AJAX functions in POST?

I need to distinguish among multiple AJAX functions in a django view's POST method, to handle multiple forms.
The background:
I'd previously written this view without AJAX and got it working just fine. Before Ajax, I was able to distinguish the POST method for each form by adding name="some_button_name", like so:
if request.method == 'POST' and 'some_button_name' in request.POST: #check which form button submitted
This was great, but AJAX can make it better if I get it working. Now I'm not sure how to distinguish the ajax functions on the view side.
Here's how I think it should work (theoretical view):
if request.method == 'POST' and request.POST['some identifier_A from ajax function here']:
# do stuff
# save form_A
if request.method == 'POST' and request.POST['some identifier_B from ajax function here']:
# do stuff
# save form_B
if request.method == 'POST' and request.POST['some identifier_C from ajax function here']:
# do stuff
# save form_C
... but I'm stumped. Below is my (simplified but structurally accurate) code. It will of course want to call every model's save method regardless of which form/ajax function was called, so saving form C will screw up form B since the B's ajax handler didn't do anything or pass any JSON.
I've looked through the list of ajax parameters and it doesn't appear that I can use one to add some identifying variable to catch on the view side in POST... or is there?
If someone could shed some light a way to solve this I'd be hugely appreciative. Also, I'm not sure if it's relevant to this question, but I also want to eventually add a "save all" button that fires all the ajax functions.
Views.py
def update_view(request, slug):
mymodel = Model.objects.get(slug=slug)
form_A = Model_A_Form(instance=mymodel.model_a)
form_B = Model_B_Form(instance=mymodel.model_b)
form_C = Model_C_Form(instance=mymodel.model_c)
if request.method == 'POST': # using request.is_ajax(): here causes the same problem
form_A = Model_A_Form(request.POST, instance=mymodel.model_a)
if form_A.is_valid():
form_A.save()
return JsonResponse
form_B = Model_B_Form(request.POST, instance=mymodel.model_b)
if form_B.is_valid():
form_B.save()
return JsonResponse
form_C = Model_C_Form(request.POST, instance=mymodel.model_c)
if form_C.is_valid():
form_C.save()
return JsonResponse
context = {
'form_A': form_A,
'form_B': form_B,
'form_C': form_C,
'obj': mymodel,
}
return render(request, "products/update_form.html", context)
.JS
<script>
$(() => {
// Form A handler
$(function () {
$('#mybtn-a').click(function () {
var formA = $(".form-a-ajax")
var formAMethod = formA.attr("method");
var formAEndpoint = formA.attr("action");
formA.submit(function (event) {
event.preventDefault();
var formAData = formA.serialize()
var thisForm = $(this)
$.ajax({
method: formAMethod,
url: formAEndpoint,
data: formAData,
success: function (data) {
$.alter({
title: "Success!",
})
},
error: function (error) {
}
}) //end ajax
});//end click
})
})
// Form B handler
$(function () {
$('#mybtn-b').click(function () {
var formB = $(".form-b-ajax")
var formBMethod = formB.attr("method");
var formBEndpoint = formB.attr("action")
formB.submit(function (event) {
event.preventDefault();
var formBData = formB.serialize()
var thisForm = $(this)
$.ajax({
method: formBMethod,
url: formBEndpoint,
data: formBData,
success: function (data) {
$.alter({
title: "Success!",
})
},
error: function (error) {
}
}) // end ajax
});//end click
})
})
// Form C handler
$(function () {
$('#mybtn-c').click(function () {
var formC = $(".form-c-ajax")
var formCMethod = formC.attr("method");
var formCEndpoint = formC.attr("action")
formC.submit(function (event) {
event.preventDefault();
var formCData = formC.serialize()
var thisForm = $(this)
$.ajax({
method: formCMethod,
url: formCEndpoint,
data: formCData,
success: function (data) {
$.alter({
title: "Success!",
})
},
error: function (error) {
}
}) //end ajax
});//end click
})
})
Template:
<form method="post" action="{{ obj.get_my_url }}" class="form-a-ajax">
{% csrf_token %} {{ form_A }}
<button type='submit' id="mybtn-a" name='save_form_a' class='btn btn-success'>Save</button>
</form>
<form method="post" action="{{ obj.get_my_url }}" class="form-b-ajax">
{% csrf_token %} {{ form_B }}
<button type='submit' id="mybtn-b" name='save_form_b' class='btn btn-success'>Save</button>
</form>
<form method="post" action="{{ obj.get_my_url }}" class="form-c-ajax">
{% csrf_token %} {{ form_C }}
<button type='submit' id="mybtn-c" name='save_form_c' class='btn btn-success'>Save</button>
</form>
Thanks for your feedback everybody! Your comments gave me an idea. I have a working solution and it seems totally simple after the fact. No need to append anything to the JSON in my case. Every model I have has some unique field names; I just need to check for the presence of one of them in the JSON object of key:value pairs. This works:
if request.method == 'POST' and 'some_unique_model_field_name' in request.POST.keys():
form_A = Model_A_Form(request.POST, instance=mymodel.model_a)
if form_A.is_valid():
form_A.save()
return JsonResponse
#rinse and repeat...

Getting the name attribute of an HTML element and sending it to the server

I trying to send the name attribute of an element to the server
So the user would click on an element and I would send its name to the server.
I am using flask.
Right now I have this JS function that selects the elements name and stores it in a variable:
$(document).ready(function(){
$("a").click(function(){
$(this).hide();
let x = $(this).attr('name');
console.log(x);
});
});
Here is my code on the server:
#app.route('/friends_Profile', methods=["GET"])
def friends_profile():
name = request.args.get('x')
print(name)
return render_template('friends-profile.html', friend=name)
the name variable is empty (None)
And here is the HTML:
<div class='friends'>
<b>You are Friends with:</b>
{% for x in range(friends|length) %}
<li><a id='{{loop.index}}'
method="GET" href="/friends_Profile" name='{{friends[loop.index-1][0][0]}}_{{friends[loop.index-1][0][1]}}' value="{{number[loop.index -1][0]}}">{{friends[loop.index -1][0][0]}} {{friends[loop.index -1][0][1]}}</a></li>
{% endfor %}
</div>
You can try something like this...via Traveling Tech Guy's comments in your question. Send your 'x' var to the server using .ajax...can do whatever you want with it after that.
$(document).ready(function(){
$("a").click(function(){
$(this).hide();
let x = $(this).attr('name');
console.log(x);
var url_to_server = "http://localhost/server_response.[php or whatever]?name=x";
jQuery.ajax({
type: "GET",
url: url_to_server,
cache: false,
success: function(response)
{
console.log("sent it to server - update view if needed");
}
});
});
});

calling function from jQuery with Django not working correctly

Im trying to make a page that searched for users based on a users criteria. It then loads the results via AJAX response into a different DIV:
function search_friends() {
$("#search-results").show();
$("#loading1").show();
var q = $("#id_q").val();
var type = $("#id_search_type").val();
$("#loading1").hide();
$("#results").load("/search/friends/?ajax&q="+encodeURIComponent(q)+"&search_ty­pe="+encodeURIComponent(type));
return false;
}
Inside this new results DIV, I have links for each user to be able to add them as a friend. Each link in this results DIV has a ID of each users userID and a class of user_link. When the logged in user clicks on the link I want it to pop up a confirmation box then send the request via AJAX. However, I cannot get the links to submit via AJAX like I want. The code I have is below:
{% for u in users %}
<div id="results">
<img src="{{ u.profile_pic }}" class="xsmall-pic" /> {{ u.username }}<br />
<span class="small-date">{{ u.get_full_name }}</span>
<span class="floatR" id="user_{{ u.id }}_link">Add as friend</span>
</div>{% endfor %}
<script type="text/javascript" language="javscript">
$(document).ready(function() {
var csrf_token = "{{ csrf_token }}";
$(".user_link").bind('click',function() {
request_friend($(this).id,csrf_token)
});
$("#search-friends-form").submit(search_friends);
});
</script>
In an external JavaScript file I have the following:
function confirm_request()
return confirm("Are you sure you want to request this user as a friend?");
}
function request_friend(id,token)
if (confirm_request())
{
var data1 = {to_friend: id,csrfmiddlewaretoken: token};
$.post('/users/requests/friends/'+id+'/?ajax',
data1, function(json) {
$("#user_"+id+"_link").html(json.status);
}, "json");
return false;
}
else
{
return;
}
}
Thanks for any help as Im not all that great with Javascript.
EDIT Python function called via AJAX
def search_for_friends(request):
users = False
friends = False
return_page = 'users/friend_search.html'
ajax = 'ajax' in request.GET
try:
if 'q' in request.GET:
form = FriendSearchForm(request.GET)
if form.is_valid():
if form.cleaned_data['search_type'] == 'username':
users = CustomUser.objects.exclude(pk=request.user.id).filter(username__icontains=form.cleaned_data['q'])
elif form.cleaned_data['search_type'] == 'name':
users = CustomUser.objects.filter(Q(first_name__icontains=form.cleaned_data['q']) | Q(last_name__icontains=form.cleaned_data['q']))
elif form.cleaned_data['search_type'] == "email":
users = CustomUser.objects.filter(email__icontains=form.cleaned_data['q'])
else:
pass
else:
pass
else:
form = FriendSearchForm()
if users != False:
users = users
error = False
if users == "":
users = ""
error = "No users match the search term provided"
if ajax:
show_results = True
context = RequestContext(request,{'users':users,'form':form,'show_results':show_results})
return render_to_response('users/friend_search_results.html',context_instance=context)
context = RequestContext(request,{'users':users,'form':form,'error':error})
return render_to_response(return_page,context_instance=context)
except:
form = FriendSearchForm()
context = RequestContext(request,{'form':form})
return render_to_response(return_page,context_instance=context)
If you want to keep from having the JavaScript in the AJAX response, you could have the completion event of .load() take the responsibility of setting up the click events:
var url = "/search/friends/?ajax&q="+encodeURIComponent(q)+"&search_ty­pe="+encodeURIComponent(type);
$("#results").load(url, function() {
var csrf_token = "{{ csrf_token }}";
$(".user_link").bind('click',function() {
request_friend($(this).id,csrf_token)
});
});
if I understand your question correctly, you want to make sure click handlers work for links loaded through a later AJAX call?
In jQuery, use the $('.user_link').live('click', function() {}) handler once to assign a click event handler to all current and future links.
The Javascript being returned from your AJAX call does not get evaluated unless you specifically tell jQuery to evaluate it. This is done by specifying the dataType on your AJAX calls, which .load() doesn't support.
As seen in this answer, you should use jQuery.get() or $.ajax and specify your data type:
$.ajax({
type: "GET",
url: "yourPage.htm",
dataType: "html"
});

Categories

Resources