需要帮助相关的asynchronous函数执行stream程(await,promises,node.js)
如果你帮我解决以下情况,我将不胜感激。
给定function:
async function getAllProductsData() { try { allProductsInfo = await getDataFromUri(cpCampaignsLink); allProductsInfo = await getCpCampaignsIdsAndNamesData(allProductsInfo); await Promise.all(allProductsInfo.map(async (item) => { item.images = await getProductsOfCampaign(item.id); })); allProductsInfo = JSON.stringify(allProductsInfo); console.log(allProductsInfo); return allProductsInfo; } catch(err) { handleErr(err); } }
这个函数在服务器启动时被触发,它收集来自其他站点的活动信息:获取数据(getDataFromUri()),然后从数据名称和id(getCpCampaignsIdsAndNamesData())中提取,然后获取每个活动的产品图像(getProductsOfCampaign()) ;
我也express.app与下面的一段代码:
app.get('/products', async (req, res) => { if (allProductsInfo.length === undefined) { console.log('Pending...'); allProductsInfo = await getAllProductsData(); } res.status(200).send(allProductsInfo); });
问题描述:
- 启动服务器,等待几秒钟,直到getAllProductsData()被执行,执行'/ products'GET请求,一切正常!
-
启动服务器和IMMEDIATELY消防'/产品'GET请求'(为此目的,我添加了与console.log('等待…')expression式),我得到损坏的结果:它包含所有的广告系列名称,ids,但NO图像数组。
- [{“id”:“1111”,“name”:“Some name”},{“id”:“2222”,“name”:“其他名字”}]
- [{“id”:“1111”,“name”:“某个名字”,“图像”:[“URI”,“URI”…]} …]
我将非常感谢您的帮助:
- 解释asynchronous执行发生的stream程,以及为什么不等待图像数组添加到对象而发送结果?
- 如果你知道一些有用的文章/规格部分涵盖我的话题,我会感激。
谢谢。
使用全局variablesallProductsInfo
存在一个巨大的问题,然后触发多个使用asynchronous的并发函数。 这就创造了各种各样的竞争条件,而且你必须认为自己只有没有图像数据才是 幸运的 。
你可以通过使allProductsInfo
成为一个局部variables来解决这个问题,或者至less不用它来存储getDataFromUri
和getCpCampaignsIdsAndNamesData
的中间结果 – 为这些variables使用不同的(local!)variables。
然而,即使你这样做,你可能多次发射getAllProductsData
,这不应该导致错误,但仍然是低效的。 在全局variables中存储承诺要简单得多,只需要一次调用信息收集过程来初始化一次 ,然后每次都等待 – 当它已经满足时不会引起注意。
async function getAllProductsData() { const data = await getDataFromUri(cpCampaignsLink); const allProductsInfo = await getCpCampaignsIdsAndNamesData(allProductsInfo); await Promise.all(allProductsInfo.map(async (item) => { item.images = await getProductsOfCampaign(item.id); })); console.log(allProductsInfo); return JSON.stringify(allProductsInfo); } const productDataPromise = getAllProductsData(); productDataPromise.catch(handleErr); app.get('/products', async (req, res) => { res.status(200).send(await productDataPromise); });
当然,你也可能只想在加载数据之后启动服务器(或者添加/products
path),直到服务器状态为止。 你也应该考虑在承诺被拒绝之后发生什么事情 – 不知道handleErr
是handleErr
。