我们如何使用 Async,在 nodeJS 中最好的方法是什么

How do we use Async, and what is the best way in nodeJS

我试图将查询传递到我的数据库,然后将结果发送到我的客户端,但看起来请求是异步的,因为我的请求发生在我的 post 请求 returns 值。

如何设置等待请求?

我的数据库连接

var connection = mysql.createConnection({
    host: 'localhost',
    user: 'root',
    password: 'my_password',
    database: 'MEETME'
});

connection.connect(function(err) {
    if (err) {
        console.log("error while connecting to database");
        console.log(err.code);
    }
});

// function that query database <-------

function queryDatabase(userQuery) {
    connection.query(userQuery, function(err, result) {
        if (err) {
            throw err;
        }
        console.log("before");
        return result;
    });
}

这是我的post请求

//POST
app.post('/signin', function(request, response) {
    var query = queryDatabase("SELECT EMAIL FROM MEMBER WHERE ID_MEMBER = 3");
    console.log(query);
    console.log("after");
    response.end(query, 200);
});

控制台中的结果是:

undefined
after
before

将 queryDatabase 函数的实现更改为 return 承诺。任何 return 承诺的功能都可以等待。

function queryDatabase(userQuery){
     return new Promise((resolve,reject) => {
        connection.query(userQuery, function(err, result){
            if(err){
              reject(err);
            }
            console.log("before");
            resolve(result);
        }); 
     }); 
}



app.post('/signin', async function(request, response){
    var query = await queryDatabase("SELECT EMAIL FROM MEMBER WHERE ID_MEMBER = 3");
    console.log(query);
    console.log("after");
    response.end(query, 200);
});

欢迎来到 Node.js,这里的一切都是异步的,除非您明确地以一种将一个事件级联到另一个事件的方式构建代码,否则代码没有义务 运行以任何特定顺序排列。

如果您不熟悉此概念,我强烈建议您学习 Promises 作为组织代码的方式。这将许多棘手的编程封装到一些简洁、整洁的方法中,并使链接、扇出和扇入实际上非常简单。

例如,用Sequelize重写,一个使用promises的数据库层:

function queryDatabase(userQuery){
   console.log("before");

   return connection.query(userQuery);
}

return承诺,那是用来上链的。如果你不这样做,你 必须 接受回调参数并将其链接起来。 Return 值在很大程度上被忽略了:

function queryDatabase(userQuery, cb){
   connection.query(userQuery, function(err, result){
      cb(err, result);
   });
   console.log("before");
}

您可以看到已经有很多废话,如果您需要以此为基础甚至更多。在回调驱动代码中插入可选步骤是 tricky.

Promises 让您的代码最终看起来像这样:

app.post('/signin', function(request, response){
  queryDatabase("SELECT EMAIL FROM MEMBER WHERE ID_MEMBER = 3")
    .then(function(results) {
      console.log(results);
      console.log("after");
      response.end(query, 200);
    });
});

catch 在一个地方修补错误处理来处理错误也是微不足道的。