NodeJS 使用await/async运算符时返回响应的主体

mmvthczy  于 2023-02-08  发布在  Node.js
关注(0)|答案(1)|浏览(164)

我试图将一个返回Promise的函数转换为使用await/async的函数(据我所知,它返回一个隐式Promise)。
此函数“ Package ”对https.request对象的调用,关键部分是返回响应主体的resolve(body)

promise_it = (data) => {

  // throws FATAL
  if (!data) {throw new Error('data is missing');}

  return new Promise((resolve, reject) => {

    let postData = JSON.stringify(data);

    let options = {
      hostname: 'httpbin.org',
      port: 443,
      path: '/post',
      method: 'POST',
      headers: {
        // 'Content-Type': 'application/json',
        // Accept: 'application/json'
          'Content-Type': 'application/x-www-form-urlencoded',
          'Content-Length': postData.length
        }
    };
    
    const https = require('https');
    let req = https.request(options, (res) => {
    
      let body = [];
      res.on('data', function(chunk) {
          body.push(chunk);
      });
      res.on('end', function() {
    
        try {
            body = JSON.parse(Buffer.concat(body).toString());
            }
        catch(e) {
            console.error(e.message)
            reject(e);
        }
    
        resolve(body);

      });
    
    });
    
    req.on('error', (e) => {
      console.error(e);
      reject(e)
    });
    
    req.write(postData);
    req.end();

  });

}
    
  try {
    data = {firstName: 'Donald', lastName: 'Duck'}
    const who = promise_it(data)
    who
      .then(r => console.info('INFO:',r))
      .catch(e => console.error('ERROR:',e));
  } 
  catch (error) {
    console.error('FATAL:',error)  
  }

函数按预期工作。
我把它翻译成一个async/await函数:

async_it = async (data) => {

  if (!data) {throw new Error('data is missing');}

  let postData = JSON.stringify(data);

  let options = {
      hostname: 'httpbin.org',
      port: 443,
      path: '/post',
      method: 'POST',
      headers: {
      // 'Content-Type': 'application/json',
      // Accept: 'application/json'
          'Content-Type': 'application/x-www-form-urlencoded',
          'Content-Length': postData.length
      }
  };

  const https = require('https');

  let req = https.request(options, (res) => {

        let body = [];
        res.on('data', function(chunk) {
            body.push(chunk);
        });

        res.on('end', function() {

            try {
                body = JSON.parse(Buffer.concat(body).toString());
                // how do i return the body?
            }
            catch(e) {
                console.error('HERE:',e.message)
                throw e;
            }

        });
  });

  req.on('error', (e) => {
        console.error('THERE:',e.message)
  });

  req.write(postData);
  req.end();

}

(async () => {

  try {
    data = {firstName: 'Donald', lastName: 'Duck'}
    const who = await async_it(data)
    console.info('INFO:',who)
  } 
  catch (error) {
    console.error('FATAL:',error)  
  }

})();

但是我似乎找不到返回body的方法,我错过了什么?

lnlaulya

lnlaulya1#

不幸的是,https.request使用“最后一个参数回调”Node.js样式,因此不可能将其原样用于async/await。
例如,您可以像nodejs - How to promisify http.request? reject got called two times那样创建一个 Package 器,然后您可以像这样使用它:

try {
  const body = await httpsRequest(options, postData);
  return body;
} catch (e) {
  console.error('THERE:',e.message);
}

但是提到的 Package 器并不比您当前的 Package 器(Promise版本)少多少。

相关问题