2013-09-26 48 views
1

我正在使用一個需要我傳入「驗證」功能的庫。在這個功能中,我需要驗證一些輸入,如果通過則返回true,否則返回false如何在函數中執行異步工作,並在完成後從該函數返回值?

問題是我需要檢查一個用戶是否存在於數據庫中用於此驗證函數,並且Mongoose調用帶有結果的回調函數。如果在回調中我return它只是從回調函數而不是我的驗證函數返回。

... 
validate: function (username) { 
    User.findOne({ username: username }, function (err, user) { 
     if (user) 
      // User exists so we should return false from the validate function 
     else 
      // User does not exist so we should return true from validate. 
    }); 
} 

我想使用異步庫來解決這個問題,但異步時也調用一個回調,當它完成!

+0

在方孔中的圓釘,不起作用。你可以僞造異步,但你不能僞造同步。 – dandavis

回答

2

簡答:你不能。

對於所有意圖和目的 JavaScript是單線程的。是的,你有回調和多線程的存在(setTimeout,setInterval,事件回調),但你不能跳出回調並回到相同的功能。

我的建議是在validate被調用之前嘗試預處理此驗證,以便您在validate之內有「yay或ney」結果。

+0

當。在調用此函數之前,我沒有在數據庫中搜索的值。圖書館應該以何種方式進行修改,以便完成這項工作?我會修改它,並提交一個拉請求,如果我可以但我不知道如何改變這種行爲。如果傳遞給validate函數的參數之一是「done」回調函數或其他東西? – Chev

+0

我不知道工作流程,但是您可以在更改值時(或稍後)執行查找(因此在驗證時您有一個校驗和值),或者引入用戶的前置步驟在驗證可用之前需要執行。 (我知道你在節點中,但例如,直到用戶按下用戶名字段旁邊的「檢查」才能啓用提交按鈕) –

0

您可以使用promises來實現此目的。

var q = require('q'); 

validate: function (username) { 
    var deferred = q.defer(); 
    User.findOne({ username: username }, function (err, user) { 
     if (err){return deferred.reject(err)} 
     if (user) 
     // User exists so we should return false from the validate function 
     deferred.resolve(false); 
     else 
     // User does not exist so we should return true from validate. 
     deferred.resolve(true) 
    }); 
    return deferred.promise; 
} 

然後使用驗證函數如下。

validate('username').then(function(result){ 
    if (result) 
    console.log('user doesnt exist'); 
    else 
    console.log('user exists'); 

}, function(err){ 
    if(err) 
     console.log('Error', err); 
}) 
+0

我無法返回承諾。庫期望true或false從validate函數返回。 – Chev

相關問題