如何解决node.js异步问题?

代码:

User.findOne({name: name}, function(err, user){
    if(err) {
      console.log(err);
      data.data = "发生未知错误"
      data.status = 1001
    }
    if(!user){
      console.log(user)
      data.data = "用户不存在"
      data.status = 1002
    }
    else{
      user.comparePassword(password, function(err, isMatch) {
        if(err) {
          console.log(err);
          data.data = "发生未知错误"
          data.status = 1001
        }
        if(isMatch) {
          data.data = "登录成功"
          data.status = 1000
        }
        else {
          data.data = "密码不正确"
          data.status = 1003
        }
      })
    } 
    res.send(data)   
  }) 

问题:数据库用的mongodb,建模工具用的mongoose,这里由于nodejs的异步机制,导致最后res.send(data)发送的数据永远是data:{data: '', status: 1000 },请问一下怎么写才能够让代码顺序执行,得到正确的data值?

回复
阅读 4.2k
7 个回答

mongoose现在都是promise的了 建议采用async await

async funcName() {

const user = await User.findOne({}); // await 后面接promise对象
....
....
res.send(...data);

}

需要分别执行 res.send(data) 而不是在最后执行

User.findOne({name: name}, function(err, user){
    if(err) {
      console.log(err);
      data.data = "发生未知错误"
      data.status = 1001
      res.send(data);   
    }
    if(!user){
      console.log(user)
      data.data = "用户不存在"
      data.status = 1002
      res.send(data);   
    }
    else{
      user.comparePassword(password, function(err, isMatch) {
        if(err) {
          console.log(err);
          data.data = "发生未知错误"
          data.status = 1001;
          res.send(data);   
        }
        if(isMatch) {
          data.data = "登录成功"
          data.status = 1000;
           res.send(data);
           res.send(data);   
        }
        else {
          data.data = "密码不正确"
          data.status = 1003;
          res.send(data);   
        }
      })
    } 
  }) 
 

每次符合条件都进行res.send()这样就是顺序执行了
引用文字

user.comparePassword这函数还是个回调函数亲。

优雅一点就不要一直回调回调,推荐使用async处理异步。

感觉这里不是异步的问题吧,data 不是全局的,你的数据状态不会改变啊,应该只是在有耗时的地方的时候,才会出现异步造成的数据问题。要是说顺序执行,可以考虑 promise

这个其实跟用不用Promise类型没啥关系,题主对js的同步和异步理解的不够透彻,建议先把这些理解了再去看看Promise然后用用async去解决回调地狱等问题。

用简单代码来做个例子:

console.log(1);
// syncFun为异步函数
syncFun(()=> {
    console.log(2);
});
console.log(3);

这里输出的结果为
1
3
2

如果这里不能理解的话,然后推荐给你文章看下,不长也不难:
深入核心,详解事件循环机制,以及该作者的前段基础进阶系列文章都值得一看。

如果题主这里能理解,那么你的程序就不难改了

User.findOne({ name: name }, function (err, user) {
  if (err) {
    console.log(err);
    data.data = "发生未知错误"
    data.status = 1001
    res.send(data);  // 修改
  }
  if (!user) {
    console.log(user)
    data.data = "用户不存在"
    data.status = 1002
    res.send(data);  // 修改
  }
  else {
    user.comparePassword(password, function (err, isMatch) {
      if (err) {
        console.log(err);
        data.data = "发生未知错误"
        data.status = 1001
      }
      if (isMatch) {
        data.data = "登录成功"
        data.status = 1000
      }
      else {
        data.data = "密码不正确"
        data.status = 1003
      }
      res.send(data);  // 修改
    })
  }
}) 

希望我的回答对题主有帮助,如有其他问题可回复。
新手答题,如有错误请直接指出,避免误导别人以及纠正自己。

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题
宣传栏