Lekce 3 - Představení MVC a MVT architektury v Django
V minulé lekci, Seznámení s Django frameworkem pro Python, jsme si vytvořili svou první webovou aplikaci ve frameworku Django pro Python. Poprali jsme se s routováním a vypsali hlášku "Ahoj světe!".
Než začneme uživateli servírovat opravdové HTML stránky, představíme si v dnešním tutoriálu webových aplikací s frameworkem Django tzv. MVC architekturu a její Django obdobu MVT. MVC architektura se totiž používá v návrhu téměř všech webových aplikací.
Architektura MVC
MVC je velmi oblíbený architektonický vzor, který se uchytil zejména na webu, ačkoli původně vznikl na desktopech. Je součástí populárních webových frameworků, jakými jsou např. Zend nebo Nette pro PHP, Ruby On Rail pro Ruby nebo MVC pro ASP .NET. Bez podobného vzoru je velice obtížné představit si fungování složitějšího webu.
Motivace
Základní myšlenkou MVC architektury je oddělení logiky od výstupu. Řeší tedy problém tzv. "špagetového kódu", kdy máme v jednom souboru (třídě) logické operace a zároveň renderování výstupu. Soubor tedy obsahuje databázové dotazy, logiku (volání Python příkazů) a různě poházené HTML tagy. Vše je zamotané do sebe jako špagety.
Kód se samozřejmě špatně udržuje, natož rozšiřuje. Je špatně highlightovaný, protože si s ním IDE neví rady, HTML není správně naformátováno, ztrácíme se v jeho stromové struktuře. Naším cílem je, aby zdrojový kód s logikou vypadal jako zdrojový kód (Python) a výstup vypadal jako HTML stránka s co nejmenší příměsí dalšího kódu.
Komponenty
Celá aplikace je rozdělena na komponenty tří typů, hovoříme o Modelech, View ("Pohledech") a Control ("Kontrolerech"), odtud MVC. Označení "Pohled" se budeme snažit vyhýbat, protože nekoresponduje s označením "V" a může mást. Neexistuje žádná striktní definice architektury a tak se můžeme setkat s více výklady. Zaměříme se na ten nejrozšířenější.
Komponenty Model a Controler jsou samozřejmě třídy. View je HTML šablona.
Model
Model obsahuje logiku aplikace a vše, co do
ní spadá. Jsou to mj. výpočty, databázové dotazy, validace a podobně.
Model vůbec neví o výstupu. Jeho funkce spočívá v
přijetí parametrů zvenku a vydání dat ven. Zdůrazněme, že parametry
nejsou URL adresa ani žádné jiné parametry od uživatele. Model
neví, odkud data v parametrech přišla a ani jak budou výstupní data
zformátována a vypsána.
Jelikož budeme používat tzv. ORM (Objektově-Relační Mapování), naše
modely budou přímo korespondovat s databázovými tabulkami. Budeme tedy mít
např. model Uzivatel
, Komentar
nebo
Clanek
. Instance modelů budou samozřejmě obsahovat atributy z
databáze. Instance modelu Uzivatel
bude mít např. atribut
jmeno
. Třídě můžeme definovat instanční metody, např.
takovou, která vypočítá věk uživatele podle jeho data narození. Metody
týkající se obecně uživatelů (tedy třídní) často vkládáme do modelu
jako statické, např. ověření správné délky a znaků hesla (tedy jeho
validaci, protože heslo ověřujeme ještě předtím, než je instance
uživatele vytvořena, a zároveň s uživatelem logicky souvisí).
Nyní máme představu, co model vykonává, pojďme se podívat na pohled.
View
Ačkoli jsme se s pojmem View v Django již setkali, v MVC architektuře má tento pojem jiný význam. Nyní budeme tedy mluvit o obecné komponentě, ne o Django.
View se stará o zobrazení výstupu
uživateli. Jedná se o HTML šablonu obsahující
HTML stránku a tagy značkovacího jazyka Django, který
umožňuje do šablony vkládat proměnné, případně provádět iterace
(cykly) a podmínky. View
uzivatel
tedy vypíše detaily o
uživateli, view clanek
vypíše obsah článku a tak dále.
View máme mnoho, např. pro funkcionalitu s entitou uživatele:
uzivatel_registrace
, uzivatel_prihlaseni
,
uzivatel_profil
a podobně. View uzivatel_profil
je
ale již společný všem uživatelům a jsou do něj posílána různá data,
vždy podle toho, koho zrovna zobrazujeme. Tato data jsou poté dosazena do HTML
elementů šablony.
Šablony lze samozřejmě vkládat do sebe, abychom se neopakovali (šablona s layoutem stránky, šablona s menu a šablona s článkem).
View není jen šablona, ale zobrazovač výstupu. Obsahuje tedy jen minimální množství logiky, která je pro výpis nutná (např. kontrola, zda si uživatel vyplnil přezdívku před jejím vypsáním nebo cyklus s komentáři, které se vypisují).
View podobně jako Model vůbec neví, odkud mu data přišla, stará se jen o jejich zobrazení uživateli.
Controler
Controler je nyní onen chybějící prvek, který osvětlí
funkčnost celého vzoru. Jedná se o jakéhosi prostředníka,
se kterým komunikuje uživatel, model i view. Drží tedy celý systém
pohromadě a komponenty propojuje. Jeho funkci pochopíme z
ukázky životního cyklu stránky. Opět existuje mnoho různých přístupů.
Nejčastěji má každá entita jeden controler, máme tedy
UzivatelControler
, ClanekControler
a tak podobně.
Životní cyklus stránky
Životní cyklus zahajuje uživatel, který
zadá do prohlížeče adresu webu a
parametry, kterými nám sdělí, kterou podstránku si přeje
zobrazit. Budeme chtít např. zobrazit detail uživatele s id 15
.
URL adresa tedy bude:
Požadavek jako první zachytí tzv. router. S tím jsme se
již seznámili. Router podle definovaných rout pozná, který
controler voláme. V našem případě voláme
UzivatelControler
.
Daný controler podle parametrů pozná, co se po něm chce, tedy že má zobrazit detail uživatele. Zavolá model, který uživatele vyhledá v databázi a vrátí jeho údaje. Dále zavolá další metodu modelu, která např. vypočítá věk uživatele. Tyto údaje si controler ukládá do proměnných. Nakonec vyrenderuje view. Název view poznáme podle akce, kterou provádíme. View jsou předány proměnné s příslušnými daty. Controler tedy poslechl uživatele, obstaral podle parametrů dotazu data od modelu a předal je view.
View přijme data od controleru a vloží je do připravené
šablony. Hotová stránka je zobrazena uživateli, který často o celé této
kráse ani netuší
Celou situaci můžeme znázornit diagramem:

Získali jsme tedy oddělení logiky od výstupu, view jsou jako HTML, modely zas v Pythonu. Dosáhli jsme přehlednosti kódu, který je logicky rozčleněný.
MVC architektura nám usnadňuje i myšlení při vývoji projektu. Když píšeme logiku, patří do modelu, formátování a stylování výstupu řešíme v šabloně, to, co uživatel chce z parametrů, zjišťujeme v controleru. Tři různé problémy na třech různých místech, oddělené tak, aby do sebe nezasahovaly a nedělaly nám vývoj složitější.
MVT
Framework Django implementuje MVC architekturu přesně tak, jak jsme si ji popsali. Jednotlivé komponenty ale nazývá po svém a bohužel název jedné používá pro označení odlišné funkcionality, což řekněme si na rovinu je matoucí:
- Modely - modelům říká Django Modely,
- Views - views říká Django Templates, což je v překladu šablony,
- Controlers - controlerům Django říká Views. Nenechme se tedy zmást. Když v naší Django aplikaci tvoříme nový View, není to HTML šablona, ale onen prostředník mezi Modelem a Šablonou.
V minulé aplikaci jsme své první view implementovali jako
metodu index()
. Ta ještě nepoužívala model ani šablonu, ale
pouze vrátila textovou odpověď uživateli.
V příští lekci, Kalkulačka v Django frameworku, vytvoříme svou první pořádnou webovou aplikaci v Pythonu. Půjde o jednoduchou kalkulačku.