【问题标题】:How to avoid a callback in promise如何避免 promise 中的回调
【发布时间】:2018-04-01 17:46:05
【问题描述】:

我是 NodeJS 和 JavaScript 的新手。我严重陷入了一个问题: 我想生成“一些文本”的 QR 图像,在生成它之后,我想查询我的 MySQL 数据库并将图像插入数据库。 问题是SOLDAIR 模块的QRCode.toDataURL 处于运行状态,并且在从.toDataUrl 函数返回QR 图像之前调用查询。 因此会导致错误。

我尝试了所有方法,包括承诺、嵌套承诺、计数器、if 语句等,但我无法找到解决方案。

我的代码:

router.post('/generateTicket', (req,res) => {
  const query1 = `SELECT * FROM booking ORDER BY  bookingID DESC LIMIT 1`;
  const query2 = `INSERT INTO ticket (ticket_image,BookingID) SET ?`;
  let bookingID;
  let count;
  let ticket_data = {};
  Promise.using(mysql.getSqlConn(), conn => {
    conn.query(query1).then(resultOfQuery1 => {
      bookingID = resultOfQuery1[0].BookingID;
      count = resultOfQuery1[0].PeopleCount;

      console.log("ID = " + bookingID + " people count = "+count);

      promiseToCreateQRcode().then(function (URLfromResolve) {
        console.log("the url is " + URLfromResolve );
      }).catch(function (fromReject) {
        console.log("Rejected "+ fromReject);
      }); // catch of promise to create QR

    }).catch(err => {
      res.json({ status: 500, message: 'Error Occured in query 1 ' + err });
    }); // catch of query 1
  });
});


var opts = {
  errorCorrectionLevel: 'H',
  type: 'image/png',
  rendererOpts: {
    quality: 0.3
  }
};

let promiseToCreateQRcode = function () {
  let QRImage;
  return new Promise(function (resolve,reject) {
    QRCode.toDataURL('text', function (err, url) {
    if (err) throw err
      console.log("\n"+url+"\n");
      QRImage = url;
    });

    if (QRImage)
      resolve(QRImage);
    else
      reject("error occured in url");
  });
};

如你所见,程序跳转到 if 语句并且二维码图像尚未生成,因此它进入“拒绝”:

【问题讨论】:

  • 我从来没有遇到过 Promise.using() 之类的东西。
  • @SatishKumar, Promise.using() 是 Bluebird 的静态方法。

标签: javascript node.js callback promise bluebird


【解决方案1】:

试试这个,

let promiseToCreateQRcode = function () {
return new Promise(function (resolve,reject) {
    QRCode.toDataURL('text', function (err, url) {
        if (err){
          reject(err); // or some message
        } else {
           resolve(url);
      }
    });
  });
};

这种方式promise只有在toDataURL返回二维码时才会被解析。

【讨论】:

    【解决方案2】:

    看看How do I convert an existing callback API to promises?。需要在异步回调中调用resolve或reject!

    function promiseToCreateQRcode() {
        return new Promise(function(resolve,reject) {
            QRCode.toDataURL('text', function (err, url) {
                if (err) {
                    reject(err);
                } else {
                    console.log("\n"+url+"\n");
                    resolve(url);
                }
            });
        });
    }
    

    像使用 cannot work 一样使用这个额外的 QRImage 变量。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2016-06-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-11-09
      • 1970-01-01
      相关资源
      最近更新 更多