ASP.NET Core 9 přináší několik výkonných nástrojů pro vývoj webových aplikací, přičemž jedním z nejvýznamnějších přínosů je schopnost vytvářet dynamické uživatelské rozhraní pomocí Razor Pages, MVC a Blazor. Každý z těchto přístupů má své specifické výhody a vhodnost pro různé typy aplikací, přičemž Blazor přináší silný nástroj pro tvorbu moderních webových aplikací s vysokou interaktivitou.
Model zpracování požadavků a vázání dat v ASP.NET Core
V rámci MVC architektury, když ASP.NET Core obdrží požadavek na akci, jako je například Result, identifikuje, že tato akce přijímá objekt typu PersonModel jako parametr. Framework následně vytvoří instanci tohoto modelu a provede vazbu dat z formuláře do příslušných vlastností objektu. Tento proces je známý jako "data binding" a funguje na základě jmen vlastností, což znamená, že pokud je některé jméno napsáno nesprávně, příslušná vlastnost zůstane nevyplněná.
Tento proces umožňuje velkou flexibilitu při práci s dynamickými stránkami, ale také klade důraz na správnost názvů vlastností, což je důležité pro správné fungování aplikace. Při vývoji aplikací v ASP.NET Core by vývojáři měli věnovat velkou pozornost validaci těchto vlastností a použití vhodných atributů k zajištění integrity dat, což bude podrobněji vysvětleno v dalších kapitolách.
Blazor: Dynamické uživatelské rozhraní s WebAssembly a SignalR
Blazor je moderní framework pro vývoj webových aplikací, který využívá WebAssembly, což je standard pro běh kódu v prohlížeči. Blazor umožňuje spouštění kódu na straně klienta a zároveň poskytuje vysoký výkon, jelikož WebAssembly je kompaktní formát bytekódu, který se rychle stahuje a vykonává. Blazor WebAssembly tak umožňuje vytváření bohatých uživatelských rozhraní s rychlou interaktivitou přímo v prohlížeči.
Významnou výhodou Blazor WebAssembly je interoperabilita s JavaScriptovým prostředím. Blazor totiž umožňuje propojení s DOM (Document Object Model) a různými API prohlížečů, což zajišťuje, že aplikace bude moci manipulovat s obsahem stránky a reagovat na uživatelské vstupy bez zbytečných zpoždění. Tento přístup je bezpečný, protože WebAssembly běží v pískovišti, které chrání aplikaci před škodlivými operacemi.
Blazor také nabízí variantu pro server-side rendering, tedy Blazor Server. Tento přístup je odlišný od tradičních Razor Pages a MVC v tom, že místo odeslání kompletní HTML stránky po každém požadavku, Blazor Server udržuje graf komponent stránky na serveru. Při každé interakci s aplikací se vyhodnocuje stav grafu a na základě toho se na klienta posílá binární reprezentace změn. Tento přístup využívá SignalR, což je technologie pro real-time komunikaci mezi serverem a klientem. SignalR poskytuje vysokou úroveň interaktivity, aniž by bylo potřeba neustále znovu načítat celou stránku.
Výhody komponentového přístupu Blazor
Blazor, stejně jako některé moderní JavaScriptové frameworky, pracuje s komponentami. Komponenta je blok UI, který má konkrétní úkol a může být opakovaně použit napříč celou aplikací. Tento přístup podporuje čistotu kódu, oddělení odpovědností a přehlednost projektu, což je zásadní pro udržitelnost a rozšiřitelnost aplikací.
Každá komponenta v Blazor má příponu .razor a používá jak syntaxi Razor, tak i plné možnosti jazyka C#. C# kód je uvnitř komponenty definován mezi tagy @code{}. Tento kód může obsahovat různé logiky, jako jsou reakce na uživatelské akce, manipulace s daty, nebo dynamické vykreslování obsahu na základě stavu aplikace.
Pro začátek vývoje Blazor aplikace stačí použít příkaz v .NET CLI:
Interaktivní režim a zlepšení výkonu
Nová funkce v ASP.NET Core 9 umožňuje zlepšení způsobu renderování aplikací Blazor díky interaktivnímu režimu. Tento režim zajišťuje, že i když je aplikace na začátku načítána jako statická HTML stránka serverem, uživatelé mohou ihned začít interagovat s aplikací. Jakmile je Blazor runtime načten na straně klienta, stránka se stává plně interaktivní. Tento přístup umožňuje plynulé přechody mezi statickým a dynamickým obsahem a výrazně zlepšuje výkon aplikace.
Hlavními cíli interaktivního režimu jsou:
-
Postupné vylepšení: Uživatelé mohou interagovat s aplikací i před tím, než je celý Blazor runtime plně inicializován.
-
Zlepšený výkon: Zkracuje se doba potřebná pro dosažení interaktivity.
-
Lepší uživatelský zážitek: Snížení viditelných zpoždění a odstranění načítacích indikátorů během přechodů.
Tento režim lze aktivovat při vytváření aplikace použitím příkazu:
Tato možnost poskytuje vývojářům ještě silnější nástroj pro optimalizaci a zlepšení uživatelského zážitku.
Závěr
ASP.NET Core 9 a Blazor přinášejí novou úroveň flexibility a výkonu pro tvorbu dynamických webových aplikací. Důraz na interaktivitu, efektivitu a moderní přístupy k renderování UI znamená, že vývojáři mají k dispozici nástroje, které mohou podstatně zlepšit kvalitu a výkon aplikací. Blazor, díky své schopnosti vykonávat kód na straně klienta i serveru, přináší nový standard v oblasti vývoje webových aplikací.
Jak správně vázat parametry v ASP.NET Core API
Vytváření webových API pomocí architektury založené na kontrolerech v ASP.NET Core zahrnuje práci s různými aspekty požadavků, jako je tělo požadavku, URL, parametry dotazu a také parametry odesílané prostřednictvím formulářů. Pro tento účel existuje v C# abstrakce, známá jako objekt HttpRequest. Tento objekt umožňuje snadný přístup k vlastnostem požadavku prostřednictvím vlastnosti Request třídy ControllerBase, která je základní třídou pro všechny kontrolery v ASP.NET Core.
Pokud potřebujete získat hodnotu z parametru dotazu v URL, můžete použít následující kód:
Tuto hodnotu je ale možné získat i pomocí modelu vazby, který poskytuje atribut FromQuery:
V tomto příkladu je parametr isCompleted označen atributem FromQuery, což znamená, že ASP.NET Core bude automaticky odpovědný za vazbu hodnoty z dotazu na parametr akce. Pokud se název parametru v dotazu neshoduje s názvem parametru v metodě, je možné použít přetížení atributu a definovat název parametru, jak je ukázáno níže:
V ASP.NET Core je k dispozici několik dalších atributů, které umožňují provádět vazbu pro různé situace, a to jak pro parametry v těle požadavku, parametry formulářů, tak pro hlavičky HTTP. Některé z těchto atributů a jejich příklady použití jsou následující:
-
FromBody: Používá se pro vazbu dat z těla požadavku (např. JSON, XML). Tento atribut může být použit pouze jednou v metodě akce, protože předpokládá, že celé tělo požadavku je použito pro vazbu na parametr.
-
FromForm: Používá se pro vazbu dat z formuláře, který obsahuje páry klíč-hodnota.
-
FromHeader: Používá se k získání dat z hlaviček HTTP, což je užitečné např. pro práci s tokeny nebo verzováním API.
-
FromRoute: Používá se pro parametry, které jsou součástí cesty URL (např. identifikátory zdrojů).
Každý z těchto atributů může být použit k přizpůsobení vazby modelu pro konkrétní akci v kontroleru.
V některých případech může výchozí vazba v ASP.NET Core nepostačovat pro složitější aplikace, které vyžadují specifické typy dat. V těchto situacích je možné implementovat vlastní modely vazby, které však spadají mimo rámec této knihy. Podrobnosti o implementaci vlastních vazeb naleznete na oficiálních stránkách Microsoftu.
Validace modelů v ASP.NET Core
Validace modelu je klíčovým prvkem pro vytváření robustních API. ASP.NET Core poskytuje silný mechanismus validace prostřednictvím objektu ModelState. Tento objekt zajišťuje, že data, která vstupují do aplikace, splňují definované validační pravidla. Pokud některá data neodpovídají těmto pravidlům, ModelState je označí jako neplatná.
Například v API pro registraci produktu může být validace použita následovně:
Pokud ModelState.IsValid vrátí hodnotu false, vrátí se HTTP status 400 (bad request) s tělem obsahujícím informace o neplatných polích, např.:
Aby ModelState správně ověřil model, je nutné přidat validační atributy k vlastnostem objektu. V následujícím příkladu je atribut Required použit k označení, že pole Name je povinné, a atribut MinLength zajišťuje, že pole Name musí obsahovat alespoň 3 znaky.
Pokud je potřeba provést ruční validaci v těle metody, lze použít metodu AddModelError k přidání vlastních validačních chyb:
Díky těmto validačním mechanizmům může ASP.NET Core 9 zajišťovat integritu dat a zachování konzistence aplikace.
Dokumentace API
API jsou mocným nástrojem pro poskytování obchodních modelů aplikace prostřednictvím služeb. Pro správnou implementaci API je kladeno důraz na dokumentaci, která uživatelům API poskytne jasné informace o dostupných zdrojích, parametrech, způsobu použití a očekávaných odpovědích. Každé API by mělo být dobře zdokumentováno, aby zákazníci věděli, jak s ním správně komunikovat, jaké formáty požadavků a odpovědí očekávat a jaké chybové stavy mohou nastat při nesprávném použití.
Jak správně dokumentovat a implementovat Web API v ASP.NET Core
Při vytváření webových API v ASP.NET Core je kladeno důraz na správné ošetření odpovědí serveru, aby spotřebitelé API byli schopni správně reagovat na různé situace. API vrací HTTP status kódy, z nichž každý označuje určitou odpověď na požadavek. Dva běžné kódy, které se používají v případě registrace produktu, jsou kód 400 pro chybu a kód 201 pro úspěšně vytvořený objekt. V praxi je důležité, aby API vracelo odpovědi, které přesně informují uživatele o výsledku jejich požadavku.
V rámci ASP.NET Core 9 existují metody, které pomáhají správně formátovat odpovědi. Například metoda BadRequest vrací chybu 400, pokud dojde k nevalidnímu požadavku. Naopak metoda CreatedAtAction vrací kód 201 a připojuje do hlavičky odpovědi odkaz na nově vytvořený objekt, což je v souladu s REST standardy. Tento odkaz je použitelný pro následné GET požadavky, které umožňují získat detaily o nově vytvořeném produktu.
Swagger UI je nástroj, který umožňuje testerům API snadno spouštět požadavky a sledovat odpovědi. Po definování těla požadavku, které v tomto případě obsahuje JSON reprezentující produkt, stačí stisknout tlačítko „Execute“ a získat odpověď API. Swagger UI také automaticky zobrazí HTTP status kód, spolu s informacemi o nově vytvořeném produktu a detaily odpovědi.
Důležitým krokem v implementaci kvalitního API je také přidání odpovídajících atributů, které pomáhají dokumentovat, jaký status kód bude vrácen v případě úspěchu a jaký v případě chyby. Atribut ProducesResponseType slouží k označení, jaký HTTP status kód je očekáván pro danou metodu, zatímco Consumes určuje typ obsahu, který API očekává. V praxi to znamená, že každý požadavek, který API přijme, bude odpovídat definovaným podmínkám.
Příklad implementace POST metody s těmito atributy vypadá následovně:
V tomto příkladu máme definováno, že metoda bude vracet kód 201 pro úspěšně vytvořené položky a kód 400 pro špatný požadavek. Přítomnost těchto atributů zajišťuje, že dokumentace API bude přesně odpovídat jeho chování, což je pro uživatele velmi důležité pro správné používání API.
Swagger UI bude následně generovat odpovídající dokumentaci, kde budou jasně uvedeny různé stavy, které metoda může vrátit. Tato dokumentace pak pomáhá vývojářům správně integrovat API do různých systémů a zajistit, že odpovědi budou odpovídat očekáváním.
Další důležitou funkcionalitou, kterou ASP.NET Core 9 nabízí pro zlepšení dokumentace, jsou XML komentáře. Tyto komentáře mohou být přidány k metodám, aby poskytovaly podrobnosti o tom, co každá metoda dělá. Aby XML dokumentace fungovala, je potřeba ji povolit v nastavení projektu a zajistit, že bude vygenerována během kompilace. Tento přístup umožňuje, aby dokumentace byla vždy aktuální a snadno dostupná pro uživatele API.
Vytváření kvalitních API, které jsou dobře zdokumentovány, je klíčem k úspěšné integraci mezi systémy. Kromě správného nastavení status kódů a dokumentace je rovněž důležité, aby vývojáři dobře rozuměli chování API v různých situacích. Správné používání atributů jako ProducesResponseType a Consumes nejen usnadňuje implementaci, ale i testování a další použití API. Při práci s ASP.NET Core 9 je třeba mít na paměti, že kvalitní dokumentace je základ pro snadnou a efektivní integraci. Ačkoli to může být na první pohled časově náročné, výsledky v podobě přehledného a dobře zdokumentovaného API, které je snadné implementovat a používat, rozhodně stojí za to.
Jak přistupovat k architektuře cloudových aplikací: Průvodce pro efektivní vývoj a správu
Při plánování a nasazování cloudových řešení je kladeno důraz na správnou strukturu prostředí, což je klíčové pro dosažení business cílů. K tomu se hodí rámce jako Cloud Adoption Framework (CAF) a Well-Architected Framework (WAF), které poskytují komplexní nástroje pro efektivní návrh, vývoj a správu cloudových aplikací. Tato rámce se soustředí na rozmanité aspekty infrastruktury, od bezpečnosti až po optimalizaci nákladů, a pomáhají zajistit, že aplikace odpovídají potřebám a požadavkům moderního podnikání.
CAF je výborným nástrojem pro plánování a porozumění cloudovým prostředím. Zaměřuje se na celkovou strukturu prostředí a jeho správu, nikoli pouze na jednu aplikaci nebo konkrétní pracovní zátěž. V rámci tohoto rámce se zohledňují všechny aspekty týkající se týmu, vývoje, infrastruktury a neustálé aktualizace a dodání softwaru. Kromě CAF existuje však další důležitý nástroj pro návrh a implementaci architektonických modelů cloudových aplikací — WAF, tedy Well-Architected Framework.
WAF je soubor zásad a doporučení pro navrhování a správu bezpečných, vysoce výkonných a odolných cloudových aplikací. Tento rámec je rozdělen do pěti pilířů, které jsou klíčové pro kvalitní architekturu:
-
Operační excelence: Tento pilíř se zaměřuje na procesy, které zajišťují plynulý a efektivní chod aplikací, včetně monitorování, automatizace a reakce na incidenty.
-
Bezpečnost: Pilíř, který zajišťuje ochranu aplikací a dat před hrozbami. Zahrnuje správu identit, ochranu infrastruktury, šifrování dat a detekci hrozeb.
-
Spolehlivost: Zaměřuje se na to, aby aplikace dokázaly zotavit se z poruch a pokračovat v požadovaném chodu. To zahrnuje strategie obnovy po havárii, odolnost vůči chybám a zálohování dat.
-
Výkonnostní efektivita: Zajistí efektivní využívání prostředků a možnost škálování aplikací tak, aby splnily požadavky na výkon. Součástí tohoto pilíře je plánování kapacity, optimalizace prostředků a sledování výkonu.
-
Optimalizace nákladů: Tento pilíř se soustředí na efektivní řízení nákladů, přičemž stále poskytuje optimální výkon a hodnotu. Zahrnuje monitorování nákladů, analýzu využívání prostředků a implementaci strategií snižování nákladů.
WAF nejen poskytuje dokumentaci a strategie k optimalizaci každého z těchto pilířů, ale také obsahuje nástroje pro analýzu existujících pracovních zátěží a poskytuje kontrolní seznamy a další materiály, které mohou pomoci při zlepšování výkonu a zajištění kvality aplikací. Všechny tyto pilíře směřují k podpoře cloud-native přístupu, což znamená schopnost neustále přizpůsobovat aplikace a infrastrukturu měnícím se potřebám trhu.
Chcete-li dosáhnout cloud-native přístupu, je třeba se vzdálit od tradičního vývoje aplikací, který se soustředí pouze na samotný kód. DevOps kultura, která se stává stále běžnější, není jen o efektivní komunikaci mezi týmy, ale i o sdílení znalostí, standardů a osvědčených postupů. V operacích, vývoji, infrastruktuře a bezpečnosti je kladeno důraz na to, aby vývojáři rozuměli všem oblastem souvisejícím s tvorbou aplikací, a to nejenom těm přímo spojeným s kódováním.
Znalost nástrojů a principů cloud-native přístupu je dnes zásadní. Nejde jen o rychlý vývoj, ale také o agilitu, která je klíčová pro úspěch na dynamickém a vysoce konkurenčním trhu. Cloud-native nástroje umožňují rychle reagovat na změny a zároveň zajišťují flexibilitu, odolnost a správu aplikací na vysoké úrovni. Agilita však neznamená pouze rychlost; znamená to schopnost rychle se přizpůsobit a reagovat na změny a výzvy, které přináší trh nebo zákazníci.
Příklad z praxe může ukázat, jak vypadá moderní vývoj cloud-native aplikace. Představme si scénář, kdy tým dostane úkol vytvořit API pro zobrazení produktů v online obchodě. Tato aplikace, postavená na ASP.NET Core, bude splňovat všechny funkční a nefunkční požadavky a bude nasazena do prostředí Microsoft Azure. Při vývoji tohoto API bude tým pracovat na zajištění všech potřebných funkcí, optimalizace výkonu a zajištění bezpečnosti dat. Vývojový proces zahrnuje správu úkolů, plánování, kódování, nasazení a následnou údržbu aplikace. Tento proces je zaměřen na co nejrychlejší doručení hodnoty trhu, což je klíčem k úspěchu.
Přechod na cloud-native model znamená, že samotný artefakt aplikace po zkompilování kódu není jediným výsledkem. Je nezbytné, aby aplikace byly připraveny plně využívat možnosti cloudového prostředí a vyrovnávaly se s rostoucími požadavky na uživatele. To zahrnuje faktory jako infrastrukturu, moderní návrh, DevOps procesy, podporu služeb, kontejnery a orchestrátory, a mikroservisní architekturu. Tato cloud-native řešení je třeba neustále zlepšovat, protože jak požadavky na služby, tak i potřeby trhu se neustále vyvíjejí.
Je také důležité si uvědomit, že cloud-native přístup není závislý na konkrétním poskytovateli cloudu, jako je Azure, AWS nebo GCP. Cloud-native model je nezávislý na dodavatelském prostředí, což znamená, že adopční vzory a osvědčené postupy, které se používají v rámci tohoto přístupu, nejsou vázány na konkrétní platformu. To podporuje širší inovace a zajišťuje, že aplikace budou interoperabilní napříč různými prostředími.
K tomu přispívá i Cloud Native Computing Foundation (CNCF), která podporuje projektové komunity a společnosti a vytváří společný jazyk mezi technologiemi a standardy, které umožňují efektivní rozvoj cloud-native aplikací. CNCF usiluje o to, aby organizace mohly bezpečně nasazovat a spravovat své aplikace v různých cloudových prostředích, což je klíčové pro rozvoj udržitelných a flexibilních řešení.
Jak funguje struktura projektu Razor Pages v ASP.NET Core?
Razor Pages je framework pro vytváření dynamických webových aplikací v ASP.NET Core, který se vyznačuje svou jednoduchostí a modularitou. I když jeho struktura může na první pohled vypadat jednoduše, stojí za ní celá řada konceptů, které mohou být později užitečné při přechodu na složitější frameworky, jako je ASP.NET Core MVC. V této části se podíváme na základní strukturu projektu Razor Pages a vysvětlíme, jak jednotlivé složky a soubory fungují.
Projekt Razor Pages má velmi jednoduchou adresářovou strukturu, která se skládá ze čtyř hlavních složek:
-
wwwroot: Tento adresář obsahuje statické soubory aplikace, jako jsou JavaScript, CSS, knihovny a obrázky. V rámci výchozí konfigurace najdeme podsložky jako css, js a lib, které slouží k ukládání souborů JavaScript z externích knihoven (například jQuery). Samozřejmě je možné vytvářet i další adresáře pro obrázky, fonty a podobně.
-
Pages: Složka obsahující samotné stránky aplikace. Každá stránka je tvořena dvojicí souborů s příponou cshtml a cshtml.cs. Soubor cshtml obsahuje HTML kód a C# kód napsaný pomocí Razor syntaxe, zatímco cshtml.cs obsahuje C# kód, který zajišťuje zpracování událostí stránky.
-
appsettings.json: Tento soubor ve formátu JSON slouží k centrálnímu uchovávání nastavení aplikace, jako jsou připojovací řetězce k databázi, API klíče a další parametry. Podrobněji se tímto souborem budeme zabývat v 9. kapitole.
-
Program.cs: Tento soubor je klíčový pro celý projekt Razor Pages. Obsahuje veškeré výchozí konfigurace a nastavení pro běh aplikace. V souboru se provádí nastavení prostředí, připojení k službám, routování a další kritické aspekty aplikace.
Pro pochopení, jak tato konfigurace funguje, se podívejme na kód v souboru Program.cs. Tento soubor by měl vypadat přibližně takto:
Vysvětlení kódu:
-
První řádek vytváří instanci ASP.NET Core webové aplikace s výchozími konfiguracemi. K tomu se používají určité middleware, které ovlivňují tok aplikace.
-
Další klíčová část kódu je
builder.Services.AddRazorPages(), která registruje Razor Pages jako součást aplikace a umožňuje použít příslušné služby. -
Kód mezi řádky 4 a 8 provádí kontrolu prostředí, v němž aplikace běží. Pokud aplikace zjistí, že není v režimu vývoje, přesměruje uživatele na stránku s chybou, čímž se zamezí odhalení detailů aplikace.
-
Kód na řádku 9 zajišťuje, že aplikace bude používat HTTPS.
-
Následující řádky definují, jak bude aplikace pracovat s veřejnými soubory (statickými soubory) a jak bude probíhat routování a autorizace.
Tento soubor Program.cs ukazuje, jak je důležité porozumět pořadí metod, protože to může zásadně ovlivnit chování aplikace při běhu. Každá metoda má svůj účel a musí být volána ve správném pořadí, aby aplikace fungovala podle očekávání.
Další důležitý aspekt Razor Pages je použití syntaxe Razor pro generování dynamických stránek. Razor slouží jako šablonovací engine, který umožňuje vkládat HTML, CSS, JavaScript a C# kód do jednoho souboru, čímž poskytuje flexibilitu při vytváření dynamických webových stránek. Příklad souboru Index.cshtml vypadá následovně:
-
@pageoznačuje, že tento soubor bude fungovat jako akční handler, což znamená, že se jedná o stránku, která bude vykreslena při požadavku na tuto adresu. -
@modelspecifikuje typ modelu, který bude předán této stránce. V tomto případě je to třída IndexModel. -
ViewData["Title"]slouží k předání malých dat, jako je název stránky, do HTML šablony. ViewData je globální slovník, který slouží k přenosu dat mezi controllerem a view.
Kromě samotného souboru s obsahem stránky (např. Index.cshtml) existuje i soubor s příponou cshtml.cs, který obsahuje C# kód pro zpracování událostí a logiku spojenou s touto stránkou. Tento soubor je spojený s HTML souborem prostřednictvím modelu. V případě Index.cshtml to bude třída IndexModel, která vypadá například takto:
V tomto případě se v metodě OnGet() provádí zpracování požadavku GET, což je typický způsob, jakým jsou stránky v Razor Pages načítány. Kód v této metodě může zahrnovat jakékoli operace, jako je načítání dat z databáze nebo provádění dalších logických operací.
Velmi důležitým aspektem Razor Pages je možnost opakovaného použití kódu díky konceptu Layout. Tento koncept umožňuje definovat společný rámec pro více stránek, což usnadňuje údržbu aplikace a zabraňuje opakování stejného kódu. _Layout.cshtml obsahuje společnou strukturu HTML, která je následně používána na stránkách. Důležitým prvkem je metoda @RenderBody(), která určuje místo, kde bude vykreslena konkrétní stránka.
Kromě _Layout.cshtml existují další soubory, které se používají pro specifické účely, jako je _ViewStart.cshtml. Tento soubor může definovat například, jaký layout bude použit pro všechny stránky aplikace.
Je klíčové pochopit, jak všechny tyto komponenty spolupracují a jakým způsobem je možné vytvářet efektivní a udržitelné webové aplikace. Razor Pages je silný nástroj pro vývojáře, který umožňuje rychlé a jednoduché vytváření dynamických stránek s využitím moderních technologií, jako je ASP.NET Core.
Jak správně pracovat s uhlí a vytvářet jemné tóny a stíny v kresbě
Jak digitální technologie a komunikace ovlivňují moderní podnikání a pracovní procesy
Jaké znamení přichází od ďábla?
Jak připravit sladké čtverečky, které zahřejí duši

Deutsch
Francais
Nederlands
Svenska
Norsk
Dansk
Suomi
Espanol
Italiano
Portugues
Magyar
Polski
Cestina
Русский