Javascript - 异步/等待数据集保存在循环中

标签 javascript velo

我正在创建一个筹款平台,但遇到了一些问题,我认为这些问题是由 for 循环中的 Async/await 引起的。

从概念上讲,假设我有一系列人们 promise 的捐款金额。当代码执行时,它将获取筹款目标并循环捐赠,对任何未收费的捐赠 promise 进行收费,直到 promise 用完或达到筹款目标。然后代码更新我的数据库以显示使用了哪些新的捐赠 promise ,或者有多少 promise 可用,因此将来不会重新收费。该代码单独工作正常,但如果我尝试循环它,则会导致错误。

我认为问题在于,循环的 future 迭代在数据集保存并识别出一些捐赠 promise 已被使用之前开始执行。我想我需要让循环的 future 迭代等待,直到保存先前的迭代?

是否有适当的方法来处理这个问题以及如何完成?

谢谢!

for (let i = 0; i < 2; i++) {
    chargeDonations(proj_sub_id, projItem.price, applications.length, project_fees);
}

function chargeDonations(proj_sub_id, price, quantity, fees) {
    wixData.query("Sponsorships")
    .eq("proj_sub_id", proj_sub_id)
    .ne("allFunds", true)
    .find()
    .then( (results) => {   
        let sponsorships = results.
        let toCharge = (price + fees);

    for (let i = 0; i < sponsorships.length; i++) {
        let amount_charged = sponsorships[i].amountCharged;
        amount_charged = amount_charged || 0;
        let remaining_sponsorship = (sponsorships[i].amount - amount_charged);
        let net_amount = (remaining_sponsorship - calculateFeesStripePhil(remaining_sponsorship, 1));
        let net_toCharge = (toCharge + calculateFeesStripePhil(toCharge));
        let sponsorships_sum = sponsorships.sum("amount");

    if ((toCharge - net_amount) > 0) {
        console.log("Donation Amount" + remaining_sponsorship);
        console.log("Net Amount" + net_amount);
        toCharge -= net_amount;
        console.log("Still to be Charged: " + toCharge);
        sponsorships_sum -= remaining_sponsorship;

    $w("#dataset2").setFilter( wixData.filter()
        .eq("_id", sponsorships[i]._id)) 
        .then( () => {
        $w("#dataset2").setFieldValue('amountCharged', (remaining_sponsorship + amount_charged));
        $w("#dataset2").setFieldValue('allFundsUsed', true);
        console.log("Saved Amount Charged");
        $w("#dataset2").save();
        });

        }
     else {                 
        console.log("Sponsorship Amount " + (toCharge / .921 - 0.3).toFixed(2));
        console.log("Net Amount: " + toCharge);

            $w("#dataset2").setFilter( wixData.filter()
        .eq("_id", sponsorships[i]._id)) 
        .then( () => {
        $w("#dataset2").setFieldValue('amountCharged', (toCharge + amount_charged));                        
        console.log("Saved Amount Charged");
        $w("#dataset2").save();                     
            }); 
        break;
                }
                }

        });

}

最佳答案

是的 - 您的假设是正确的,即在前一个循环迭代完成之前调用下一个循环迭代。 使用 async/awaitPromise.all(/* array of Promise*/) 应该可以解决这个问题。

我相信正确的方法是这样做:

for (let i = 0; i < 2; i++) {
    await chargeDonations(...);
}

async function chargeDonations(...) {
    ...
}

此外,我会检查WixCode API用于 dataset API 中的哪些函数(例如 savesetFilter...)和 $w API返回一个 Promise 并用 async/await block 包装它。

以下是我试图让您的代码更易于阅读和理解的一些内容:

for (let i = 0; i < 2; i++) {
  await chargeDonations(...);
}

async function filterBySubId(filter){
  /*...*/
}
async function filterBySponsorshipId(filter){
  /*...*/
}

async function chargeDonations(proj_sub_id, price, quantity, fees) {
    const results = await filterBySubId();

    let sponsorships = results;
    let toCharge = (price + fees);

    for (let i = 0; i < sponsorships.length; i++) {
      /* I would also put this block in a function and return values */
      let amount_charged = sponsorships[i].amountCharged;
      amount_charged = amount_charged || 0;
      let remaining_sponsorship = (sponsorships[i].amount - amount_charged);
      let net_amount = (remaining_sponsorship - calculateFeesStripePhil(remaining_sponsorship, 1));
      let net_toCharge = (toCharge + calculateFeesStripePhil(toCharge));
      let sponsorships_sum = sponsorships.sum("amount");
      /* end of calculations block */

      if ((toCharge - net_amount) > 0) {
        console.log("Donation Amount" + remaining_sponsorship);
        console.log("Net Amount" + net_amount);
        toCharge -= net_amount;
        console.log("Still to be Charged: " + toCharge);
        sponsorships_sum -= remaining_sponsorship;

        await filterBySponsorshipId(/* your filter */)

        $w("#dataset2").setFieldValue('amountCharged', (remaining_sponsorship + amount_charged));
        $w("#dataset2").setFieldValue('allFundsUsed', true);
        console.log("Saved Amount Charged");
        await $w("#dataset2").save();

      } else {
        console.log("Sponsorship Amount " + (toCharge / .921 - 0.3).toFixed(2));
        console.log("Net Amount: " + toCharge);

        await filterBySponsorshipId(/* your filter */)
        $w("#dataset2").setFieldValue('amountCharged', (toCharge + amount_charged));
        console.log("Saved Amount Charged");
        await $w("#dataset2").save();
        break;
      }
    }
}

希望它对您有意义并能帮助您, 干杯!

关于Javascript - 异步/等待数据集保存在循环中,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48523732/

相关文章:

javascript - React-Native-Navigation:未定义已使用但尚未注册

javascript - 我有一段 html/javascript 需要在新页面中打开,但我使用的是 Wix.com

javascript - HtmlUnit:anchor.click 不会更改页面

javascript - 如何在 javascript 中将异步调用转换为同步调用?

javascript - 控制 console.log 的函数而不返回

custom-element - 将自定义元素连接到 wix 和 corvid 中的数据集

react-native - 假设 AppDelegate 中不存在某些代码,则 react-native-navigation 安装说明存在问题

javascript - typescript 错误: type this is not assignable to type this

javascript - 遍历 div 内的输入

javascript - 如何在 Wix 中使用 JavaScript 代码构建动态搜索表单?