[英]Can't store data fetched with jQuery JSONP
我试图通过使用JSONP的jQuery AJAX调用从Flickr获取一堆照片数据,但我不想立即使用这些数据。 相反,我想保留它以供日后使用。 在一个复杂的情况下,我想让用户对预取的数据执行不同的查询。 在更简单的情况下,我想在每次用户单击按钮时加载下n个图像。
现在,我正在测试下面最基本的功能,它是根据这个问题的最佳答案改编的: JQuery - 将ajax响应存储到全局变量中
但是,检索到的JSON数据不会存储在jsonData变量中。 我将alert语句调试,奇怪的是getData()警报是在回调函数中的警报之前触发的。 为什么会这样?
var dataStore = ( function() {
var jsonData;
$.ajax({
type: "GET",
url: "http://api.flickr.com/services/feeds/photos_public.gne?jsoncallback=?",
dataType: "json",
data: {
tags: "dog",
tagmode: "any",
format: "json"
},
success: function(data) {
jsonData = data;
alert(jsonData);
}
});
return { getData : function()
{
if (jsonData) return jsonData;
else alert("no data!");
}};
})();
var stuff = dataStore.getData();
$.each(stuff.items, function(i,item) {
$("<img/>").attr("src", item.media.m).appendTo("#images");
if ( i == 3 ) return false;
});
...而奇怪的是,在回调函数中的警报之前触发了getData()警报。 为什么会这样?
因为默认情况下ajax调用是异步的 - 而且JSONP调用本质上总是异步的(其他类型的ajax调用可以同步,但通常是个坏主意)。
这意味着你的
var stuff= dataStore.getData();
line在JSONP请求完成之前执行。 这也是它在jsonData
不到任何内容的jsonData
。
您需要将JSONP调用结果的任何处理移动到从请求的success
回调调用的内容中。
问题是当$.each
运行时, stuff
是undefined
,因为stuff
还没有运行完毕。 一切都需要回调。 有很多方法可以解决这个问题,从最丑陋的hacky做一个setInterval()
来检查是否有stuff === undefined
,如果没有,那么它会将$.each
用于更简单地使用回调的JS本机方式。
就个人而言,我强烈建议您更有效地使用回调。 这就是我要做的。 这应该会让你走上正轨。 显然,很多这是人工码,但很容易根据您的需求进行修改。
var cachedImageData = {}; //To check if data exists for the search term
var displayImages = function(stuff){
$.each(stuff.items, function(i,item) {
$("<img/>").attr("src", item.media.m).appendTo("#images");
if ( i == 3 ) return false;
});
}
$('button').bind('click',function(){ //Triggers the ajax...
if(cachedImageData[$('input').val()] === undefined){ //If this search doesn't exist...
$.ajax({
url:''
data:{ tag: $('input').val() }, //Get the value however
success: function(data){
cachedImageData[$('input').val()] = data; //Save for later
displayImages(data); //Run the display images function which is your $.each()
}
});
}
});
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.