2017-01-02 67 views
0

我有一個基本的貓鼬身​​份驗證,與bcryptjs哈希密碼。 bcrypt和mongoose都會答應。在我routes.js我有以下腳本,獲取數據庫找到用戶後卡住:如何調用返回承諾的函數?

routes.post('/auth', (req, res)=> { 
    User.findOne({'local.username': req.body.username}) 
     .then(
      user=> Promise.all([user, user.validate(req.body.password)]) 
     ) 
     .then(
      results => { 
       console.log(results); 
       res.json({token: jwt.sign({id: results[0]._id}, config.secret)}); 
      } 
     ) 
     .catch(
      err=> console.log(err) 
     ); 
}); 

正如你可以看到我找到用戶,然後試圖調用其validate方法(它被調用) ,但它不會解決承諾也不會拋出錯誤。在我的user.js的定義我UserSchema我有這樣的代碼來比較口令:

UserSchema.methods.validate = function (password) { 
    return bcrypt.compare(password, this.local.password); 
}; 

這就是所謂的,但返回的承諾,好像它消失,問題沒有解決,結果變量從未登錄。

還有一件事,如果我編輯的用戶驗證代碼如下:

UserSchema.methods.validate = function (password) { 
    return bcrypt.compare(password, this.local.password).then(
     results => { 
      console.log(results) 
     } 
    ) 
}; 

我得到真正的登錄到控制檯,因此它必須正常工作,但我不希望在這裏解決我的承諾,我想在我的路由器上附加.then(...),這不可能嗎?

我在做什麼錯?

UPDATE:

如果我把它的工作原理routes.js比較方法,但是這不是我想做的事,我想保持它在user.js的,但我認爲這可能會指出我仍然看不到的問題。我想我必須立即根據承諾調用then(),但我不明白爲什麼。

User.findOne({'local.username': req.body.username}) 
     .then(
      user=> Promise.all([user, bcrypt.compare(req.body.password,user.local.password)]) 
     ) 
     .then(
      results => { 
       console.log(results); 
       res.json({token: jwt.sign({id: results[0]._id}, config.secret)}); 
      } 
     ) 
     .catch(
      err=> console.log(err) 
     ); 
+0

''Promise.all([用戶,user.validate(req.body.password)])''應''Promise.all( [Promise.resolve(user),user.validate(req.body.password)])'' – MatthieuLemoine

+0

@MatthieuLemoine是的,這似乎是合理的,但試過了,它不起作用:S – godzsa

+0

不確定,但我認爲你的validate方法應該也解決了承諾。 –

回答

-1

你沒有對Promise做任何事情,你在那裏打電話。

而不是

user=> Promise.all([user, user.validate(req.body.password)]) 

你應該那麼:

user.validate(req.body.password) 
.then(results => { 
    // Do stuff with results here... 
}); 
+1

我認爲這是相同的,因爲Promise.all()返回一個由.then() – godzsa

+0

處理的承諾而這也不起作用 – godzsa

+1

他正在從回調中返回'Promise.all(...)',這就是足以做到。 – Bergi

0

首先,爲什麼在這裏使用Promise.all?特別是我不認爲需要做像Promise.resolve(user)這樣的事情。如果不知道如何user.validate工作,我會寫什麼樣子

routes.post('/auth', (req, res)=> { 
    let userId 

    User.findOne({'local.username': req.body.username}) 
    .then(user => { 
     userId = user._id 
     return user.validate(req.body.password) 
    }) 
    .then(results => { 
     console.log(results); 
     res.json({token: jwt.sign({id: userId}, config.secret)}); 
    }) 
    .catch(err => console.log(err)) 
}); 
+0

我試過了。它不適用於我,這就是爲什麼我嘗試Promise.all()後,這也不起作用 – godzsa

+0

爲什麼'Promise.all'?因爲這是[好得多的模式](http://stackoverflow.com/a/28250704/1048572)比[醜陋的全局'userId'變量](http://stackoverflow.com/a/28250700/1048572)。 – Bergi

+0

會部分同意你的看法。會爭論什麼更醜陋,創建範圍變量來路由處理程序或創建一個不需要的承諾。 – Srle