Ajax Request wont work unless I use alert() [duplicate] - javascript

This question already has answers here:
How do I return the response from an asynchronous call?
(41 answers)
Closed 8 years ago.
I've been trying for hours to get this to work, but it's just not budging; I have the following code:
var text = "";
function getText(c1, c2)
{
url = "http://en.wikipedia.org/w/api.php?format=json&action=query&titles=" + c1 + "-" + c2 + "_relations&prop=revisions&rvprop=content"
$.ajax({
type: "GET",
dataType: "jsonp",
async: false,
url: url,
success: function (data) {
var obj = (data.query.pages );
var keys = [];
for(var k in obj) keys.push(k);
if (keys[0] == -1) {
//Link doesnt exist
text = "-1";
return text;
}
//Link Exists
else {
link = "http://en.wikipedia.org/wiki/" + c1 + "-" + c2 + "_relations"
text = c1 + "-" + c2 + " Relations"
return text;
}
}
});
return text;
}
var a = (getText(country1, country2))
alert(text);
alert(a);
I'm making an ajax request; a simple inquiry to see if wiki has a page between any 2 given countrie.
If I use alert inside, it works fine, and it returns the correct data inside the text variable. However, when the getText function is called outside, the text variable is always empty. I've tried everything I can think of, including getting the app to sleep for some time, but even that didn't work. I know the async doesn't work from ajax 1.8 onwards, but is there anyway around this?
Thanks in advance.

It is because the asynchronous behavior of ajax. You can't return values from ajax like this way. Because the function will not wait for the success event to happen.
When you put an alert inside that function, success event may occur before the user clicks on alert. That is why it returning value. Otherwise it will not return the value.
Its not a good practice to use async : false in ajax calls. It will freeze the browser.
Good practice is to call a method from the ajax success with the returned data, then do operations with that data inside the function.

Related

jQuery.ajax returning empty array [duplicate]

This question already has answers here:
Why is my variable unaltered after I modify it inside of a function? - Asynchronous code reference
(7 answers)
Closed 6 years ago.
I'm currently learning to use API's. I'm retrieving data from my Github repo. I'm trying to have the script load the JSON info into the githubData variable. But when I log the githubData variable to console it returns an empty array.
Yet, if I create a new variable with the exact same function after the page is loaded the script works exactly as it should.
When the page is loading, it's not loading the actual data. It loads an an empty array. I realize the function is asynchronous, so how would I go about getting the array to not be empty when I load the page?
Here's my code:
var githubAPI = 'https://api.github.com/repos/zacharysohovich/ticTacToe/readme';
var items = {};
jQuery.ajax({
url: githubAPI,
contentType: 'application/json; charset=utf-8',
success: function(resultData) {
$.each(resultData, function(key,val) {
items[key] = val;
});
}
});
var githubData = $.map(items,function(k,v) {
return ("<p>" + k + ": " + v + "</p>");
});
The problem is that its an asynchronous call meaning that once it fires of the request it goes onto the next piece of code. Once it gets to githubData items is still an empty object because the api response hasn't been received yet.
I would instantiate the githubData variable right below var items = {}
like so
var items = {}
var githubData;
and then in the success: function after you do the $.each you can put the
githubData = $.map(items,function(k,v) {
return ("<p>" + k + ": " + v + "</p>");
});
this ensures that the api call has finished and items should have something in it as long as the response came back with something

Set a variable to the data element

Setting up a Flickr script... In my ajax success function, how would I put a var in with the actual this element? I know this and $(this) represent different things. Hard to write out, so I'll use my code examples to explain better.
I have my function set with the defined variables: function flickr_feed(flickrID, flickr_count, photo_size) {, which the variable in question is the photo_size
Using a condition to set the getSize variable from the readable format in photo_size:
if (photo_size == 'square') var getSize = 'url_sq';
I then dump that getSize into the ajax url:
url: 'http://api.flickr.com/services/rest/?&method=flickr.people.getPublicPhotos&api_key=' + flickrAPI + '&user_id=' + flickrID + '&per_page=' + flickr_count + '&page=0&extras=' + getSize + '&format=json&jsoncallback=?',
The problem I'm having in the success function is setting that getSize var to the element.
success: function(data) {
$.each(data.photos.photo, function() {
var photoID = 'http://www.flickr.com/photos/' + flickrID + '/' + this.id;
var photoSrc = this.getSize;
console.log(photoSrc);
});
}
In this result, photoSrc returns undefined. But if I manually set photoSrc to this.url_sq, it's fine. Just can't figure out how to get the variable in there to work the same way.
Apologies for the horrible explanation. If it makes sense at all, any help would be greatly appreciated.
EDIT: My experience with $.ajax is limited. But from what I gather, this refers to the returned data. So in that sense, the photoSrc returns undefined as it is thinking getSize is a result within the data, which it isn't. So how would that be written so that it would use the actual getSize value?
EDIT: Here's a pastebin of the script: http://pastebin.com/KGCUgAet
Cache your this before your ajaxRequest
var originalContext = this;
$.ajax({
success: function() {
$.each(data.photos.photo, function() {
originalContext // Available here
this // Current object under iteration
});
}
Sorted it out with writing the photoSrc var like this: var photoSrc = this[getSize];
Thanks Sushanth for confirming my question about this and the returned data. That helped figure it out.

Javascript variable not updating value [duplicate]

This question already has answers here:
How do I return the response from an asynchronous call?
(41 answers)
Closed 6 years ago.
This is makinkg me crazy, i cant Get the outside variable Get the inside data
Sorry for the bad formating I'm writing from the phone, if someone can helpme out with the format I appreciate it
window.getReasons = function(line) {
var $reasons;
$reasons = "";
$.get(window.location.protocol + "//" + window.location.host + "/" + "allLineReasons.js?line=" + line, function(returnData) {
$reasons = returnData.toString();
return console.log("T_T ----->" + returnData.toString());
}, "html");
console.log($reasons);
return $reasons;
};
The most important thing for you to understand is that $.get() is ASYNCHRONOUS by default. So what is happening is that your console.log() and return statements that follow your call to get() are executing before the get() has returned it's value.
You might look to utilize the when() method here to handle the deferred object that is returned from get()
window.getReasons = function(line) {
var reasons = '';
$.when(
$.get(window.location.protocol + "//" + window.location.host + "/" + "allLineReasons.js?line=" + line)
).done(function(jqxhr) {
data = jqxhr[0];
reasons = data.toString();
});
console.log(reasons);
return reasons;
}
$reasons won't be updated until after the GET completes on the server and the response is returned. But your console.log will execute immediately after the request is made.

Javascript Array loses data

I'm having trouble getting my information into an array in an ajax call, if I alert the information right after I insert it into the array it works fine, but if I do it at the end it alerts unidentified. I made sure that books is declared outside so it doesn't interfere.
var books = [];
$.ajax({
url: 'getFolderContents.php',
dataType: 'json',
success: function (data)
{
for(var i=0;i<data.length;i++) {
var amm = 0;
if(data[i].indexOf(".epub") !== -1) {
//$('#bTable').append("<td><a id = '" + data[i] + "' href = 'book.html'><img src = 'book.png' width = '100px'/><br/>" + data[i] + "</a></td>");
books.push(data[i]);
//alert(books[0]) Works if I call it from here, but not at the end.
}
}
},
error: function()
{
alert("error");
}
});
alert(books[0]);
Your
alert(books[0]);
will be executed while the Ajax call is running and therefore will not have any elements at this point of execution yet. Ajax is asynchronous - while you are doing a request to your PHP script your script continues execution.
Put all actions with books in your success function.
Another hint: As of jQuery version 1.8 you cannot longer use the parameter async: false to create a synchronous "A"jax call. You have to use the callback functions. Have a look at the docs for $.ajax
Your array hasn't lost any data; the data hasn't been put in there yet. The 'A' stands for "asynchronous", meaning your success callback hasn't run yet at the time you call the alert.
Put the alert inside your callback instead:
success: function (data)
{
for(var i=0;i<data.length;i++) {
var amm = 0;
if(data[i].indexOf(".epub") !== -1) {
//$('#bTable').append("<td><a id = '" + data[i] + "' href = 'book.html'><img src = 'book.png' width = '100px'/><br/>" + data[i] + "</a></td>");
books.push(data[i]);
//alert(books[0]) Works if I call it from here, but not at the end.
}
}
alert(books[0]);
},
Your alert is executing before the success function is called. Perhaps seeing the same code using a promise will make things clearer.
$.ajax( url: 'getFolderContents.php', dataType: "json" )
//the then function's first argument is the success handler
.then(function( data ) {
for(var i=0;i<data.length;i++) {
var amm = 0;
if(data[i].indexOf(".epub") !== -1) {
//$('#bTable').append("<td><a id = '" + data[i] + "' href = 'book.html'><img src = 'book.png' width = '100px'/><br/>" + data[i] + "</a></td>");
books.push(data[i]);
//alert(books[0]) Works if I call it from here, but not at the end.
}
alert(books[0]
});
});
I always feel this syntax makes async stuff make more sense. Otherwise this code functions exactly like Blazemonger's correct answer.
Your AJAX call is asynchronous, that's why it is undefined.
The alert at the end happens before the ajax success callback, because ajax is asynchronous.

Scoping Issues inside jQuery.ajax()

I'm caching label strings by saving them into a variable, but running into weird scoping issues. I know this has to do with closures, but I can't seem to figure out what the issue is exactly.
info_lbl = {};
$("#chkCorporateGift").click(function(){
var type = $(this).is(":checked") ? "Corporate" : "Personal";
if(!info_lbl.hasOwnProperty(type)){
$.ajax({
url: svc_og + "Get" + type + "InformationLabel",
success: function(data){
info_lbl[type] = data;
}
});
}
$("#lblInformationType").text(info_lbl[type]);
});
lblInformationType label isn't set the very first time GetCorporateInformationLabel or GetPersonalInformationLabel methods are called. After the first time each one is called, the label's value is being changed. Could somebody please explain why this behavior occurs? When I use Firebug and set a break point on $("#lblInformationType").text(info_lbl[type]);, info_lbl[type] contains the right value and everything works fine on the first two calls as well.
AJAX calls are asynchronous. This means that any code following the request does not wait for the request to return before it runs.
In other words, the AJAX request does not block execution of subsequent lines of code. So by the time the response is received from the AJAX request, the following lines of code have already executed.
Any code that relies on the response of the AJAX request should be placed inside the callback.
$("#chkCorporateGift").click(function(){
// var type = $(this).is(":checked") ? "Corporate" : "Personal";
// It is more efficient to use this.checked instead of using .is(":checked")
var type = this.checked ? "Corporate" : "Personal";
if(!info_lbl.hasOwnProperty(type)){
$.ajax({
url: svc_og + "Get" + type + "InformationLabel",
success: function(data){
info_lbl[type] = data;
// code that relies on the response needs to be placed in
// a callback (or in a function that is called here).
$("#lblInformationType").text(info_lbl[type]);
}
});
} else {
$("#lblInformationType").text(info_lbl[type]);
}
});
I would image that the reason things work properly when you have a breakpoint is that the pause in execution gives the AJAX response time to return.
EDIT: Improved efficiency of the code by using this.checked instead of the original $(this).is(':checked').
Move this line:
$("#lblInformationType").text(info_lbl[type]);
into the "success" callback.
As said above, there is 2 solutions :
1) Making $.ajax asynchronous
$.ajax({
url: svc_og + "Get" + type + "InformationLabel",
async: false,
success: function(data){
info_lbl[type] = data;
}
});
2) Keep it asynchronous but doing twice :
var type = $(this).is(":checked") ? "Corporate" : "Personal";
if(!info_lbl.hasOwnProperty(type)){
$.ajax({
url: svc_og + "Get" + type + "InformationLabel",
success: function(data){
info_lbl[type] = data;
$("#lblInformationType").text(data);
}
});
}
$("#lblInformationType").text(info_lbl[type]);

Categories

Resources