IT rekvalifikace s garancí práce. Seniorní programátoři vydělávají až 160 000 Kč/měsíc a rekvalifikace je prvním krokem. Zjisti, jak na to!
Hledáme nové posily do ITnetwork týmu. Podívej se na volné pozice a přidej se do nejagilnější firmy na trhu - Více informací.

Lekce 3 - Směrovač (router)

V minulé lekci, .htaccess, autoloader a obecný kontroler, jsme si nastavili .htaccess, vytvořili index.php a obecný kontroler.

Dnes se budeme věnovat směrovači, tedy komponentě, která podle URL adresy nasměruje požadavek na správný kontroler.

Směrovač

Směrovač (anglicky router) dostane URL adresu, kterou si zpracuje a na jejím základě zavolá příslušný kontroler. Opět je několik způsobů, kterými lze směrovač implementovat a opět jsem vybral ten nejjednodušší. Princip směrovače nápadně připomíná princip kontroleru, toho také využijeme, směrovač bude kontroler.

Směrovač tedy přidáme jako kontroler. Ve složce kontrolery/ vytvoříme soubor SmerovacKontroler.php a do něj stejnojmennou třídu, která bude dědit z obecné třídy Kontroler, kterou jsme si udělali minule. Nezapomeneme implementovat abstraktní metodu zpracuj().

Směrovač dle adresy zjistí, který kontroler voláme, vytvoří nám ho a zároveň i uloží do atributu $kontroler, který třídě rovněž přidáme.

<?php

class SmerovacKontroler extends Kontroler
{

    protected Kontroler $kontroler;

    public function zpracuj(array $parametry): void
    {

    }

}

Možná je trochu matoucí, že v sobě máme vlastně vložené 2 kontrolery, ale je to tak. Kontroler SmerovacKontroler bere URL od uživatele, tu zpracuje a podle ní zavolá příslušný vložený kontroler (např. ClanekKontroler). Oba kontrolery budou mít pohled, SmerovacKontroler bude mít šablonu s rozložením stránky (hlavička, menu atd.) a vložený kontroler bude mít šablonu s obsahem dané stránky (článek, kontaktní formulář, přihlašovací obrazovka atd.).

Parsování URL adresy

Jako první si naparsujeme URL adresu a to přímo v PHP. Adresa nám přijde jako textový řetězec, bude vypadat stejně, jako ta v adresním řádku. Pojďme se dohodnout nejprve na jejím formátu, který bude následující a který jsme již minule naťukli:

http://www.domena.cz/kontroler/parametr2/parametr3

V praxi by vypadala třeba takto:

http://www.domena.cz/clanek/nazev-clanku

Říkáme, že voláme kontroler ClanekKontroler a předáváme mu parametr "nazev-clanku". Kontroler si už článek vezme od modelu a předá ho pohledu, který ho vypíše uživateli.

Např. z této URL:

http://www.domena.cz/kontroler/parametr2/parametr3

bychom potřebovali získat takového pole:

Array
(
    [0] => kontroler
    [1] => parametr2
    [2] => parametr3
)

Přijdeme třídě tedy metodu parsujURL(), která bude jako argument přijímat URL adresu a vrátí nám výše zmíněné pole:

private function parsujURL(string $url) : array
{

}

K naparsování url adresy nám PHP poskytuje funkci parse_url(), která za nás sice neudělá všechnu práci, ale pomůže nám oddělit část s protokolem a doménou od části s parametry. Funkce vrátí asociativní pole, část /kontroler/parametr2/parametr3 dostaneme pod indexem path. Pozor si dáme jen na "/", kterým může tato část začínat, pokud tam je, jednoduše ho odstraníme pomocí funkce ltrim(). Odstraníme také bílé znaky kolem URL (kdyby za ni třeba někdo napsal mezeru), k tomu slouží PHP funkce trim().

$naparsovanaURL = parse_url($url);
$naparsovanaURL["path"] = ltrim($naparsovanaURL["path"], "/");
$naparsovanaURL["path"] = trim($naparsovanaURL["path"]);

Nyní není nic jednoduššího, než si výsledný řetězec rozbít podle lomítek na pole jednotlivých parametrů:

$rozdelenaCesta = explode("/", $naparsovanaURL["path"]);

Výsledek vrátíme a funkce k parsování URL je hotová:

return $rozdelenaCesta;

Volání vloženého kontroleru

Přesuňme se do metody zpracuj(), která se nám na začátku požadavku zavolá. V argumentu $parametry budeme očekávat pole, kde na 1. indexu bude URL adresa. Tu si naparsujeme pomocí naší metody:

$naparsovanaURL = $this->parsujURL($parametry[0]);

Zatím nebudeme ošetřovat případy, kdy je URL zadána nekompletní nebo neexistující.

Získání názvu třídy

První úkol bude zjistit jméno třídy kontroleru. Již víme, že název kontroleru je 1. parametr v naparsované URL adrese. Pro URL adresy však platí jiné konvence, než pro názvy tříd. Proto nám název kontroleru přijde jako nazev-kontroleru a my z něj potřebujeme vytvořit NazevKontroleruKontroler, tedy např. řetězec clanek převedeme na ClanekKontroler a vypis-uzivatelu na VypisUzivateluKontroler. Na tento převod si opět vytvoříme ve třídě metodu a pojmenujeme ji pomlckyDoVelbloudiNotace(). Metoda bude přijímat i vracet řetězec:

private function pomlckyDoVelbloudiNotace(string $text): string
{

}

Použijeme PHP funkci ucwords(), která zvětší počáteční písmeno všech slov ve větě. Funkce sice není UTF-safe, ale to nám zde nevadí. Z parametru si tedy nejprve uděláme větu a to jednoduše tak, že pomlčky nahradíme mezerami:

$veta = str_replace('-', ' ', $text);

Následně zvětšíme první písmena slov a mezery odstraníme:

$veta = ucwords($veta);
$veta = str_replace(' ', '', $veta);

To je vše. Kód by šel napsat i do jednoho řádku, ale pro potřeby tutoriálu jsem ho rozepsal. Metoda převede např. řetězec vypis-uzivatelu na VypisUzivatelu. Výsledek navrátíme:

return $veta;

Vraťme se do metody zpracuj() a zjistěme si název třídy kontroleru pomocí naší nové metody:

$tridaKontroleru = $this->pomlckyDoVelbloudiNotace(array_shift($naparsovanaURL)) . 'Kontroler';

Pomocí array_shift() jsme získali 1. parametr z naparsované URL a zároveň ho z tohoto pole i odstranili, již ho tam totiž nebudeme potřebovat.

Název třídy kontroleru si pro testovací účely pouze vypišme:

echo($tridaKontroleru);

Stejně tak si vypišme i zbytek pole z URL adresy:

echo('<br />');
print_r($naparsovanaURL);

Volání směrovače

Přesuňme se do index.php a vytvořme si zde směrovač. Necháme ho zpracovat URL adresu, kterou v PHP nalezneme v superglobálním poli $_SERVER pod klíčem REQUEST_URI. Hodnotu ještě musíme vložit do pole, jelikož to metoda zpracuj() očekává:

$smerovac = new SmerovacKontroler();
$smerovac->zpracuj(array($_SERVER['REQUEST_URI']));

Díky autoloaderu z minula se nám třída SmerovacKontroler sama načte. Celou magii si vyzkoušíme, zadáme následující URL:

localhost/clanek/nazev-clanku/dalsi-parametr

A měli bychom dosáhnout následujícího výsledku:

Test směrovače
localhost/cla­nek/nazev-clanku/dalsi-parametr

Směrovač nám tedy funguje, z URL adresy nám zjistil název kontroleru a pole parametrů. Pro dnešek toho již bylo dost.

Příště, v lekci Propojení kontroleru a pohledu, si propojíme pohled s kontrolerem.


 

Měl jsi s čímkoli problém? Stáhni si vzorovou aplikaci níže a porovnej ji se svým projektem, chybu tak snadno najdeš.

Stáhnout

Stažením následujícího souboru souhlasíš s licenčními podmínkami

Staženo 3546x (4.4 kB)
Aplikace je včetně zdrojových kódů v jazyce PHP

 

Předchozí článek
.htaccess, autoloader a obecný kontroler
Všechny články v sekci
MVC - Jednoduchý redakční systém v PHP objektově
Přeskočit článek
(nedoporučujeme)
Propojení kontroleru a pohledu
Článek pro vás napsal David Hartinger
Avatar
Uživatelské hodnocení:
154 hlasů
David je zakladatelem ITnetwork a programování se profesionálně věnuje 15 let. Má rád Nirvanu, nemovitosti a svobodu podnikání.
Unicorn university David se informační technologie naučil na Unicorn University - prestižní soukromé vysoké škole IT a ekonomie.
Aktivity