Calling ajax several times result a duplicated response - javascript

I created an ajax function that returns my items Price by fetching from my DB. I'm sure there isn't any problem with my php but sometimes I get the same result twice!
jQuery
$('.removemore___').click(function(e) {
var item_id = $(this).attr('data-item');
var col_id = $(this).attr('data-col');
var value = $(this).attr('data-value');
if ($(this).attr('data-trash') == 'trash') {
newPopuper('alert_sure__', 'flex', 'blackScreen');
$('.__aggtoyes').attr('data-item', item_id);
$('.__aggtoyes').attr('data-col', col_id);
$('.__aggtoyes').attr('data-value', value);
} else {
$.ajax({
type: "POST",
url: "includes/chekavailableitem.php?remove",
data: {
item_id: item_id,
col_id: col_id,
value: value
},
dataType: "text",
success: function(response) {
var iNum = parseInt(value);
iNum--;
if (response == 'done') {
$('.value__cart[data-item=' + item_id + '][data-col=' + col_id + ']').html(iNum);
$('.removemore___[data-item=' + item_id + '][data-col=' + col_id + ']').attr('data-value', iNum);
$('.addmore___[data-item=' + item_id + '][data-col=' + col_id + ']').attr('data-value', iNum);
if (iNum == 1) {
location.reload();
}
} else if (response == 'deleted') {
location.reload();
}
},
error: function() {
$('#wrong-signup').html(': 102');
},
timeout: 5000
});
}
$.ajax({
type: "POST",
url: "includes/get_finalize_cart.php",
data: {},
cache: false,
async: true,
dataType: "json",
success: function(response) {
// var final_price = $.parseJSON(response)
console.log(response);
if (response[0] == 'done') {
$('.final_price__').html(response[1] + ' <span style="font-size: .786rem;font-weight: 400">تومان</span>');
} else {
}
},
error: function() {
$('#wrong-signup').html(': 101');
},
timeout: 5000
});
e.stopImmediatePropagation();
return false;
});
Here is full function in jQuery
<?php
include 'db.php';
include 'function.php';
$user_id = extractUserId();
$chekcart = "SELECT * FROM `box` WHERE `user_id`='$user_id'";
$result_cox_cart_cheker = connectANDdie($chekcart);
$sum_price = 0;
while($row_items = mysqli_fetch_assoc($result_cox_cart_cheker)){
$price = $row_items['item_price'];
$value = $row_items['value'];
$sum_price = $sum_price + ( $price*$value );
$final_value = number_format($sum_price);
$result = ['done',$final_value];
$result1 = json_encode($result);
echo $result1;
}
and I'll also show a screenshot from console page so you can see what my result is:

You're not waiting for chekavailableitem.php?remove to complete before you call get_finalize_cart.php. Since AJAX is asynchronous, the latter might be processed first, so you'll get a duplicate of the old value.
You should put the second $.ajax() call in the sucess: function of the first $.ajax() call, or use a promise.

Related

Not able to check the empty data returned from view

I am working on Infinite scrolling.
Here is the code in js
$('.workspace-activity .modal-body').scroll(function() {
if ($(this).scrollTop() + $(this).innerHeight() >= $(this)[0].scrollHeight)
{
loadResults(base + 'co8/workspace/activityLogPagination');
}
});
function loadResults(url) {
start = parseInt($('.modal-body .acti-count').length);
var id = $(".single-workspace").attr("data-id");
$.ajax({
url: url,
type: "POST",
data: "start=" + start + "&limit=10&type=workspace&id=" + id,
success: function(data) {
if (!data) {
noData = '<h5 class="no-data">No more data</h5>';
$('.workspace-activity .modal-body').append(noData);
} else {
$('.workspace-activity .modal-body').append(data);
}
}
});
};
The problem is with !data.
The data returned is empty but the if statement executes the else statement,
Is the condition checking correct?
The problem might exists with the blank spaces
!$.trim(data) will remove the blank spaces
The updated javascript function is
function loadResults(url) {
start = parseInt($('.modal-body .acti-count').length);
var id = $(".single-workspace").attr("data-id");
$.ajax({
url: url,
type: "POST",
data: "start=" + start + "&limit=10&type=workspace&id=" + id,
success: function(data) {
if (!$.trim(data)) {
noData = '<h5 class="no-data">No more data</h5>';
$('.workspace-activity .modal-body').append(noData);
} else {
$('.workspace-activity .modal-body').append(data);
}
}
});
};

I want to return function result after calculating in a for loop

i want to check whether is a valid item or not before saving the values. then i create java-script function to check validation and return result. but the problem is this function returns before validate items, the always true the condition above if condition. my code is below. could anyone help me please?
this is series of ajax call and i'm not aware of how to use callback for this..
if(IsValidItems() != ''){
//Do something
}
function IsValidItems() {
var IsvalidStatus = '';
var lineqty = 0;
var LineNumber = -1;
var allRowData = jQuery("#tblJQGrid").jqGrid("getRowData");
for (var i = 0; i < allRowData.length - 1; i++) {
if (allRowData[i].BulkItem != "False") {
if (allRowData[i].quantity != '') {
lineqty = parseInt(allRowData[i].quantity);
LineNumber = i + 1;
var postURL = "/BookingDetail/GetItemAvailablity?ItemCode=" + allRowData[i].itemCode + "&StartDate=" + allRowData[i].StartDate + "&EndDate=" + allRowData[i].EndDate + "&srno=" + allRowData[i].srno + "&locationID=" + allRowData[i].Location;
$.ajax({
url: postURL,
dataType: "json",
contentType: "application/json; charset=utf-8",
data: "",
type: "POST",
async: true,
dataFilter: function (data) {
return data;
},
success: function (result) {
if (lineqty > parseInt(result)) {
IsvalidStatus = IsvalidStatus + "," + LineNumber;
}
},
error: function (XMLHttpRequest, textStatus, errorThrown) { }
});
}
}
}
return IsvalidStatus;
}

JavaScript callback function when working withing a loop

This is what the code below does:
Goes to a table in a database and retrieves some search criteria I will send to Google API (the PHP file is getSearchSon.php)
After having the results, I want to loop around it, call the Google API (searchCriteriasFuc) and store the results in an array
The last part of the code is doing an update to two different tables with the results returned from Google API (updateSearchDb.php)
In my code, I am using setTimeout in a few occasions which I don't like. Instead of using setTimeout, I would like to properly use callback functions in a more efficient way (This might be the cause of my problem) What is the best way of me doing that?
$(document).ready(function() {
$.ajax({
url: 'getSearchSon.php',
type: 'POST',
async: true,
dataType: 'Text',
/*data: { }, */
error: function(a, b, c) { alert(a+b+c); }
}).done(function(data) {
if(data != "connection")
{
var dataSent = data.split("|");
var search_criterias = JSON.parse(dataSent[0]);
var date_length = dataSent[1];
var divison_factor = dataSent[2];
var length = search_criterias.length;
var arrXhr = [];
var totalResultsArr = [];
var helperFunc = function(arrayIndex)
{
return function()
{
var totalResults = 0;
if (arrXhr[arrayIndex].readyState === 4 && arrXhr[arrayIndex].status == 200)
{
totalResults = JSON.parse(arrXhr[arrayIndex].responseText).queries.nextPage[0].totalResults;
totalResultsArr.push(totalResults);
}
}
}
var searchCriteriasFuc = function getTotalResults(searchParam, callback)
{
var searchParamLength = searchParam.length;
var url = "";
for(var i=0;i<searchParamLength;i++)
{
url = "https://www.googleapis.com/customsearch/v1?q=" + searchParam[i] + "&cx=005894674626506192190:j1zrf-as6vg&key=AIzaSyCanPMUPsyt3mXQd2GOhMZgD4l472jcDNM&dateRestrict=" + date_length;
arrXhr[i] = new XMLHttpRequest();
arrXhr[i].open("GET", url, true);
arrXhr[i].send();
arrXhr[i].onreadystatechange = helperFunc(i);
}
setTimeout(function()
{
if (typeof callback == "function") callback.apply(totalResultsArr);
}, 4000);
return searchParam;
}
function callbackFunction()
{
var results_arr = this.sort();
var countResultsArr = JSON.stringify(results_arr);
$.ajax({
url: 'updateSearchDb.php',
type: 'POST',
async: true,
dataType: 'Text',
data: { 'countResultsArr': countResultsArr },
error: function(a, b, c) { alert(a+b+c); }
}).done(function(data) {
var resultsDiv = document.getElementById("search");
if(data == "NORECORD") resultsDiv.innerHTML = 'Updated failed. There was a problem with the database';
else resultsDiv.innerHTML = 'Update was successful';
}); //end second ajax call
}
//llamando funcion principal
var arrSearchCriterias = searchCriteriasFuc(search_criterias, callbackFunction);
}
else
{
alert("Problem with MySQL connection.");
}
}); // end ajax
});
How you did it in 2015
Callbacks are things of the past. Nowadays you represent result values of asynchronous tasks with Promises. Here is some untested code:
$(document).ready(function() {
$.ajax({
url: 'getSearchSon.php',
type: 'POST',
async: true,
dataType: 'text'
/*data: { }, */
}).then(function(data) {
if (data == 'connection') {
alert("Problem with MySQL connection.");
} else {
var dataSent = data.split("|");
var search_criterias = JSON.parse(dataSent[0]);
var date_length = dataSent[1];
var divison_factor = dataSent[2];
return Promise.all(search_criterias.map(function(criteria) {
return $.ajax({
url: "https://www.googleapis.com/customsearch/v1"
+ "?q=" + criteria
+ "&cx=005894674626506192190:j1zrf-as6vg"
+ "&key=AIzaSyCanPMUPsyt3mXQd2GOhMZgD4l472jcDNM"
+ "&dateRestrict=" + date_length,
type: 'GET'
});
})).then(function(totalResultsArr) {
totalResultsArr.sort();
var countResultsArr = JSON.stringify(totalResultsArr);
return $.ajax({
url: 'updateSearchDb.php',
type: 'POST',
async: true,
dataType: 'text',
data: { 'countResultsArr': countResultsArr },
error: function(a, b, c) { alert(a+b+c); }
});
}).then(function(data) {
var resultsDiv = document.getElementById("search");
if(data == "NORECORD") {
resultsDiv.innerHTML = 'Updated failed. There was a problem with the database';
} else {
resultsDiv.innerHTML = 'Update was successful';
}
});
}
}).then(null, function() {
alert('Some unexpected error occured: ' + e);
});
});
This is how you do it in 2016 (ES7)
You can just use async/await.
$(document).ready(async() => {
try {
var data = await $.ajax({
url: 'getSearchSon.php',
type: 'POST',
async: true,
dataType: 'text'
/*data: { }, */
});
if (data == 'connection') {
alert("Problem with MySQL connection.");
} else {
var dataSent = data.split("|");
var search_criterias = JSON.parse(dataSent[0]);
var date_length = dataSent[1];
var divison_factor = dataSent[2];
var totalResultsArr = await Promise.all(
search_criterias.map(criteria => $.ajax({
url: "https://www.googleapis.com/customsearch/v1"
+ "?q=" + criteria
+ "&cx=005894674626506192190:j1zrf-as6vg"
+ "&key=AIzaSyCanPMUPsyt3mXQd2GOhMZgD4l472jcDNM"
+ "&dateRestrict=" + date_length,
type: 'GET'
}))
);
totalResultsArr.sort();
var countResultsArr = JSON.stringify(totalResultsArr);
var data2 = await $.ajax({
url: 'updateSearchDb.php',
type: 'POST',
async: true,
dataType: 'text',
data: { 'countResultsArr': countResultsArr },
error: function(a, b, c) { alert(a+b+c); }
});
if(data2 == "NORECORD") {
resultsDiv.innerHTML = 'Updated failed. There was a problem with the database';
} else {
resultsDiv.innerHTML = 'Update was successful';
}
}
} catch(e) {
alert('Some unexpected error occured: ' + e);
}
});
UPDATE 2016
Unfortunately the async/await proposal didn't make it to the ES7 specification ultimately, so it is still non-standard.
You could reformat your getTotalResults function in the following matter, it would then search rather sequential, but it should also do the trick in returning your results with an extra callback.
'use strict';
function getTotalResults(searchParam, callback) {
var url = "https://www.googleapis.com/customsearch/v1?q={param}&cx=005894674626506192190:j1zrf-as6vg&key=AIzaSyCanPMUPsyt3mXQd2GOhMZgD4l472jcDNM&dateRestrict=" + (new Date()).getTime(),
i = 0,
len = searchParam.length,
results = [],
req, nextRequest = function() {
console.log('received results for "' + searchParam[i] + '"');
if (++i < len) {
completeRequest(url.replace('{param}', searchParam[i]), results, nextRequest);
} else {
callback(results);
}
};
completeRequest(url.replace('{param}', searchParam[0]), results, nextRequest);
}
function completeRequest(url, resultArr, completedCallback) {
var req = new XMLHttpRequest();
req.open("GET", url, true);
req.onreadystatechange = function() {
if (this.readyState === 4 && this.status == 200) {
var totalResults = JSON.parse(this.responseText).queries.nextPage[0].totalResults;
resultArr.push(totalResults);
completedCallback();
}
};
req.send();
}
getTotalResults(['ford', 'volkswagen', 'citroen', 'renault', 'chrysler', 'dacia'], function(searchResults) {
console.log(searchResults.length + ' results found!', searchResults);
});
However, since you already use JQuery in your code, you could also construct all the requests, and then use the JQuery.when functionality, as explained in this question
Wait until all jQuery Ajax requests are done?
To get the callback execute after google calls are finished you could change:
var requestCounter = 0;
var helperFunc = function(arrayIndex)
{
return function()
{
if (arrXhr[arrayIndex].readyState === 4 && arrXhr[arrayIndex].status == 200)
{
requestCounter++;
totalResults = JSON.parse(arrXhr[arrayIndex].responseText).queries.nextPage[0].totalResults;
totalResultsArr.push(totalResults);
if (requestCounter === search_criterias.length) {
callbackFunction.apply(totalResultsArr);
}
}
}
}
then remove the setTimeout on searchCreteriaFuc.
Consider using promises and Promise.all to get all much cleaner :D

How to check if the server returns undefined then ignore it

I am sent many dynamic post ids from a page and a php server side page(server.php) make a query with those id to find out newly added data in mysql.
If it not found any newly added data in mysql, it's return a undefined value. So as per my script, It's append a undefined one after one at a time interval.
So how can I check, if php query cannot found anything in sql then exit and not return anything?
I tried this in my php if(mysqli_num_rows($res)) { //do something } but it's also display undefined.
my javascript:
var CID = []; // Get all dynamic ids of posts (works well)
$('div[data-post-id]').each(function(i){
CID[i] = $(this).data('post-id');
});
function addrep(type, msg){
CID.forEach(function(id){
$("#newreply"+id).append("<div class='"+ type +""+ msg.id +"'><ul><div class='cdomment_text'>"+ msg.detail +"</ul></div>");
});
}
function waitForRep(){
$.ajax({
type: "GET",
url: "server.php",
cache: false,
data: {CID : CID},
timeout:15000,
success: function(data){
addrep("postreply", data);
setTimeout(waitForRep, 15000 );
},
error: function(XMLHttpRequest, textStatus, errorThrown){
setTimeout(waitForRep, 15000); }
});
}
$(document).ready(function(){
waitForRep();
});
server.php
while (true) {
if($_REQUEST['CID']){ //cid got all dynamic post id as: 1,2,3,4 etc.
foreach($_REQUEST['CID'] as $key => $value){
$datetime = date('Y-m-d H:i:s', strtotime('-15 second'));
$res = mysqli_query($dbh,"SELECT * FROM reply WHERE qazi_id=".$_REQUEST['tutid']." AND date >= '$datetime' ORDER BY id DESC LIMIT 1") or die(mysqli_error($dbh));
$data = array();
while($rows = mysqli_fetch_assoc($res)){
$data[]=$rows;
$data['id'] = $rows['id'];
$data['qazi_id'] = $rows['qazi_id'];
$data['username'] = $rows['username'];
$data['description'] = $rows['description'];
$data['date'] = $rows['date'];
//etc. all
$id = $rows['id'];
$qazi_id = $rows['qazi_id'];
$username = $rows['username'];
$description = $rows['description'];
//etc. all
} //foreach close
} //foreach close
if ($description=="") {$detail .= '';}
else {$detail .=''.$description.'';}
$data['detail'] = $detail;
// do others something more
if (!empty($data)) {
echo json_encode($data);
flush();
exit(0);
}
} //request close
sleep(5);
} //while close
I tried this in my php if(mysqli_num_rows($res)) { //do something } but it's also display undefined.
I guess that should be because you are calling this php code every 15000 ms via ajax with a setTimeout.
So instead stopping it there you can just ignore it with your js code in addrep() function.
function addrep(type, msg) {
CID.forEach(function(id) {
if (msg.id !== undefined && msg.detail !== undefined) { // <--check undefined here
$("#newreply" + id).append("<div class='" + type + "" + msg.id + "'>"+
"<ul><div class='cdomment_text'>" + msg.detail +
"</ul></div>");
}
});
}
Or other option is to make use of clearTimeout() when you get undefined.
var timer; // declare the timer here
var CID = []; // Get all dynamic ids of posts (works well)
$('div[data-post-id]').each(function(i) {
CID[i] = $(this).data('post-id');
});
function addrep(type, msg) {
CID.forEach(function(id) {
if(msg.id === undefined || msg.details === undefined){
clearTimeout(timer); // cleartimeout timer
}else{
$("#newreply" + id).append("<div class='" + type + "" + msg.id + "'><ul><div class='cdomment_text'>" + msg.detail + "</ul></div>");
}
});
}
function waitForRep() {
$.ajax({
type: "GET",
url: "server.php",
cache: false,
data: {
CID: CID
},
timeout: 15000,
success: function(data) {
addrep("postreply", data);
timer = setTimeout(waitForRep, 15000); // assign the settimeout to timer
},
error: function(XMLHttpRequest, textStatus, errorThrown) {
setTimeout(waitForRep, 15000);
}
});
}
$(document).ready(function() {
waitForRep();
});

"Uncaught TypeError: undefined is not a function " when adding a value to an input field

the weird thing is that I get in my alert the proper values, but not in my
$('kl_naam').val();
var _naam="",
_voornaam="",
_straat="",
_post="",
_gem="",
_firma="",
data="";
function getFsmaGeg(str){
$.ajax({
url: 'classes/FsmaGeg.php?inscript='+str,
dataType: 'json',
error: function() {
//updateAfspraak(final);
},
type: 'post',
complete: function(data) {
data = $.parseJSON(data.responseText);
alert(data.straat);
if(data) {
_naam=data.naam ;
_voornaam=data.voornaam ;
_straat=data.straat ;
_post=data.post ;
_gem=data.gem ;
_firma=data.firma ;
//checkStep1();
}
}
});
$('#kl_voornaam').val()=_voornaam;
$('#kl_naam').val()=_naam;
$('#kl_straat').val()=_straat;
$('#kl_postcode').val()=_post;
$('#kl_gemeente').val()=_gem;
$('#kl_firma').val()=_firma;
alert(_naam+" "+_voornaam+" "+_straat);
}
You should parse the data like
data = JSON.parse(data);
To assign a value to an input do
$(input-selector).val(value);
In your case
function getFsmaGeg(str){
$.ajax({
url: 'classes/FsmaGeg.php?inscript=' + str,
dataType: 'json',
error: function () {
//updateAfspraak(final);
},
type: 'post',
success: function (data) {
data = $.parseJSON(data);
alert(data.straat);
if (data) {
_naam = data.naam;
_voornaam = data.voornaam;
_straat = data.straat;
_post = data.post;
_gem = data.gem;
_firma = data.firma;
$('#kl_voornaam').val(_voornaam);
$('#kl_naam').val(_naam);
$('#kl_straat').val(_straat);
$('#kl_postcode').val(_post);
$('#kl_gemeente').val(_gem);
$('#kl_firma').val(_firma);
}
}
});
alert(_naam + " " + _voornaam + " " + _straat);
}
You need to pass the value into the .val() method: $('#k1_voornaam').val(_voornaam).
You would set it with = if you were using just the DOM API: document.getElementById('k1_voornaam').value = _voornaam.

Categories