Úvod do promises v JavaScriptu

Už víte, že použití callback modelu asynchronnosti snadno vede k situaci callback hell. Proto byl v JavaScriptu zaveden nový model s názvem promises (promise). Pojďme se tento model naučit.

Promise je objekt, do kterého jako parametr předáváme funkci, uvnitř které je třeba umístit náš asynchronní kód:

javascriptlet promise = new Promise(function() {
  // asynchronní kód
});

Jak vidíte, zapsal jsem objekt s promise do proměnné promise. Na nějakém jiném místě kódu mohu na této proměnné aplikovat metodu then, předáním do ní funkce s kódem, který má být proveden po dokončení asynchronního kódu, zapsaného při vytváření této promise:

javascriptpromise.then(function() {
  // provedeno po dokončení asynchronního kódu
});

Zní to matoucí, tak se podívejme na příklad. Předpokládejme, že mám takový asynchronní kód:

javascriptsetTimeout(function() {
  let result = [1, 2, 3, 4, 5];
}, 3000);

Předpokládejme, že pro něj chci vyřešit naši hlavní úlohu asynchronnosti: provést nějaký kód po spuštění časovače. Přitom nechci umístit tento kód do samotného časovače a chci, aby se do tohoto kódu nějak dostal výsledek, který jsem zapsal do proměnné result. Obecně jsme tuto úlohu řešili v předchozích lekcích pomocí callbacků a odběrů. Pojďme se nyní podívat, jak to udělat pomocí promises.

Nejprve je třeba zabalit náš asynchronní kód do promise:

javascriptlet promise = new Promise(function() {
  setTimeout(function() {
    let result = [1, 2, 3, 4, 5];
  }, 3000);
});

To však nestačí. Musíme explicitně uvést, že náš asynchronní kód skončil. S tím nám pomůže speciální funkce dokončení, která automaticky přichází jako první parametr funkce, pokud je uveden:

javascriptlet promise = new Promise(function(resolve) { // uvedeme parametr
  setTimeout(function() {
    let result = [1, 2, 3, 4, 5];
  }, 3000);
});

Pomocí funkce dokončení můžeme explicitně uvést promise, že asynchronní kód skončil. K tomu musíme tuto funkci zavolat na požadovaném místě:

javascriptlet promise = new Promise(function(resolve) {
  setTimeout(function() {
    let result = [1, 2, 3, 4, 5];
    resolve(); // dokončíme promise
  }, 3000);
});

Přitom, pokud chceme předat nějaký výsledek asynchronního kódu ven, můžeme jej předat jako parametr naší funkci dokončení:

javascriptlet promise = new Promise(function(resolve) {
  setTimeout(function() {
    let result = [1, 2, 3, 4, 5];
    resolve(result); // předáváme výsledek
  }, 3000);
});

Lze se samozřejmě zbavit mezilehlé proměnné:

javascriptlet promise = new Promise(function(resolve) {
  setTimeout(function() {
    resolve([1, 2, 3, 4, 5]);
  }, 3000);
});

Nyní na jakémkoli jiném místě můžeme zavolat metodu then naší promise:

javascriptpromise.then(function() {
  // spustí se po dokončení promise
});

Výsledek práce promise přijde jako první parametr funkce, pokud jej budeme chtít uvést:

javascriptpromise.then(function(result) {
  console.log(result); // vypíše pole s výsledkem
});
Задание 1

Vytvořte promise, uvnitř které bude zpoždění 5 sekund, po kterém se promise má dokončit, a svým výsledkem vrátit nějaký text. Vypište tento text na obrazovku.