循环内的多个 AJAX 请求并构建数组
Multi AJAX requests inside a loop and building an array
我完全卡住了。我想完成以下任务:
登录和注销时使用正确的价格协议更新购物车。
- 从 LocalStorage 获取当前 cartlines(成功)
- 每个 cartline 都有一个 AJAX 请求(例如 getJSON)以取回当时应用的新数据。 (成功)
- 创建新对象并保存新数据。
- 将新对象添加到数组。
- 当所有AJAX个请求都准备好并且新数组(new_cart)完全填满后,再次推送到LocalStorage。
在我的脚本下面。我希望有人能帮助我。
function sync() {
// Read LocalStorage
try {
var dataArray = JSON.parse(getLocalStorage('cartarray'));
}
catch (err) {
var dataArray = null;
}
ary1 = dataArray.cartlines;
var keys = Object.values(ary1);
// Delete LocalStorage
// unsetLocalStorage('cartarray');
new_cart1 = [];
$.each( keys, function( index, value ){
var itemUrl = "https://" + window.location.hostname + "/search/?sku=" + value.sku;
var value1 = value.quantity;
var p = $.getJSON(itemUrl);
p.then(function(data) {
var obj = {};
// Add items
obj['sku'] = data.results[0].sku;
obj['quantity'] = value1;
obj['price'] = data.results[0].price;
obj['title'] = data.results[0].product_title;
obj['img'] = data.results[0].img;
obj['url'] = data.results[0].url;
obj['internalSku'] = data.results[0].sku;
// Return obj
return obj;
});
// Add to object to array.
new_cart1.push(obj);
});
$.when.apply($, new_cart1).then(function() {
var keys1 = new_cart1;
var cartarray1 = [];
for (var key of keys1) {
console.log(key);
if(key.quantity >= 1){
cartarray1.push({
sku: key.sku,
title: key.title,
price: key.price,
img: key.img,
url: key.url,
quantity: key.quantity,
internalSku: key.internalSku,
// custom: key.custom
});
}
}
// setLocalStorage('cartarray', '{"cartId": "","cartlines":'+JSON.stringify(cartarray)+'}');
});
}
我假设你想要什么:
- 您已经有一些
dataArray
- 您希望从服务器为每个项目并行请求额外的数据
- 完成所有请求后,您希望处理结果
$.getJSON
方法returnsjqXHR
object, which implements the Promise接口,所以你可以这样使用它:
$.getJSON(someUrl).then(result => {
// do something with result
});
或这种方式(在 async
函数内):
const result = await $.getJSON(someUrl);
// do something with result
下一步是使您的项目处理异步:
async function processItem(item) {
return await $.getJSON(item.url);
}
并并行处理整个数组:
async function processArray(array) {
const promises = array.map(processItem);
return await Promise.all(promises);
}
请注意,Promise.all
解析为包含每个项目结果的数组,results 的顺序与 promises
初始数组中的顺序相同.
下面是异步处理数组并等待处理完成的完整代码段。请注意,我在我的代码片段中创建了 asyncGetJson
占位符函数来模拟带有超时的真实服务器请求:
// Helper function to simulate random request timeout
function getRandomInt(min, max) {
min = Math.ceil(min);
max = Math.floor(max);
return Math.floor(Math.random() * (max - min) + min);
}
/**
* Not a real request, just a placeholder
* This function multiplies n by 2 and returns it after random timeout
*/
function asyncGetJson(n) {
return new Promise(resolve => {
setTimeout(() => {
resolve(n * 2);
}, getRandomInt(500, 2000));
});
}
async function processItem(item) {
return await asyncGetJson(item);
}
async function processArray(dataArray) {
const promises = dataArray.map(processItem);
return await Promise.all(promises);
}
async function init() {
const dataArray = [1, 2, 3];
console.log('Start');
const result = await processArray(dataArray);
console.log(result);
console.log('Done');
// Here should be your logic that works with results from the server
}
init();
如果您认为每个项目都是一个 async
方法
,这一切都会简单得多
async function processItem(value) {
var itemUrl = "https://" + window.location.hostname + "/search/?sku=" + value.sku;
var data = await $.getJSON(itemUrl);
return {
sku: data.results[0].sku,
quantity: value.quantity,
price: data.results[0].price,
title: data.results[0].product_title,
img: data.results[0].img,
url: data.results[0].url,
internalSku: data.results[0].sku
};
}
然后等待它们就像对 map
的结果执行 Promise.all
以获取值一样简单。下面同时运行它们并等待所有结果完成。
async function execute(){
var dataArray = JSON.parse(getLocalStorage('cartarray'));
var values = Object.values(dataArray.cartlines);
var new_cart1 = await Promise.all(values.map(processItem));
// do something with new_cart1 which is an array of
// the objects returned from processItem
}
我完全卡住了。我想完成以下任务: 登录和注销时使用正确的价格协议更新购物车。
- 从 LocalStorage 获取当前 cartlines(成功)
- 每个 cartline 都有一个 AJAX 请求(例如 getJSON)以取回当时应用的新数据。 (成功)
- 创建新对象并保存新数据。
- 将新对象添加到数组。
- 当所有AJAX个请求都准备好并且新数组(new_cart)完全填满后,再次推送到LocalStorage。
在我的脚本下面。我希望有人能帮助我。
function sync() {
// Read LocalStorage
try {
var dataArray = JSON.parse(getLocalStorage('cartarray'));
}
catch (err) {
var dataArray = null;
}
ary1 = dataArray.cartlines;
var keys = Object.values(ary1);
// Delete LocalStorage
// unsetLocalStorage('cartarray');
new_cart1 = [];
$.each( keys, function( index, value ){
var itemUrl = "https://" + window.location.hostname + "/search/?sku=" + value.sku;
var value1 = value.quantity;
var p = $.getJSON(itemUrl);
p.then(function(data) {
var obj = {};
// Add items
obj['sku'] = data.results[0].sku;
obj['quantity'] = value1;
obj['price'] = data.results[0].price;
obj['title'] = data.results[0].product_title;
obj['img'] = data.results[0].img;
obj['url'] = data.results[0].url;
obj['internalSku'] = data.results[0].sku;
// Return obj
return obj;
});
// Add to object to array.
new_cart1.push(obj);
});
$.when.apply($, new_cart1).then(function() {
var keys1 = new_cart1;
var cartarray1 = [];
for (var key of keys1) {
console.log(key);
if(key.quantity >= 1){
cartarray1.push({
sku: key.sku,
title: key.title,
price: key.price,
img: key.img,
url: key.url,
quantity: key.quantity,
internalSku: key.internalSku,
// custom: key.custom
});
}
}
// setLocalStorage('cartarray', '{"cartId": "","cartlines":'+JSON.stringify(cartarray)+'}');
});
}
我假设你想要什么:
- 您已经有一些
dataArray
- 您希望从服务器为每个项目并行请求额外的数据
- 完成所有请求后,您希望处理结果
$.getJSON
方法returnsjqXHR
object, which implements the Promise接口,所以你可以这样使用它:
$.getJSON(someUrl).then(result => {
// do something with result
});
或这种方式(在 async
函数内):
const result = await $.getJSON(someUrl);
// do something with result
下一步是使您的项目处理异步:
async function processItem(item) {
return await $.getJSON(item.url);
}
并并行处理整个数组:
async function processArray(array) {
const promises = array.map(processItem);
return await Promise.all(promises);
}
请注意,Promise.all
解析为包含每个项目结果的数组,results 的顺序与 promises
初始数组中的顺序相同.
下面是异步处理数组并等待处理完成的完整代码段。请注意,我在我的代码片段中创建了 asyncGetJson
占位符函数来模拟带有超时的真实服务器请求:
// Helper function to simulate random request timeout
function getRandomInt(min, max) {
min = Math.ceil(min);
max = Math.floor(max);
return Math.floor(Math.random() * (max - min) + min);
}
/**
* Not a real request, just a placeholder
* This function multiplies n by 2 and returns it after random timeout
*/
function asyncGetJson(n) {
return new Promise(resolve => {
setTimeout(() => {
resolve(n * 2);
}, getRandomInt(500, 2000));
});
}
async function processItem(item) {
return await asyncGetJson(item);
}
async function processArray(dataArray) {
const promises = dataArray.map(processItem);
return await Promise.all(promises);
}
async function init() {
const dataArray = [1, 2, 3];
console.log('Start');
const result = await processArray(dataArray);
console.log(result);
console.log('Done');
// Here should be your logic that works with results from the server
}
init();
如果您认为每个项目都是一个 async
方法
async function processItem(value) {
var itemUrl = "https://" + window.location.hostname + "/search/?sku=" + value.sku;
var data = await $.getJSON(itemUrl);
return {
sku: data.results[0].sku,
quantity: value.quantity,
price: data.results[0].price,
title: data.results[0].product_title,
img: data.results[0].img,
url: data.results[0].url,
internalSku: data.results[0].sku
};
}
然后等待它们就像对 map
的结果执行 Promise.all
以获取值一样简单。下面同时运行它们并等待所有结果完成。
async function execute(){
var dataArray = JSON.parse(getLocalStorage('cartarray'));
var values = Object.values(dataArray.cartlines);
var new_cart1 = await Promise.all(values.map(processItem));
// do something with new_cart1 which is an array of
// the objects returned from processItem
}