2016-08-13 5 views
0

1. Wie schreibt man Versprechen im Knoten, so dass ich meine gewünschte Ausgabe bekommen kann. Ich bin ein Neuling und würde jede mögliche Hilfe/Vorschlag schätzen.Wie schreibe ich eine synchrone Funktion in Node mit Promises

// This is my core function 

var compareData = function(userIdArray) { 
    return new Promise(function(resolve, reject) { 
    var missingArray = new Array(); 
    userIdArray.forEach(function(id) { 
     var options = { 
     method: 'POST', 
     url: 'http://localhost:6006/test1', 
     headers:{ 
     'content-type': 'application/json' }, 
      body: { email: id }, 
      json: true 
     }; 

     request(options, function (error, response, body) { 
     missingArray.push(body); 
     }); 
    }); 
    resolve(missingArray); 
    }); 
} 


//I'm calling my function here 

compareData(userIdArray) 
.then(function(missingArray){ 
    console.log("The Body is: "+ missingArray); 
}); 

/* I expect the console.log to print the missingArray with data from my POST call, 
but it prints an empty array. Can someone please tell me how to do this synchronously. 
I'm pretty new to Node and finding it difficult to understand.*/ 
+3

Versprechen sind per Definition async, Sie können * das Versprechen * synchron zurückgeben, aber der versprochene Wert ist ** immer ** aufgelöst async. – Thomas

+1

Ein Promise kann nicht synchron sein, und synchroner Code benötigt im Allgemeinen kein Versprechen, also macht das wenig Sinn? – adeneo

+0

Sie lösen sofort mit dem 'missingArray' var in Ihrem Versprechen. 'request' ist async, also wird Ihr Push aufgerufen, nachdem das Versprechen aufgelöst wurde, daher das leere Array in der Funktion. Was Sie brauchen, ist ein 'Promise.all', das sich um Anfragen für alle userIds dreht. –

Antwort

2

mit bluebird und request-promise:

var Promise = require('bluebird'); 
var request = require('request-promise'); 

var compareData = function(userIdArray) { 
    //Promise.all(): 
     //takes an array of promises (and/or values), 
     //returns a promise of the resolved array 
    return Promise.all( 
     userIdArray.map(function(id){ 
      return request({ 
       method: 'POST', 
       url: 'http://localhost:6006/test1', 
       headers: { 'content-type': 'application/json' }, 
       body: { email: id }, 
       json: true 
      }); 
     }) 
    ); 
} 

ist es etwas, das eine weitere Erklärung braucht?

0

Ohne Bibliotheken und request vorausgesetzt, kehrt nicht bereits ein Versprechen

var compareData = function(userIdArray) { 
    return Promise.all(
     userIdArray.map(function(id) { 
      var options = { 
       method : 'POST', 
       url  : 'http://localhost:6006/test1', 
       headers : { 'content-type': 'application/json' }, 
       body : { email: id }, 
       json : true 
      }; 

      return new Promise(function(resolve, reject) { 
       request(options, function(error, response, body) { 
        if (error) { 
         reject(); 
        } else { 
         resolve(body); 
        } 
       }); 
      }); 
     }) 
    ); 
} 

compareData(userIdArray).then(function(missingArray) { 
    console.log(missingArray); 
}); 
2

Wenn Sie externe Bibliotheken nicht verwenden möchten, wie pro @Thomas Antwort können Sie native Promises direkt verwenden - und es ist nicht zu viel ausführlicher

var compareData = function compareData(userIdArray) { 
    return Promise.all(userIdArray.map(function (id) { 
     return new Promise(function (resolve, reject) { 
      var options = { 
       method: 'POST', 
       url: 'http://localhost:6006/test1', 
       headers: { 
        'content-type': 'application/json' 
       }, 
       body: { 
        email: id 
       }, 
       json: true 
      }; 
      return request(options, function (error, response, body) { 
       error ? reject(error) : resolve(body); 
      }); 
     }); 
    })); 
}; 

compareData(userIdArray) 
.then(function (missingArray) { 
    console.log("The Body is: " + missingArray); 
}); 

Oder, wie dieser Knoten, die modernere Code verarbeiten kann:

var compareData = userIdArray => 
    Promise.all(userIdArray.map(id => 
     new Promise((resolve, reject) => 
      request({ 
       method: 'POST', 
       url: 'http://localhost:6006/test1', 
       headers: { 
        'content-type': 'application/json' 
       }, 
       body: { 
        email: id 
       }, 
       json: true 
      }, (error, response, body) => error ? reject(error) : resolve(body)) 
     ) 
    )); 

compareData(userIdArray) 
.then(missingArray => 
    console.log("The Body is: "+ missingArray) 
); 
+0

Danke @Jaromanda X. Das funktioniert gut, aber es braucht viel Zeit, um das Versprechen zurückzugeben. Ich rufe diese compareData-Funktion innerhalb meiner POST-Anforderung auf, und die Anforderung überschreitet das Zeitlimit, bevor dieses Versprechen aufgelöst wird und die Antwort gesendet wird. Irgendein Vorschlag? –

Verwandte Themen