2016-04-13 15 views
0

Ich habe eine Versprechenskette, die zur Zeit mit sehr einfacher Fehlerbehandlung läuft. Wenn ein Schritt fehlschlägt, werden die nachfolgenden Schritte nicht ausgeführt. Ich möchte in der Lage sein, die Versprechenskette zu einem späteren Zeitpunkt fortzusetzen, wenn ein Fehler auftritt, und sie sollte dort beginnen, wo sie aufgehört hat. DieseWie man modulare js Versprechenketten baut?

ist, was meine aktuellen Code wie folgt aussieht:

// controller.js 
var failure = false; 
QueryFactory.step1()      // Step 1 
    .then(function(msg){ 
     if(failure == false){ 
     console.log("Finished Step 1"); 
     return QueryFactory.step2(); 
     } 
    }, function(err){ 
     console.log(err); 
     failure = true; 
    }) 
    .then(function(msg){     // Step 2 
     if(failure == false){ 
     console.log("Finished Step 2"); 
     return QueryFactory.step3(); 
     } 
    }, function(err){ 
     console.log(err); 
     failure = true; 
    }) 
    .then(function(msg){     // Step 3 
     if(failure == false){ 
     console.log("Finished Step 3"); 
     } 
    }, function(err){ 
     console.log(err); 
     failure = true; 
    }) 

Und meine Fabrik sieht wie folgt aus:

// QueryFactory.js 
step1 = function(){ 
    var deferred = $q.defer(); 
    $http.post('/task', {step_num: 1}) 
     .then(function(data)){ 
     deferred.resolve(data); 
     }, function(err){ 
     deferred.reject(err); 
     }); 
    return deferred.promise; 
} 
// step2 and step3 are similar 

Aber vielleicht gibt es einen besseren Weg, dies zu schreiben, für die Modularität zu ermöglichen? Angenommen, Schritt 2 würde fehlschlagen, wie kann ich einen Weg entwerfen, so dass ein Benutzer auf eine Schaltfläche klicken kann, um später die Kette aus Schritt 2 fortzusetzen?

+0

Ihre "Kette" gibt keine Daten von einem Schritt an den nächsten Schritt weiter. Außerdem werden sie alle nacheinander ausgeführt, unabhängig von "Erfolg" oder "Fehlschlag". – Amit

+0

Also, wie empfehlen Sie, dass ich das richtig mache? –

+1

Vor allem vermeiden Sie die [latente Antipattern] (http://stackoverflow.com/q/23803743/1048572)! – Bergi

Antwort

1

Werfen Sie einen Blick auf die difference between .then(…).catch(…) and .then(…, …). In diesem Fall würden Sie, indem Sie den zweiten Rückruf an then übergeben, den letzten Schritt überspringen und nicht dort fortfahren, wo Sie aufgehört haben. Was Sie suchen ist

QueryFactory.step1() 
.then(function(msg) { 
    console.log("Finished Step 1 without error"); 
    return msg; 
}, function(err) { 
    console.log(err); 
    … 
}).then(function() { 
    return QueryFactory.step2(); 
}).then(function(msg) { 
    console.log("Finished Step 2 without error"); 
    return msg; 
}, function(err) { 
    console.log(err); 
    … 
}).then(function() { 
    return QueryFactory.step3(); 
}).then(function(msg) { 
    console.log("Finished Step 3 without error"); 
    return msg; 
}, function(err) { 
    console.log(err); 
    … 
}).then(function(res) { 
    console.log("everything is finished"); 
}).catch(function(err){ 
    console.error("something bad happened", err); 
}); 

(Alternativ können Sie auch eine einfache .catch anstelle des then mit dem Rückruf verwenden, die Sie, ob ein Schritt ohne Fehler beendet erklärt, wenn Sie nicht über diese Protokolle benötigen)

Nun, was sind diese im Code? Es ist für Ihre Anforderung

Ich will das Versprechen Kette zu einem späteren Zeitpunkt fortsetzen können, wenn ein Fehler ist

In den Abschnitten finden Sie der Fehler Griff benötigen, und ein Versprechen für das fehlerfreie Ergebnis des fehlgeschlagenen Schrittes, z durch Wiederholen. Dieses Versprechen würde sich erst zu dieser "späteren Zeit" einstellen - Sie können auf eine Benutzerbestätigung des Fehlers, eine Zeitüberschreitung oder was immer Sie wollen warten.

Sobald dieses Versprechen, das Sie von dem Fehlerrückruf zurückgebracht haben, zurückgeht, wird die Kette fortgesetzt.