将回调转换为异步抛出错误

时间:2018-02-07 16:51:11

标签: node.js typescript async-await es6-promise nodemailer

以下代码有效:

  var smtpConfig = {
    host: 'localhost',
    port: 465,
    secure: true, // use SSL
    selfSigned: true
  };

  // create reusable transporter object using the default SMTP transport
  var transporter = nodemailer.createTransport(smtpConfig);

  // setup e-mail data with unicode symbols
  var mailOptions = {
    from: '"Some One" <someone@example.com>', // sender address
    to: 'validuser@company.com', // list of receivers
    subject: 'Hello', // Subject line
    text: 'Hello world ?', // plaintext body
    html: '<b>Hello world ?</b>' // html body
  };

  transporter.sendMail(mailOptions, (error, info) => {
      if (error) {
          console.log(error);
      } else {
          console.log(info);
      }
  });

但是,如果我使用节点

中的util.promisify
  var sendMail = promisify(transporter.sendMail);
  var info = await sendMail(mailOptions);

我得到了一个例外

TypeError: Cannot read property 'getSocket' of undefined
  at sendMail (c:\Users\user\Source\project\node_modules\nodemailer\lib\mailer\index.js:143:25)
  at sendMail (internal/util.js:230:26)

问题出在sendMail中,因为&#39;这个&#39;未定义:

/**
 * Sends an email using the preselected transport object
 *
 * @param {Object} data E-data description
 * @param {Function?} callback Callback to run once the sending succeeded or failed
 */
sendMail(data, callback) {
    let promise;

    if (!callback && typeof Promise === 'function') {
        promise = new Promise((resolve, reject) => {
            callback = shared.callbackPromise(resolve, reject);
        });
    }

    if (typeof this.getSocket === 'function') { <-- this is undefined
        this.transporter.getSocket = this.getSocket;
        this.getSocket = false;
    }

在普通函数上使用util.promisify工作。我想这是因为我在类方法上使用util.promisify

有没有办法实现这一点,还是我需要使用async function sendMail重载扩展exting类

1 个答案:

答案 0 :(得分:2)

要解决此特定情况,您可以使用

await sendMail.call(transporter, mailOptions) // provide a context

当然,查看transporter.sendMail()的来源,它已经支持调用then而无需包含util.promisify(),因此您可以直接await:< / p>

await transporter.sendMail(mailOptions) // omit callback to kick in promise-style async