在forEach中使用await/async被坑

昨天项目中,一个数组中的值需要异步获取,最后发现老是不对,打了好多断点,最最后才意识到可能是forEach中await没有获取到值, 网上已经有很多答案了,我自己再记录一遍,加深印象.

问题现象

  Object.values(formInstance).forEach(async (ele) => {
    const { name, checked, value } = ele;
    const eleVal = name.indexOf("CHECKBOX") !== -1 ? String(checked) : value;
    formData.push({
        FieldID: name,
        FieldValue: name === "DATETEXT2" ? await getDate() :eleVal,
      });
  });

现象就是formData中最后DATETEXT2没有. forEach平常使用得挺多的, 里面跟一个callbackFn, 结果没有意识到callbackFn 不能是异步function.

官方解释

根据文档https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/forEach 里面说的

forEach 的回调函数期望是一个同步函数,官方都说了,肯定搞不成噻, 哎, 确实好久没有看官方文档了.

替换方案

  1. For....of

async getData() {
    const formData = [];
    const formValue = [];
    for(const ele of Object.values(formInstance)) {
        const { name, checked, value } = ele;
        const eleVal = name.indexOf("CHECKBOX") !== -1 ? String(checked) : value;
        if (name === "DATETEXT2") {
          formData.push({
            FieldID: "DATETEXT2",
            FieldValue: await getDate(),
          });
          formValue["DATETEXT2"] = await getDate();
        } else {
          formData.push({
            FieldID: name,
            FieldValue: eleVal,
          });
          formValue[name] = eleVal;
        }
    }
}
  1. Array.map

  Object.values(formInstance).map(async (ele) => {
    const { name, checked, value } = ele;
    const eleVal = name.indexOf("CHECKBOX") !== -1 ? String(checked) : value;
    formData.push({
      FieldID: name,
        FieldValue: name === "DATETEXT4" ? await getDate() : eleVal,
    })
  });

总结

日常的工作中,数组的操作使用频率相当高, 常用的几个还是要更加熟悉啊,多看文档.

参考:

https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/Array/forEach

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/map

https://plainenglish.io/blog/async-await-foreach#2-the-arrayreduce-solution


版权声明:本文为u014049463原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。