Classe Promise in JavaScript
In questo articolo, spieghiamo la classe Promise in JavaScript.
YouTube Video
Promise
La classe Promise
è una classe per gestire operazioni asincrone. Gestisce i risultati se l'operazione ha successo o gestisce errori se fallisce. Tradizionalmente, venivano utilizzate le funzioni di callback per aspettare la conclusione di un'operazione asincrona, ma Promise
rende questo processo più chiaro e potente.
1const promise = new Promise((resolve, reject) => {
2 setTimeout(() => resolve("Done!"), 1000);
3});
4
5// Displays "Done!" after 1 second
6promise.then(result => console.log(result));
- Questo codice è un esempio di un processo asincrono che mostra "Fatto!" dopo un secondo.
- Per prima cosa, viene creato un nuovo oggetto
Promise
usandonew Promise
. L'argomento è una funzione che accetta due callback:resolve
per il successo ereject
per il fallimento. - Si usa
setTimeout
per chiamareresolve()
dopo un secondo. - Il metodo
then()
dell'oggettopromise
attende il completamento e visualizza il risultato.
- Per prima cosa, viene creato un nuovo oggetto
Struttura di base
Un Promise
è un oggetto che alla fine si conclude con successo o fallimento.
1const promise = new Promise((resolve, reject) => {
2 // Asynchronous operation
3 // Flag indicating whether the operation was successful
4 const success = true;
5
6 if (success) {
7 resolve('Operation successful!');
8 } else {
9 reject('An error occurred');
10 }
11});
- In caso di successo, viene chiamato
resolve()
. - In caso di fallimento, viene chiamato
reject()
.
L'oggetto Promise
ha tre stati.
1promise
2 .then((result) => {
3 console.log(result);
4 })
5 .catch((error) => {
6 console.error(error);
7 })
- In attesa
- Il processo asincrono non è ancora stato completato.
- Completato
- Il processo asincrono è riuscito e il risultato è stato restituito da
resolve()
. Il risultato viene ricevuto usando il metodothen()
.
- Il processo asincrono è riuscito e il risultato è stato restituito da
- Rifiutato
- Il processo asincrono è fallito ed è stato generato un errore tramite
reject()
. L'errore viene ricevuto usando il metodocatch()
.
- Il processo asincrono è fallito ed è stato generato un errore tramite
Metodi then()
e catch()
Utilizzando una Promise
, è possibile definire cosa fare quando un'operazione asincrona si completa. Per questo, si utilizzano i metodi then()
e catch()
.
then()
1const promise = new Promise((resolve, reject) => {
2 resolve('Operation successful!');
3});
4
5promise.then((result) => {
6 console.log(result); // "Operation successful!"
7});
- Il metodo
then()
specifica una funzione da chiamare quando laPromise
ha successo.
catch()
1const promise = new Promise((resolve, reject) => {
2 reject('An error occurred');
3});
4
5promise.catch((error) => {
6 console.error(error); // "An error occurred"
7});
- Il metodo
catch()
specifica una funzione da chiamare quando laPromise
fallisce.
Metodo finally()
1const promise = new Promise((resolve, reject) => {
2 resolve('Operation successful!');
3});
4
5promise
6 .then((result) => {
7 console.log(result);
8 })
9 .catch((error) => {
10 console.error(error);
11 })
12 .finally(() => {
13 console.log('The operation has completed');
14 });
- Il metodo
finally()
definisce il codice che verrà eseguito alla fine, indipendentemente dal successo o fallimento dellaPromise
.
then()
Catena
then()
restituisce una nuova Promise
, quindi puoi catenare il prossimo then()
.
1const promise = new Promise((resolve, reject) => {
2 setTimeout(() => {
3 resolve(1);
4 }, 1000);
5});
6
7promise
8 .then(result => {
9 console.log(result); // 1
10 return result + 1;
11 })
12 .then(result => {
13 console.log(result); // 2
14 return result + 1;
15 })
16 .then(result => {
17 console.log(result); // 3
18 })
19 .catch(error => {
20 console.error(error.message); // Something went wrong
21 });
- In questo codice, il
resolve()
iniziale passa il valore 1 e ogni valore restituito da unthen
viene passato al prossimothen
. - Usando
catch()
, puoi gestire in un solo posto qualsiasi errore che si verifichi nella catena.
Esempio Pratico
Ad esempio, i Promises
vengono spesso utilizzati per recuperare dati da un server. Vediamo un esempio utilizzando l'API fetch()
.
1fetch('https://codesparklab.com/json/example.json')
2 .then(response => {
3 if (!response.ok) {
4 throw new Error('Network error');
5 }
6 return response.json();
7 })
8 .then(data => {
9 console.log(data);
10 })
11 .catch(error => {
12 console.error('Error:', error);
13 });
- In questo codice, poiché
fetch()
restituisce unPromise
, viene utilizzatothen()
per elaborare i dati dopo aver ricevuto una risposta dal server. Gli errori vengono gestiti utilizzandocatch()
.
Gestione di Promesse Multiple
Promise.all()
Per eseguire più Promises
contemporaneamente e procedere solo se tutte hanno successo, utilizza Promise.all()
.
1const promise1 = Promise.resolve(1);
2const promise2 = Promise.resolve(2);
3const promise3 = Promise.resolve(3);
4
5Promise.all([promise1, promise2, promise3])
6 .then((results) => {
7 console.log(results); // [1, 2, 3]
8 })
9 .catch((error) => {
10 console.error('Error :', error);
11 });
then()
viene chiamato solo se tutte lePromises
hanno successo.catch()
viene chiamato se anche solo una fallisce.
Promise.allSettled()
Se vuoi eseguire più Promise
simultaneamente e ottenere tutti i risultati indipendentemente dal successo o dal fallimento, usa Promise.allSettled()
.
1const promise1 = Promise.resolve(1);
2const promise2 = Promise.reject("Failed");
3const promise3 = Promise.resolve(3);
4
5Promise.allSettled([promise1, promise2, promise3])
6 .then((results) => {
7 results.forEach(result => console.log(result));
8 // [
9 // { status: 'fulfilled', value: 1 },
10 // { status: 'rejected', reason: 'Failed' },
11 // { status: 'fulfilled', value: 3 }
12 // ]
13 });
then()
viene chiamato una volta che tutte lePromise
sono state risolte (sia soddisfatte che rifiutate). Ogni risultato include una proprietàstatus
('fulfilled'
o'rejected'
). Anche se alcune falliscono, non influisce sulle altre operazioni.
Promise.race()
Promise.race()
restituisce il risultato della Promise
che si risolve per prima, sia che venga completata sia che venga rifiutata.
1const promise1 = new Promise((resolve) => setTimeout(resolve, 100, 'First'));
2const promise2 = new Promise((resolve) => setTimeout(resolve, 500, 'Second'));
3
4Promise.race([promise1, promise2]).then((result) => {
5 console.log(result); // "First"
6});
- Come in questo esempio, viene restituito il risultato del primo
Promise
completato.
Relazione con async
/await
Utilizzando la sintassi async
/await
è possibile scrivere Promises
in modo più intuitivo. Una funzione async
restituisce sempre un Promise
e await
attende che il Promise
venga risolto.
1async function fetchData() {
2 try {
3 const response = await fetch('https://codesparklab.com/json/example.json');
4 const data = await response.json();
5 console.log(data);
6 } catch (error) {
7 console.error('Error :', error);
8 }
9}
10
11fetchData();
Utilizzando async
/await
in questo modo, le operazioni asincrone possono essere scritte come codice sincrono, rendendolo più facile da leggere.
Riepilogo
Promise
è un oggetto per gestire il successo o il fallimento delle operazioni asincrone.- Gestisci le operazioni di successo con
then()
e gli errori concatch()
. finally()
definisce il codice che viene eseguito alla fine indipendentemente dal successo o dal fallimento.- Puoi gestire più
Promises
insieme utilizzandoPromise.all()
oPromise.race()
. async
/await
è una sintassi per scrivere iPromises
in modo più semplice.
Puoi seguire l'articolo sopra utilizzando Visual Studio Code sul nostro canale YouTube. Controlla anche il nostro canale YouTube.