Úkol asynchronní programování
Jednoduchý úkol, který objasňuje základní principy asynchronního programování
3. Řešení
Třída Objednávka
namespace asynchronni_programovani_ukol.Models { public class Objednavka //Třída Objednávka, která má vlastnosti NazevPizzy a Stav { public string NazevPizzy { get; set; } = ""; public string Stav { get; set; } = "Čeká ve frontě"; } }
Třída Objednavka slouží k evidenci toho, co se v naší kuchyni děje. Má vlastnost Stav, která se bude v čase měnit, aniž bychom museli vytvářet novou instanci objektu.
Razor komponenta
@page "/" <PageTitle>Pizzerie Async</PageTitle> <h1>Pizzerie U C#</h1> <p>Objednejte si více pizz najednou. Díky asynchronnímu kódu se při objednání více pizz najednou aplikace nezasekne.</p> <div class="mb-3"> <button class="btn btn-primary" @onclick='() => ZpracovatObjednavku("Šunková", 3000)'> <!--Tlačíko zavolá metodu ZpracovatObjednavku() s parametry: název pizzy a doba pečení--> Objednat Šunkovou (3s) </button> <button class="btn btn-warning" @onclick='() => ZpracovatObjednavku("Sýrová", 5000)'> Objednat Sýrová (5s) </button> <button class="btn btn-danger" @onclick='() => ZpracovatObjednavku("Pálivá", 2000)'> Objednat Pálivá (2s) </button> </div> <hr /> <h3>Stav objednávek:</h3> <table class="table"> <!--Tabulka pro výpis objednávek--> <thead> <tr> <th>Pizza</th> <th>Aktuální stav</th> </tr> </thead> <tbody> @foreach (var pizza in seznamObjednavek) //Výpis objednávek a jejich stavu { <tr> <td>@pizza.NazevPizzy</td> <td> @if (pizza.Stav == "Hotovo!") //Pokud je pizza hotová, text se zbarví zeleně { <span class="text-success fw-bold">@pizza.Stav</span> } else { <span class="text-muted">@pizza.Stav...</span> } </td> </tr> } </tbody> </table> @code { private List<Models.Objednavka> seznamObjednavek = new List<Models.Objednavka>(); //Vytvoření seznamu, kam budeme ukládat všechny objednávky private async Task ZpracovatObjednavku(string nazev, int dobaPeceni) //Metoda je 'async', protože uvnitř používáme 'await' { var novaPizza = new Models.Objednavka { NazevPizzy = nazev, Stav = "Příprava těsta" }; //Vytvoření nové objednávky seznamObjednavek.Add(novaPizza); //Přidání objednávky do seznamu, aby ji mohl uživatel vidět await Task.Delay(2000); //Task.Delay() simuluje dobu přípravy těsta novaPizza.Stav = "Peče se v peci"; //Změna stavu na pečení, Task.Delay() simuluje dobu pečení StateHasChanged(); await Task.Delay(dobaPeceni); novaPizza.Stav = "Hotovo!"; //Po uplynutí doby pečení se stav změní na Hotovo } }
V části @code definujeme asynchronní metodu ZpracovatObjednavku. Klíčovým momentem je řádek await Task.Delay(dobaPeceni). Kdybychom zde nepoužili await (nebo použili příkaz Thread.Sleep), tlačítko by po kliknutí zůstalo "zamáčknuté" a celá stránka by zamrzla na 3 až 5 sekund. Uživatel by nemohl objednat další pizzu, dokud se ta první nedopeče. Díky asynchronnímu přístupu ale metoda pouze "odstartuje" pečení na pozadí a okamžitě uvolní aplikaci. Uživatel tak může naklikat třeba 5 pizz naráz a v tabulce uvidí, jak se každá z nich peče svým vlastním tempem a postupně se mění na "Hotovo".