2017-03-19 8 views
6

इसलिए मेरे पास एक वादा है जो सर्वर से डेटा एकत्र करता है लेकिन केवल एक समय में 50 प्रतिक्रियाएं एकत्र करता है। मेरे पास इकट्ठा करने के लिए 250 प्रतिक्रियाएं हैं Iवादे का लूप कैसे बनाएं

मैं कर सकता था एक साथ की तरह

नीचे
new Promise((resolve, reject) => { 
    resolve(getResults.get()) 
    }) 
    .then((results) => { 
    totalResults.concat(results) 
    return getResults.get() 
    }) 
    .then((results) => { 
    totalResults.concat(results) 
    return getResults.get() 
    }).then((results) => { 
    totalResults.concat(results) 
    return getResults.get() 
    }) 

इस उदाहरण में मैं केवल 250 परिणाम की जरूरत है तो यह एक प्रबंधनीय समाधान लगता है, लेकिन वहाँ एक पाश में वादों concating का एक तरीका है बस concate वादे। तो मैं 5 बार एक लूप चलाता हूं और हर बार अगले वादे को चलाता हूं।

क्षमा करें मैं वादे के लिए नया हूं और यदि यह कॉलबैक था तो मैं यही करता हूं।

+1

क्या 'वादा' वापस आ गया है? –

+0

मैं इसके लिए [async] (http://caolan.github.io/async/) लाइब्रेरी को देखने की अनुशंसा करता हूं। यह आपके जीवन को आसान बना देगा। 'Async.eachLimit' कार्यक्षमता को देखें। – forrestmid

+0

@forrestmid नहीं, यह वादे के साथ अच्छी तरह से काम नहीं करता है। – Bergi

उत्तर

7

यदि आप लूप करना चाहते और वादों serialise, किसी भी अन्य get कॉल को क्रियान्वित नहीं एक बार एक विफल रहता है, तो यह पाश की कोशिश:

function getAllResults() { // returns a promise for 250 results 
    let totalResults = []; 
    let prom = getResults.get(); 
    for (let i = 0; i < 4; i++) { // chain four more times 
     prom = prom.then(results => { 
      totalResults = totalResults.concat(results); 
      return getResults.get(); 
     }); 
    } 
    return prom.then(results => totalResults.concat(results)); 
} 

ध्यान दें कि आप promise construction anti-pattern से बचना चाहिए। यहां new Promise का उपयोग करना आवश्यक नहीं है।

त्रुटि शर्तों से निपटने के लिए उपर्युक्त फ़ंक्शन द्वारा दिए गए वादे पर कॉल .catch() पर भी विचार करें।

अंत में, ध्यान रखें कि concat उस सरणी को संशोधित नहीं करता है जिसे आप इसे कॉल करते हैं। यह समेकित सरणी देता है, इसलिए आपको उस वापसी मान को असाइन करने की आवश्यकता है। अपने कोड में आप रिटर्न वैल्यू असाइन नहीं करते हैं, इसलिए कॉल का कोई प्रभाव नहीं पड़ता है।

+2

आप 'prom = Promise.resolve ([]) 'से शुरू करना चाहते हैं ताकि आपको' get' कॉल को डुप्लिकेट करने की आवश्यकता न हो और concatenation, और 5 ठीक से गिनती। – Bergi

+0

धन्यवाद, यह अच्छी तरह से काम कर रहा है। उत्कृष्ट सुझाव –

8

शायद आपको केवल Promise.all विधि की आवश्यकता है। प्रत्येक अनुरोध के लिए आपको एक वादा करना चाहिए और इसे एक सरणी में रखना चाहिए, फिर आप सब कुछ all विधि में लपेटें और आप कर चुके हैं।

उदाहरण (यह सोचते हैं कि getResults.get रिटर्न एक वादा): Promise.all at MDN

संपादित आप वादों इस तरह से दिए गए डेटा का उपयोग कर सकते हैं:

let promiseChain = []; 
for(let i = 0; i <5; i++){ 
    promiseChain.push(getResults.get()); 
} 

Promise.all(promiseChain) 
    .then(callback) 

आप इस विधि के बारे में अधिक पढ़ सकते हैं :

function callback(data){ 
    doSomething(data[0]) //data from the first promise in the chain 
    ... 
    doEventuallySomethingElse(data[4]) //data from the last promise 
} 
+0

आप ओपी का प्रस्ताव कैसे करेंगे इस दृष्टिकोण का उपयोग कर प्राप्त() कॉल से परिणाम प्राप्त करते हैं? – rasmeister

+0

कृपया संपादन को देखें;) – Phugo

+0

धन्यवाद लेकिन यह वही 50 परिणाम लौटा रहा है 5 बार –

संबंधित मुद्दे