2013-12-13 12 views
16

पर असफल असफलता मैं रिमोट कॉल्स की एक श्रृंखला को हल करने के लिए कुछ स्थानीय डेटा भरने की कोशिश कर रहा हूं।
जब हर वादा हल हो जाता है, तो मैं डेटा लोड करता हूं और आगे बढ़ता हूं।

विधि $q.all([]) वास्तव में यह करता है:

 $q.all([ 
      this.getUserInfo(11) 
       .then(function (r) { 
        results.push(r) 
       }), 

      this.getUserConns() 
       .then(function (r) { 
        results.push(r) 
       }), 

      this.getUserCtxs() 
       .then(function (r) { 
        results.push(r) 
       }) 
     ]) 
     .then(function() { 
      console.log(results) 
     }) 


समस्या है, इस कोड को लचीला नहीं है।
यदि इनमें से कोई भी कॉल विफल रहता है, तो कोई भी मछली नहीं पाता है!

आज़माएं/कैच बयान में कॉल रैपिंग, बस $q.all() का कारण बनता है पूरी तरह से प्रवेश की अनदेखी करने, यहां तक ​​कि (समारोह में console.log ध्यान दें) जब नाकाम रहने नहीं ...

 $q.all([ 
      this.getUserInfo2(11) 
       .then(function (r) { 
        results.push(r) 
       }), 

      function() { 
       try { 
        this.getUserGroups() 
         .then(function (r) { 
          console.log(r) 
          results.push(r) 
         }) 
       } 
       catch (err) { 
        console.log(err) 
       } 
      }, 
     ]) 
     .then(function() { 
      console.log(results) 
     }) 

आउटपुट:

[वस्तु]


किसी भी संकेत पर कि मैं इसे लचीला होने के लिए कैसे लपेट सकता हूं?


@dtabuenc के लिए धन्यवाद, मैं एक कदम आगे चला गया हूं। त्रुटि कॉलबैक को कार्यान्वित करना, मैं श्रृंखला के तोड़ने से बच सकता हूं, और हल किए गए वादे के मूल्यों को धक्का दे सकता हूं।

हालांकि, कंसोल पर एक बुरा अपवाद अभी भी प्रदर्शित होता है ... अगर मैं एसिंक अनुरोधों को आजमा नहीं सकता तो मैं इससे कैसे छुटकारा पा सकता हूं?

कोलर कोड

return $q.all([ 

      this.getUserInfo(user_id) 
       .then(function (r) { 
        results['personal_details'] = r 
       }), 

      this.getUserConns() 
       .then(
        function (r) { 
        results['connections'] = r 
        }, 
        function(err) { 
         console.log(err) 
        }) 

     ]) 
     .then(function() { 
      return (results) 
     }) 

कॉल प्राप्त करने वाला कोड (एक अपवाद के साथ इंजेक्षन)

getUserConns: function() { 

     return __doCall(ws.getUserConnections, {}) 
      .then(function(r) { 

       // very generic exception injected 
       throw new Error 

       if (r && r.data['return_code'] === 0) { 
        return r.data['entries'] 
       } 
       else { 
        console.log('unable to retrieve the activity - err: '+r.data['return_code']) 
        return null 
       } 
      }) 
    }, 

उत्तर

23

यह काम करेगा लेकिन त्रुटियों को सरणी में भी धक्का देगा।

function push(r) { 
    results.push(r); 
} 

$q.all([ 
    this.getUserInfo(11).then(push).catch(push), 
    this.getUserConns().then(push).catch(push), 
    this.getUserCtxs().then(push).catch(push) 
]) 
.then(function() { 
    console.log(results); 
}) 

तुम भी वादे की अपनी समझ में सुधार करना चाहिए, आप कभी नहीं वादों से try-catch का उपयोग करना चाहिए - जब वादों का उपयोग कर, आप (सब कुछ परोक्ष एक try बताते हैं) .catch() विधि का उपयोग करें। यह सामान्य त्रुटियों के साथ-साथ एसिंक्रोनस त्रुटियों के लिए भी काम करता है।


आप पूरी तरह से त्रुटियों को अनदेखा करना चाहते हैं:

function push(r) { 
    results.push(r); 
} 

function noop() {} 

$q.all([ 
    this.getUserInfo(11).then(push).catch(noop), 
    this.getUserConns().then(push).catch(noop), 
    this.getUserCtxs().then(push).catch(noop) 
]) 
.then(function() { 
    console.log(results); 
}) 
+0

वास्तव में, मैं अभी भी कोणीय, वादे और यहां तक ​​कि जेएस पर एक नौसिखिया हूं, और मैं हर दिन नई चीजें सीखने से खुश हूं! .catch() विधि अभी भी मेरे अंतिम उदाहरण पर अपवाद को "अवरुद्ध" नहीं करती है, लेकिन मुझे लगता है कि यह मेरे आदर्श परिणाम में सबसे नज़दीक है। धन्यवाद! – domokun

+1

@domokun कोणीय वादे गलत तरीके से पकड़े गए अपवादों की रिपोर्ट करते हैं, वादे – Esailija

+0

का उल्लंघन नहीं करते हुए वादा/ए + की भावना का उल्लंघन करते हैं ... मुझे लगता है ... Thx फिर से! – domokun

0

मुझे यकीन है कि आप लचीला द्वारा क्या मतलब है नहीं कर रहा हूँ। यदि कोई वादा विफल रहता है तो आप क्या करना चाहते हैं?

आपका प्रयास-पकड़ काम नहीं करेगा क्योंकि वादा असीमित रूप से विफल हो जाएगा।

हालांकि आप then() कॉल पर दूसरे पैरामीटर के रूप में एक त्रुटि हैंडलर में पास कर सकते हैं और जो कुछ भी आप चाहते हैं उसे करें।

+0

ठीक है, मैं त्रुटि कॉलबैक के बारे में भूल गया। यह इस अर्थ में लचीला है कि श्रृंखला में बाधा नहीं आती है, और यही वह है जो मैं चाहता था। हालांकि, अगर मैं इसे पकड़ नहीं पाता हूं तो मैं अपवाद को छुपा नहीं सकता ... मैं – domokun

+0

को समझाने के लिए अपना प्रश्न अपडेट करूंगा, मुझे नहीं लगता कि आप HTTP त्रुटियों को पकड़ सकते हैं। वे हमेशा कंसोल पर दिखाई देंगे। यह इस पर ध्यान दिए बिना कि आप कोणीय का उपयोग कर रहे हैं या नहीं। – dtabuenc

+0

यह सच है, और मुझे परेशान नहीं करता है। मुझे वास्तव में परेशान करता है जो कंसोल पर अपवाद प्रदर्शित कर रहा है। कृपया मेरे अपडेट किए गए प्रश्न – domokun

0

ही यहां मुद्दा। एक तो प्रतिक्रिया के अंदर:: लूप के साथ आप के उन लोगों के लिए

var tracks = []; 
var trackDfds = []; 
for(var i = 0; i < res.items.length; i++){ 
    var fn = function() { 
     var promise = API.tracks(userId, res.items[i].id); 
     return promise.then(function (res) { 
      if (res.items.length) { 
       tracks.push(res.items); 
      } 
     }).catch(angular.noop); 
    }; 
    trackDfds.push(fn()); 
} 
$q.all(trackDfds) 
    .then(function (res) { 
     console.log(tracks); 
    }); 
1

मुझे लगता है कि यह करने के लिए आसान है:

$q.all([ 
mypromise1.$promise.catch(angular.noop), 
mypromise2.$promise.catch(angular.noop), 
mypromise1.$promise.catch(angular.noop) 
]) 
.then(function success(data) { 
//..... 
}); 
0

@ Esailija का जवाब एक समस्या का एक समाधान की तरह लगता है। आप समस्या में मुख्य योगदानकर्ता के बाहर समस्या का समाधान नहीं कर सकते: $q

प्रत्येक then (द्वितीय तर्क) और $q.reject(...) डालने के लिए कॉलबैक को अस्वीकार करना थोड़ा सा बुद्धिमान लगता है।

उदाहरण:

$q.all([ 
    this.getUserInfo(11).then(
     function (response) { // UI data preparation for this part of the screen }, 
     function (response) { 
      $q.reject(response); 
     } 
    ), 
    // ... 
]) 
.then(
    function() { 
     // all good 
    }, 
    function() { 
     // at least one failed 
    } 
) 

यह विशेष रूप से इंगित किया जाता है जब यूआई मॉडल सभी ajax कॉल पर निर्भर करता है।

व्यक्तिगत रूप से मुझे लगता है कि यह आगे बढ़ने का सुरक्षित तरीका है, क्योंकि ज्यादातर बार आप कुछ सर्वर संदेशों को अस्वीकार कॉलबैक पर कुछ टोस्ट घटक को धक्का देना चाहते हैं, या उपयोगकर्ता को किसी भी तरह से चेतावनी देना चाहते हैं (कतार 7 AJAX कॉल इसका मतलब यह नहीं है कि आप कुछ भी नहीं दिखा सकते हैं क्योंकि 1 असफल रहा - इसका मतलब है कि आप स्क्रीन के कुछ क्षेत्र को दिखाने में सक्षम नहीं होंगे - जिसके लिए उपयोगकर्ता को विशेष प्रतिक्रिया की आवश्यकता है)।