the order of performing asynchronous a few methods in JavaScript

问题: I have a three method in JavaScript NodeJS Sequelize. Calling them is saved as follows: setTransferHistory(senderId, recipientId, amountMoney, transferTitle); setWidgetSt...

问题:

I have a three method in JavaScript NodeJS Sequelize. Calling them is saved as follows:

setTransferHistory(senderId, recipientId, amountMoney, transferTitle);
setWidgetStatus(senderId);
setWidgetStatus(recipientId);

Each method does update or select in the mysql database. It is very important that they are made in this order and it is not always so.

I know that solving this problem uses the word then in the setTransferHistory method, thus:

  function setTransferHistory(
    senderId,
    recipientId,
    amountMoney,
    transferTitle,
  ) {
    Transaction.create({
      id_sender: senderId,
      id_recipient: recipientId,
      date_time: getTodayDate(),
      amount_money: amountMoney,
      transfer_title: transferTitle,
    }).then(() => {
      setWidgetStatus(senderId);
      setWidgetStatus(recipientId);
    });
  }

...but I don't want these two methods to be included in this method. I would like to just write it one below the other.


回答1:

All you need to do is return the promise from setTransferHistory that create gives you, so that you can invoke then on the result of the call:

function setTransferHistory(senderId, recipientId, amountMoney, transferTitle) {
  return Transaction.create({
//^^^^^^
    id_sender: senderId,
    id_recipient: recipientId,
    date_time: getTodayDate(),
    amount_money: amountMoney,
    transfer_title: transferTitle,
  });
}

setTransferHistory(senderId, recipientId, amountMoney, transferTitle).then(() => {
//                                                                   ^^^^^
  setWidgetStatus(senderId);
  setWidgetStatus(recipientId);
});

回答2:

Since Transaction.create returns a Promise, you can have setTransferHistory returns that, and defer the execution of setWidgetStatus after setTransferHistory's promise is fulfilled. So with:

const setTransferHistory = (
  senderId,
  recipientId,
  amountMoney,
  transferTitle
) =>
  Transaction.create({
    id_sender: senderId,
    id_recipient: recipientId,
    date_time: getTodayDate(),
    amount_money: amountMoney,
    transfer_title: transferTitle
  });

You can have either:

setTransferHistory(/* args ... */).then(() => {
  setWidgetSatus(senderId);
  setWidgetSatus(recipientId);
});

Or use await - that works with promise, as soon you use it in an async function, setTransferHistory doesn't need to be async:

async function foobar() {
  await setTransferHistory(/* args ... */);

  setWidgetSatus(senderId);
  setWidgetSatus(recipientId);
}

Of course at this point you could just use directly Transation.create, but it's up to you, if you want to add a layer of abstraction.


回答3:

Nowadays when dealing with promises, good practice is using the async/await keywords. They basically allow you to run your asynchronous code in a synchronous manner. Using them, your code would look like this :

async function setTransferHistory(senderId, recipientId, amountMoney, transferTitle) {
     return await Transaction.create({
       id_sender: senderId,
       id_recipient: recipientId,
       date_time: getTodayDate(),
       amount_money: amountMoney,
       transfer_title: transferTitle,
     });
}

await setTransferHistory(senderId, recipientId, amountMoney, transferTitle);
setWidgetStatus(senderId);
setWidgetStatus(recipientId);

The await keyword stops the execution of the function and waits for the result of Transaction.create() and async is needed in order to use await inside the function.

Hope this helps.

  • 发表于 2019-01-21 16:22
  • 阅读 ( 200 )
  • 分类:网络文章

条评论

请先 登录 后评论
不写代码的码农
小编

篇文章

作家榜 »

  1. 小编 文章
返回顶部
部分文章转自于网络,若有侵权请联系我们删除