Tratarea erorilor în Promise
Unul dintre avantajele promise-urilor este gestionarea mai simplă a erorilor. Pentru a primi și a trata o eroare, putem folosi funcția catch() a obiectului Promise, care acceptă ca parametru o funcție de tratare a erorii:
const myPromise = new Promise(function(resolve, reject){
console.log("Executarea operațiunii asincrone");
reject("Au fost transmise date incorecte");
});
myPromise.catch( function(error){
console.log(error);
});
Funcția catch() acceptă ca parametru un handler de erori. Parametrul acestei funcții-handler este valoarea care este transmisă în reject().
Ieșirea în consolă:
Executarea operațiunii asincrone
Au fost transmise date incorecte
Generarea erorilor
Mai sus, pentru a notifica despre o eroare care a apărut, a fost apelată funcția reject(). Dar trebuie de menționat că o eroare poate apărea și fără apelarea funcției reject(). Și dacă în operația executată în promise se generează o eroare din diferite motive, atunci întreaga operație se finalizează de asemenea cu o eroare. De exemplu, în următorul cod este apelată o funcție nedefinită getSomeWork():
const myPromise = new Promise(function(resolve){
console.log("Executarea operațiunii asincrone");
getSomeWork(); // apelarea unei funcții inexistente
resolve("Salut lume!");
});
myPromise.catch( function(error){
console.log(error);
});
Deoarece funcția getSomeWork() nu este declarată nicăieri, executarea sarcinii asincrone se va finaliza cu o eroare și nu va ajunge la apelul resolve("Salut lume!"). Prin urmare, va fi activată funcția de tratare a erorilor din catch(), care prin parametrul error va primi informații despre eroarea apărută, și în consola browserului vom vedea un mesaj despre eroare:
Executarea operațiunii asincrone
ReferenceError: getSomeWork is not defined
la index.html:39
în new Promise (<anonymous>)
la index.html:37
Operatorul throw
De asemenea, o eroare poate fi rezultatul apelării operatorului throw, care generează o eroare:
const myPromise = new Promise(function(resolve, reject){
console.log("Executarea operațiunii asincrone");
const parsed = parseInt("Salut");
if (isNaN(parsed)) {
throw "Nu este un număr"; // Generăm o eroare
}
resolve(parsed);
});
myPromise.catch( function(error){
console.log(error);
});
Aici se parsează în număr un șir aleatoriu. Și dacă rezultatul parsării nu reprezintă un număr, atunci prin intermediul operatorului throw generăm o eroare. Aceasta va duce la finalizarea întregii funcții cu o eroare. Și în final, rezultatul va fi tratat de funcția catch:
Executarea operațiunii asincrone
Nu este un număr
În acest caz, funcția handler primește mesajul despre eroare, care este specificat după operatorul throw.
Această situație poate părea artificială, deoarece nu are sens să generăm o eroare în codul de mai sus cu ajutorul throw, deoarece în acest caz putem de asemenea transmite un mesaj despre eroare în funcția reject:
if (isNaN(parsed)) {
reject("Nu este un număr");
}
Totuși, acest operator poate fi folosit într-o funcție externă, pe care o apelăm în cod:
function getNumber(str){
const parsed = parseInt(str);
if (isNaN(parsed)) throw "Nu este un număr"; // Generăm o eroare
else return parsed;
}
const myPromise = new Promise(function(resolve){
console.log("Executarea operațiunii asincrone");
const result = getNumber("salut");
resolve(result);
});
myPromise.catch( function(error){
console.log(error);
});
Aici parsarea șirului în număr este externalizată în funcția - getNumber, totuși, la apelarea acestei funcții în promise, de asemenea din operatorul throw va rezulta o eroare. Și, în consecință, va fi executată funcția catch(), unde va avea loc tratarea erorii.
try..catch
Ca și în cazul general, operațiile care pot genera erori pot fi plasate în construcția try..catch, iar la apariția unei excepții în blocul catch se poate apela funcția reject():
const myPromise = new Promise(function(resolve, reject){
try{
console.log("Executarea operațiunii asincrone");
getSomeWork(); // apelul unei funcții inexistente
resolve("Salut lume!");
}
catch(err){
reject(`A apărut o eroare: ${err.message}`);
}
});
myPromise.catch( function(error){
console.log(error);
});
Ieșirea în consolă:
Executarea operațiunii asincrone
A apărut o eroare: getSomeWork is not defined
Tratarea erorilor cu ajutorul funcției then
În afară de funcția catch pentru primirea informațiilor despre eroare și tratarea ei, de asemenea se poate folosi funcția then() - al doilea său parametru reprezintă handlerul de erori, care primește ca parametru valoarea transmisă din funcția reject:
promise
.then(function(value){
// primirea valorii
},
function(error){
// tratarea erorii
});
Al doilea parametru al funcției then() reprezintă funcția de tratare a erorilor. Prin intermediul parametrului error în funcția-handler putem primi valoarea transmisă în reject sau informații despre eroarea apărută.
Să examinăm următorul exemplu:
function generateNumber(str){
return new Promise(function(resolve, reject){
const parsed = parseInt(str);
if (isNaN(parsed)) reject("valoarea nu este un număr")
else resolve(parsed);
})
.then(function(value){ console.log("Rezultatul operațiunii:", value);},
function(error){ console.log("A apărut o eroare:", error);});
}
generateNumber("23");
generateNumber("salut");
În acest caz, pentru ca în promise să se poată transmite date diferite, acesta este definit ca rezultatul returnat al funcției generateNumber(). Adică în acest caz ieșirea în consolă va fi următoarea:
Rezultatul operațiunii: 23
A apărut o eroare: valoarea nu este un număr