首页 > 解决方案 > 尽管使用了 Async 模块,为什么这些函数仍然异步执行

问题描述

我决定使用 Async 模块按我想要的顺序填充 mongodb 集合。
如果没有 Async,代码可以工作,但文档没有以正确的顺序插入:

function insertRowInBLD(ref, riskstatements, maximpact, controleffectiveness, recommendedriskrating, frequency, impact, validatedreviewriskrating, rationalforriskadjustment) {
    const businessLineDashboard = new BusinessLineDashboard({
        ref: ref,
        riskstatements: riskstatements,
        maximpact: maximpact,
        controleffectiveness: controleffectiveness,
        recommendedriskrating: recommendedriskrating,
        frequency: frequency,
        impact: impact,
        validatedreviewriskrating: validatedreviewriskrating,
        rationalforriskadjustment: rationalforriskadjustment
    });
    businessLineDashboard.save()
        .then(row => {
            console.log('row ' + businessLineDashboard.ref + ' has been inserted succesfully');
        })
        .catch(err => {
            console.log('err: ', err);
        });
}

我希望按该顺序插入“文档”。由于 JavaScript 的异步特性,这并没有发生。所以我尝试使用

异步系列:

function fillBLD() {


  async.series([
    function (callback) {
      console.log("Task 1");
      insertRowInBLD('R01', 'Disclosure of data due to deliberate action by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 1 Inserted');
    },
    function (callback) {
      console.log("Task 2");
      insertRowInBLD('R02', 'Corruption of data due to deliberate action by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 2 Inserted');
    },
    function (callback) {
      console.log("Task 3");
      insertRowInBLD('R03', 'Unavailability of data due to deliberate action by internal actor', 'E. Not significant', 'Partially effective', '', '', '', '', '')
      callback(null, 'Row 3 Inserted');
    },
    function (callback) {
      console.log("Task 4");
      insertRowInBLD('R04', 'Disclosure of data due to attack of the communications link by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 4 Inserted');
    },
    function (callback) {
      console.log("Task 5");
      insertRowInBLD('R05', 'Corruption of data due to attack of the communications link by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 5 Inserted');
    },
    function (callback) {
      console.log("Task 6");
      insertRowInBLD('R06', 'Unavailability of data due to attack of the communications link by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 6 Inserted');
    },
    function (callback) {
      console.log("Task 7");
      insertRowInBLD('R07', 'Disclosure of data due to social engineering by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 7 Inserted');
    },
    function (callback) {
      console.log("Task 8");
      insertRowInBLD('R08', 'Corruption of data due to social engineering by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 8 Inserted');
    },
    function (callback) {
      console.log("Task 9");
      insertRowInBLD('R09', 'Unavailability of data due to social engineering by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 9 Inserted');
    },
    function (callback) {
      console.log("Task 10");
      insertRowInBLD('R10', 'Disclosure of data due to  erroneous useby internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 10 Inserted');
    },
    function (callback) {
      console.log("Task 11");
      insertRowInBLD('R11', 'Corruption of data due to erroneous useby internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 11 Inserted');
    },
    function (callback) {
      console.log("Task 12");
      insertRowInBLD('R12', 'Unavailability of data due to erroneous useby internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 12 Inserted');
    },
    function (callback) {
      console.log("Task 13");
      insertRowInBLD('R13', 'Disclosure of data due to  unauthorized access by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 13 Inserted');
    },
    function (callback) {
      console.log("Task 14");
      insertRowInBLD('R14', 'Corruption of data due to unauthorized access by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 14 Inserted');
    },
    function (callback) {
      console.log("Task 15");
      insertRowInBLD('R15', 'Unavailability of data due to unauthorized access by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 15 Inserted');
    },
    function (callback) {
      console.log("Task 16");
      insertRowInBLD('R16', 'Disclosure of data due to  attack by malicious code by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 16 Inserted');
    },
    function (callback) {
      console.log("Task 17");
      insertRowInBLD('R17', 'Corruption of data due to attack by malicious code by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 17 Inserted');
    },
    function (callback) {
      console.log("Task 18");
      insertRowInBLD('R18', 'Unavailability of data due to erroneous useby internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 18 Inserted');
    },
    function (callback) {
      console.log("Task 19");
      insertRowInBLD('R19', 'Disclosure of data due to improper change/maintenance by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 19 Inserted');
    },
    function (callback) {
      console.log("Task 20");
      insertRowInBLD('R20', 'Corruption of data due to improper change/maintenance by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 20 Inserted');
    },
    function (callback) {
      console.log("Task 21");
      insertRowInBLD('R21', 'Unavailability of data due to improper change/maintenance by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 21 Inserted');
    },
    function (callback) {
      console.log("Task 22");
      insertRowInBLD('R22', 'Disclosure of data due to loss or theft of device by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 22 Inserted');
    },
    function (callback) {
      console.log("Task 23");
      insertRowInBLD('R23', 'Unavailability of data due to loss or theft of device by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 23 Inserted');
    },
    function (callback) {
      console.log("Task 24");
      callback(null, 'Row 24 Inserted');
    },
    function (callback) {
      console.log("Task 25");
      insertRowInBLD('R25', 'Corruption of data due to bypassing physical security by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')

      callback(null, 'Row 25 Inserted');
    },
    function (callback) {
      console.log("Task 26");
      insertRowInBLD('R26', 'Unavailability of data due to bypassing physical security by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 26 Inserted');
    },
    function (callback) {
      console.log("Task 27");
      insertRowInBLD('R27', 'Disclosure of data due to third-party security breach by external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 27 Inserted');
    },
    function (callback) {
      console.log("Task 28");
      insertRowInBLD('R28', 'Corruption of data due to  third-party security breach by external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 28 Inserted');
    },
    function (callback) {
      console.log("Task 29");
      insertRowInBLD('R29', 'Unavailability of data due to third-party security breach by external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 29 Inserted');
    },
    function (callback) {
      console.log("Task 30");
      insertRowInBLD('R30', 'Disclosure of data due to unmanaged legal, regulatory and contractual requirements by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 30 Inserted');
    },
    function (callback) {
      console.log("Task 31");
      insertRowInBLD('R31', 'Corruption of data due to unmanaged legal, regulatory and contractual requirements by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 31 Inserted');
    },
    function (callback) {
      console.log("Task 32");
      insertRowInBLD('R32', 'Unavailability of data due to unmanaged legal, regulatory and contractual requirements by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')

      callback(null, 'Row 32 Inserted');
    },
    function (callback) {
      console.log("Task 33");
      callback(null, 'Row 33 Inserted');
    },
    function (callback) {
      console.log("Task 33");
      insertRowInBLD('R33', 'Unavailability of data due to component failure by internal/external factor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')

      callback(null, 'Row 33 Inserted');
    },
    function (callback) {
      console.log("Task 34");
      insertRowInBLD('R34', 'Unavailability of data due to exhaustion of resources by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 34 Inserted');
    },
    function (callback) {
      console.log("Task 35");
      insertRowInBLD('R35', 'Unavailability of data due to environmental & natural disasters by external factor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')

      callback(null, 'Row 35 Inserted');
    },
    function (callback) {
      console.log("Task 36");
      insertRowInBLD('R36', 'Lack of accountability due to tampering with audit trails by internal/external actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
      callback(null, 'Row 36 Inserted');
    },
  ], function (error, results) {
    console.log(results);
  });
}

但是,虽然控制台日志是同步执行的,并且结果会按顺序传递给回调函数:

任务 1 任务 2 任务 3 任务 4 任务 5 任务 6 任务 7 任务 8 任务 9 任务 10 任务 11 任务 12 任务 13 任务 14 任务 15 任务 16 任务 17 任务 18 任务 19 任务 20 任务 21 任务 22 任务 23 任务 24 任务 25任务 26 任务 27 任务 28 任务 29 任务 30 任务 31 任务 32 任务 33 任务 33 任务 34 任务 35 任务 36 ['插入第 1 行','插入第 2 行','插入第 3 行','插入第 4 行','已插入第 5 行、“已插入第 6 行”、“已插入第 7 行”、“已插入第 8 行”、“已插入第 9 行”、“已插入第 10 行”、“已插入第 11 行”、“已插入第 12 行”、“已插入第 13 行”已插入','插入第 14 行','插入第 15 行','插入第 16 行','插入第 17 行','插入第 18 行','插入第 19 行','已插入第 20 行、“已插入第 21 行”、“已插入第 22 行”、“已插入第 23 行”、“已插入第 24 行”、“已插入第 25 行”、“已插入第 26 行”、“已插入第 27 行”、“已插入第 28 行”已插入”、“已插入第 29 行”、“已插入第 30 行”、“已插入第 31 行”、“已插入第 32 行”、“已插入第 33 行”、“已插入第 33 行”、“已插入第 34 行”、“已插入第 35 行” , '插入第 36 行' ]插入第 31 行,插入第 32 行,插入第 33 行,插入第 33 行,插入第 34 行,插入第 35 行,插入第 36 行]插入第 31 行,插入第 32 行,插入第 33 行,插入第 33 行,插入第 34 行,插入第 35 行,插入第 36 行]

insertRowInBLD 函数仍未按我定义的顺序执行:

R01行插入成功 R02行插入成功 R03行插入成功 R04行插入成功 R05行插入成功 R07行插入成功 R08行插入成功 R09行插入成功 R06行已插入成功 R12 行已成功插入 R19 已成功插入 R14 已成功插入 R17 已成功插入 R22 已成功插入 R28 已成功插入 R33 已成功插入 R25 已成功插入成功 R30 行已成功插入 R35 行已成功插入 R10 行已成功插入 R15 行已成功插入 R20 行已成功插入成功插入 R26 行 成功插入 R31 行 成功插入 R36 行 成功插入 R11 行 成功插入 R16 行 成功插入 R21 行 成功插入 R27 行 成功插入 R32 行R13 插入成功 R18 插入成功 R23 插入成功 R29 插入成功 R34 插入成功插入成功 R18 行已成功插入 R23 行已成功插入 R29 行已成功插入 R34 行已成功插入插入成功 R18 行已成功插入 R23 行已成功插入 R29 行已成功插入 R34 行已成功插入

我真的不明白为什么它们仍然异步执行。知道可能是什么原因造成的,我该如何解决?
谢谢!

标签: javascriptnode.jsmongodbasynchronousasync.js

解决方案


您当前正在立即调用回调,而不是等待插入完成。这意味着您将立即开始所有保存,并且无法控制它们何时完成。相反,您希望等待一个完成后再进行下一个,为此您需要使用 businessLaneDashboard.save() 创建的承诺。特别是,您需要从 insertRowInBLD 中返回它:

function insertRowInBLD(/* args */) {
    const businessLineDashboard = new BusinessLineDashboard(
      //etc
    );
    return businessLineDashboard.save();
}

使用 promise,您可以使用它的 .then 方法在调用回调之前等待。

    function (callback) {
      console.log("Task 1");
      insertRowInBLD('R01', 'Disclosure of data due to deliberate action by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
        .then(() => callback(null, 'Row 1 Inserted'));
    },

虽然现在我们正在使用 Promise,但我会放弃 async.series 的东西,而只使用一系列 Promise,如下所示:

insertRowInBLD('R01', 'Disclosure of data due to deliberate action by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
  .then(() => {
    return insertRowInBLD('R02', 'Corruption of data due to deliberate action by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '')
  })
  .then(() => {
    return insertRowInBLD('R03', 'Unavailability of data due to deliberate action by internal actor', 'E. Not significant', 'Partially effective', '', '', '', '', '')
  })
  // etc

如果您可以选择 async/await,那么使用 Promise 可以变得更加简单:

async function fillBLD() {
  await insertRowInBLD('R01', 'Disclosure of data due to deliberate action by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '');
  await insertRowInBLD('R02', 'Corruption of data due to deliberate action by internal actor', 'E. Not significant', 'Partially effective', 'Low', '', '', '', '');
  await insertRowInBLD('R03', 'Unavailability of data due to deliberate action by internal actor', 'E. Not significant', 'Partially effective', '', '', '', '', '');
  // etc
}

推荐阅读