Usmerjanje
Usmerjevalnik (Router) skrbi za vse v zvezi z URL naslovi, da vam nad njimi ne bi bilo treba več razmišljati. Pokazali si bomo:
- kako nastaviti usmerjevalnik, da bodo URL-ji po želji
- povedali si bomo o SEO in preusmeritvah
- in pokazali si bomo, kako napisati lasten usmerjevalnik
Bolj človeški URL-ji (ali tudi kul ali lepi URL-ji) so bolj uporabni, lažje zapomnljivi in pozitivno prispevajo k SEO. Nette na to misli in razvijalcem popolnoma ustreza. Za svojo aplikacijo si lahko zasnujete točno takšno strukturo URL naslovov, kakršno boste želeli. Lahko jo zasnujete celo šele takrat, ko je aplikacija že končana, saj se to izvede brez posegov v kodo ali predloge. Definira se namreč na eleganten način na enem samem mestu, v usmerjevalniku, in ni tako razpršena v obliki anotacij v vseh presenterjih.
Usmerjevalnik v Nette je izjemen s tem, da je dvosmeren. Zna tako dekodirati URL v HTTP zahtevku kot tudi ustvarjati povezave. Igra torej ključno vlogo v Nette Application, saj delsno odloča o tem, kateri presenter in akcija bosta izvajala trenutni zahtevek, delsno pa se uporablja za generiranje URL-jev v predlogi itd.
Vendar usmerjevalnik ni omejen samo na to uporabo, lahko ga uporabite v aplikacijah, kjer se presenterji sploh ne uporabljajo, za REST API itd. Več v delu Samostojna uporaba.
Zbirka poti
Najprijetnejši način, kako definirati obliko URL naslovov v aplikaciji, ponuja razred Nette\Application\Routers\RouteList. Definicija je sestavljena iz seznama t.i. poti (routes), torej mask URL naslovov in k njim pridruženih presenterjev in akcij s pomočjo preprostega API-ja. Poti ni treba poimenovati.
$router = new Nette\Application\Routers\RouteList;
$router->addRoute('rss.xml', 'Feed:rss');
$router->addRoute('article/<id>', 'Article:view');
// ...
Primer pravi, da če v brskalniku odpremo https://domain.com/rss.xml
, se prikaže presenter Feed
z akcijo rss
, če https://domain.com/article/12
, se prikaže presenter Article
z akcijo
view
itd. V primeru nenajdene primerne poti Nette Application reagira s sprožitvijo izjeme BadRequestException, ki se
uporabniku prikaže kot stran z napako 404 Not Found.
Vrstni red poti
Popolnoma ključni je vrstni red, v katerem so posamezne poti navedene, ker se vrednotijo postopoma od zgoraj navzdol. Velja pravilo, da poti deklariramo od specifičnih k splošnim:
// SLABO: 'rss.xml' ujame prva pot in ta niz razume kot <slug>
$router->addRoute('<slug>', 'Article:view');
$router->addRoute('rss.xml', 'Feed:rss');
// DOBRO
$router->addRoute('rss.xml', 'Feed:rss');
$router->addRoute('<slug>', 'Article:view');
Poti se vrednotijo od zgoraj navzdol tudi pri generiranju povezav:
// SLABO: povezava na 'Feed:rss' generira kot 'admin/feed/rss'
$router->addRoute('admin/<presenter>/<action>', 'Admin:default');
$router->addRoute('rss.xml', 'Feed:rss');
// DOBRO
$router->addRoute('rss.xml', 'Feed:rss');
$router->addRoute('admin/<presenter>/<action>', 'Admin:default');
Ne bomo vam skrivali, da pravilno sestavljanje poti zahteva določeno spretnost. Preden se vanjo poglobite, vam bo koristen pomočnik usmerjevalna plošča.
Maska in parametri
Maska opisuje relativno pot od korenskega direktorija spletnega mesta. Najenostavnejša maska je statični URL:
$router->addRoute('products', 'Products:default');
Pogosto maske vsebujejo t.i. parametre. Ti so navedeni v ostrih oklepajih (npr. <year>
) in so
posredovani v ciljni presenter, na primer metodi renderShow(int $year)
ali v persistentni parameter
$year
:
$router->addRoute('chronicle/<year>', 'History:show');
Primer pravi, da če v brskalniku odpremo https://example.com/chronicle/2020
, se prikaže presenter
History
z akcijo show
in parametrom year: 2020
.
Parametrom lahko določimo privzeto vrednost neposredno v maski in s tem postanejo izbirni:
$router->addRoute('chronicle/<year=2020>', 'History:show');
Pot bo zdaj sprejela tudi URL https://example.com/chronicle/
, ki spet prikaže History:show
s parametrom year: 2020
.
Parameter je lahko seveda tudi ime presenterja in akcije. Na primer tako:
$router->addRoute('<presenter>/<action>', 'Home:default');
Navedena pot sprejema npr. URL v obliki /article/edit
ali tudi /catalog/list
in jih razume kot
presenterje in akcije Article:edit
in Catalog:list
.
Hkrati daje parametroma presenter
in action
privzeti vrednosti Home
in
default
in sta torej tudi izbirna. Tako pot sprejema tudi URL v obliki /article
in ga razume kot
Article:default
. Ali obratno, povezava na Product:default
generira pot /product
, povezava
na privzeti Home:default
pot /
.
Maska lahko opisuje ne samo relativno pot od korenskega direktorija spletnega mesta, ampak tudi absolutno pot, če se začne s poševnico, ali celo celoten absolutni URL, če se začne z dvema poševnicama:
// relativno glede na document root
$router->addRoute('<presenter>/<action>', /* ... */);
// absolutna pot (relativna glede na domeno)
$router->addRoute('/<presenter>/<action>', /* ... */);
// absolutni URL vključno z domeno (relativen glede na shemo)
$router->addRoute('//<lang>.example.com/<presenter>/<action>', /* ... */);
// absolutni URL vključno s shemo
$router->addRoute('https://<lang>.example.com/<presenter>/<action>', /* ... */);
Validacijski izrazi
Za vsak parameter lahko določimo validacijski pogoj s pomočjo regularnega izraza. Na primer, parametru
id
določimo, da lahko vsebuje samo števke s pomočjo regularnega izraza \d+
:
$router->addRoute('<presenter>/<action>[/<id \d+>]', /* ... */);
Privzeti regularni izraz za vse parametre je [^/]+
, tj. vse razen poševnice. Če mora parameter sprejemati tudi
poševnice, navedemo izraz .+
:
// sprejema https://example.com/a/b/c, path bo 'a/b/c'
$router->addRoute('<path .+>', /* ... */);
Izbirne sekvence
V maski lahko označujemo izbirne dele s pomočjo oglatih oklepajev. Izbirni je lahko katerikoli del maske, lahko se v njem nahajajo tudi parametri:
$router->addRoute('[<lang [a-z]{2}>/]<name>', /* ... */);
// Sprejema poti:
// /sl/download => lang => sl, name => download
// /download => lang => null, name => download
Ko je parameter del izbirne sekvence, postane seveda tudi izbiren. Če nima navedene privzete vrednosti, bo null.
Izbirni deli so lahko tudi v domeni:
$router->addRoute('//[<lang=en>.]example.com/<presenter>/<action>', /* ... */);
Sekvence je mogoče poljubno gnezditi in kombinirati:
$router->addRoute(
'[<lang [a-z]{2}>[-<sublang>]/]<name>[/page-<page=0>]',
'Home:default',
);
// Sprejema poti:
// /sl/hello
// /en-us/hello
// /hello
// /hello/page-12
Pri generiranju URL-jev se stremi k najkrajši varianti, zato se vse, kar je mogoče izpustiti, izpusti. Zato na primer pot
index[.html]
generira pot /index
. Obrniti obnašanje je mogoče z navedbo klicaja za levim oglatim
oklepajem:
// sprejema /hello in /hello.html, generira /hello
$router->addRoute('<name>[.html]', /* ... */);
// sprejema /hello in /hello.html, generira /hello.html
$router->addRoute('<name>[!.html]', /* ... */);
Izbirni parametri (tj. parametri, ki imajo privzeto vrednost) brez oglatih oklepajev se obnašajo v bistvu tako, kot da bi bili oklepajeni na naslednji način:
$router->addRoute('<presenter=Home>/<action=default>/<id=>', /* ... */);
// ustreza temu:
$router->addRoute('[<presenter=Home>/[<action=default>/[<id>]]]', /* ... */);
Če bi želeli vplivati na obnašanje končne poševnice, da bi se npr. namesto /home/
generiralo samo
/home
, lahko to dosežemo takole:
$router->addRoute('[<presenter=Home>[/<action=default>[/<id>]]]', /* ... */);
Nadomestni znaki
V maski absolutne poti lahko uporabimo naslednje nadomestne znake in se tako izognemo npr. potrebi po zapisovanju domene v masko, ki se lahko razlikuje v razvojnem in produkcijskem okolju:
%tld%
= top level domain, npr.com
aliorg
%sld%
= second level domain, npr.example
%domain%
= domena brez poddomen, npr.example.com
%host%
= celoten gostitelj, npr.www.example.com
%basePath%
= pot do korenskega direktorija
$router->addRoute('//www.%domain%/%basePath%/<presenter>/<action>', /* ... */);
$router->addRoute('//www.%sld%.%tld%/%basePath%/<presenter>/<action', /* ... */);
Razširjeni zapis
Cilj poti, običajno zapisan v obliki Presenter:action
, je lahko zapisan tudi s pomočjo polja, ki definira
posamezne parametre in njihove privzete vrednosti:
$router->addRoute('<presenter>/<action>[/<id \d+>]', [
'presenter' => 'Home',
'action' => 'default',
]);
Za podrobnejšo specifikacijo lahko uporabimo še razširjenejšo obliko, kjer poleg privzetih vrednosti lahko nastavimo tudi
druge lastnosti parametrov, kot na primer validacijski regularni izraz (glej parameter id
):
use Nette\Routing\Route;
$router->addRoute('<presenter>/<action>[/<id>]', [
'presenter' => [
Route::Value => 'Home',
],
'action' => [
Route::Value => 'default',
],
'id' => [
Route::Pattern => '\d+',
],
]);
Pomembno je opozoriti, da če parametri, definirani v polju, niso navedeni v maski poti, njihovih vrednosti ni mogoče spremeniti, niti s pomočjo poizvedbenih parametrov, navedenih za vprašajem v URL-ju.
Filtri in prevodi
Izvorne kode aplikacije pišemo v angleščini, vendar če naj ima spletno mesto slovenske URL-je, potem preprosto usmerjanje tipa:
$router->addRoute('<presenter>/<action>', 'Home:default');
bo generiralo angleške URL-je, kot na primer /product/123
ali /cart
. Če želimo imeti presenterje
in akcije v URL-ju predstavljene s slovenskimi besedami (npr. /izdelek/123
ali /kosarica
), lahko
uporabimo prevodni slovar. Za njegov zapis že potrebujemo »bolj zgovorno« varianto drugega parametra:
use Nette\Routing\Route;
$router->addRoute('<presenter>/<action>', [
'presenter' => [
Route::Value => 'Home',
Route::FilterTable => [
// niz v URL => presenter
'izdelek' => 'Product',
'kosarica' => 'Cart',
'katalog' => 'Catalog',
],
],
'action' => [
Route::Value => 'default',
Route::FilterTable => [
'seznam' => 'list',
],
],
]);
Več ključev prevodnega slovarja lahko vodi na isti presenter. S tem se zanj ustvarijo različni aliasi. Za kanonično varianto (torej tisto, ki bo v generiranem URL-ju) se šteje zadnji ključ.
Prevodno tabelo lahko na ta način uporabimo za katerikoli parameter. Pri čemer, če prevod ne obstaja, se vzame prvotna
vrednost. To obnašanje lahko spremenimo z dopolnitvijo Route::FilterStrict => true
in pot potem zavrne URL, če
vrednost ni v slovarju.
Poleg prevodnega slovarja v obliki polja lahko uporabimo tudi lastne prevodne funkcije.
use Nette\Routing\Route;
$router->addRoute('<presenter>/<action>/<id>', [
'presenter' => [
Route::Value => 'Home',
Route::FilterIn => function (string $s): string { /* ... */ },
Route::FilterOut => function (string $s): string { /* ... */ },
],
'action' => 'default',
'id' => null,
]);
Funkcija Route::FilterIn
pretvarja med parametrom v URL-ju in nizom, ki se nato posreduje v presenter, funkcija
FilterOut
zagotavlja pretvorbo v nasprotno smer.
Parametri presenter
, action
in module
že imajo preddefinirane filtre, ki pretvarjajo
med slogom PascalCase oz. camelCase in kebab-case, uporabljenim v URL-ju. Privzeta vrednost parametrov se zapisuje že
v transformirani obliki, tako da na primer v primeru presenterja pišemo <presenter=ProductEdit>
, ne pa
<presenter=product-edit>
.
Splošni filtri
Poleg filtrov, namenjenih konkretnim parametrom, lahko definiramo tudi splošne filtre, ki prejmejo asociativno polje vseh
parametrov, ki jih lahko kakorkoli modificirajo in nato vrnejo. Splošne filtre definiramo pod ključem null
.
use Nette\Routing\Route;
$router->addRoute('<presenter>/<action>', [
'presenter' => 'Home',
'action' => 'default',
null => [
Route::FilterIn => function (array $params): array { /* ... */ },
Route::FilterOut => function (array $params): array { /* ... */ },
],
]);
Splošni filtri dajejo možnost prilagoditi obnašanje poti na popolnoma kakršenkoli način. Lahko jih uporabimo na primer za
modifikacijo parametrov na podlagi drugih parametrov. Na primer, prevajanje <presenter>
in
<action>
na podlagi trenutne vrednosti parametra <lang>
.
Če ima parameter definiran lasten filter in hkrati obstaja splošni filter, se izvede lastni FilterIn
pred
splošnim in obratno splošni FilterOut
pred lastnim. Torej znotraj splošnega filtra so vrednosti parametrov
presenter
oz. action
zapisane v slogu PascalCase oz. camelCase.
Enosmerne poti OneWay
Enosmerne poti se uporabljajo za ohranjanje funkcionalnosti starih URL-jev, ki jih aplikacija ne generira več, vendar jih še
vedno sprejema. Označimo jih z zastavico OneWay
:
// stari URL /product-info?id=123
$router->addRoute('product-info', 'Product:detail', $router::ONE_WAY);
// novi URL /product/123
$router->addRoute('product/<id>', 'Product:detail');
Pri dostopu do starega URL-ja presenter samodejno preusmeri na nov URL, tako da vam te strani iskalniki ne indeksirajo dvakrat (glej SEO in kanonizacija).
Dinamično usmerjanje s povratnimi klici
Dinamično usmerjanje s povratnimi klici (callbacks) vam omogoča, da potem dodelite neposredno funkcije (callbacke), ki se izvedejo, ko je dana pot obiskana. Ta fleksibilna funkcionalnost vam omogoča hitro in učinkovito ustvarjanje različnih končnih točk (endpoints) za vašo aplikacijo:
$router->addRoute('test', function () {
echo 'ste na naslovu /test';
});
Lahko tudi definirate v maski parametre, ki se samodejno posredujejo v vaš callback:
$router->addRoute('<lang sl|en>', function (string $lang) {
echo match ($lang) {
'sl' => 'Dobrodošli na slovenski različici našega spletnega mesta!',
'en' => 'Welcome to the English version of our website!',
};
});
Moduli
Če imamo več poti, ki spadajo v skupni modul, uporabimo
withModule()
:
$router = new RouteList;
$router->withModule('Forum') // naslednje poti so del modula Forum
->addRoute('rss', 'Feed:rss') // presenter bo Forum:Feed
->addRoute('<presenter>/<action>')
->withModule('Admin') // naslednje poti so del modula Forum:Admin
->addRoute('sign:in', 'Sign:in');
Alternativa je uporaba parametra module
:
// URL manage/dashboard/default se preslika na presenter Admin:Dashboard
$router->addRoute('manage/<presenter>/<action>', [
'module' => 'Admin',
]);
Poddomene
Zbirke poti lahko členimo po poddomenah:
$router = new RouteList;
$router->withDomain('example.com')
->addRoute('rss', 'Feed:rss')
->addRoute('<presenter>/<action>');
V imenu domene lahko uporabimo tudi Nadomestni znaki:
$router = new RouteList;
$router->withDomain('example.%tld%')
// ...
Predpona poti
Zbirke poti lahko členimo po poti v URL-ju:
$router = new RouteList;
$router->withPath('eshop')
->addRoute('rss', 'Feed:rss') // ujame URL /eshop/rss
->addRoute('<presenter>/<action>'); // ujame URL /eshop/<presenter>/<action>
Kombinacije
Zgoraj navedeno členjenje lahko medsebojno kombiniramo:
$router = (new RouteList)
->withDomain('admin.example.com')
->withModule('Admin')
->addRoute(/* ... */)
->addRoute(/* ... */)
->end()
->withModule('Images')
->addRoute(/* ... */)
->end()
->end()
->withDomain('example.com')
->withPath('export')
->addRoute(/* ... */)
// ...
Poizvedbeni parametri
Maske lahko vsebujejo tudi poizvedbene parametre (parametre za vprašajem v URL-ju). Tem ni mogoče definirati validacijskega izraza, vendar lahko spremenimo ime, pod katerim se posredujejo v presenter:
// poizvedbeni parameter 'cat' želimo v aplikaciji uporabiti pod imenom 'categoryId'
$router->addRoute('product ? id=<productId> & cat=<categoryId>', /* ... */);
Foo parametri
Zdaj gremo že globlje. Foo parametri so v bistvu neimenovani parametri, ki omogočajo ujemanje regularnega izraza. Primer je
pot, ki sprejema /index
, /index.html
, /index.htm
in /index.php
:
$router->addRoute('index<? \.html?|\.php|>', /* ... */);
Lahko tudi eksplicitno definiramo niz, ki bo uporabljen pri generiranju URL-ja. Niz mora biti umeščen neposredno za
vprašajem. Naslednja pot je podobna prejšnji, vendar generira /index.html
namesto /index
, ker je niz
.html
nastavljen kot generacijska vrednost:
$router->addRoute('index<?.html \.html?|\.php|>', /* ... */);
Vključitev v aplikacijo
Da bi ustvarjeni usmerjevalnik vključili v aplikacijo, moramo o njem povedati DI vsebnika. Najlažja pot je pripraviti
tovarno, ki bo objekt usmerjevalnika izdelala, in sporočiti v konfiguraciji vsebnika, da jo naj uporabi. Recimo, da za ta namen
napišemo metodo App\Core\RouterFactory::createRouter()
:
namespace App\Core;
use Nette\Application\Routers\RouteList;
class RouterFactory
{
public static function createRouter(): RouteList
{
$router = new RouteList;
$router->addRoute(/* ... */);
return $router;
}
}
V konfiguracijo nato zapišemo:
services:
- App\Core\RouterFactory::createRouter
Kakršnekoli odvisnosti, na primer od podatkovne baze itd., se posredujejo tovarniški metodi kot njeni parametri s pomočjo autowiringa:
public static function createRouter(Nette\Database\Connection $db): RouteList
{
// ...
}
SimpleRouter
Veliko enostavnejši usmerjevalnik kot zbirka poti je SimpleRouter. Uporabimo ga takrat,
ko nimamo posebnih zahtev glede oblike URL-ja, če ni na voljo mod_rewrite
(ali njegove alternative) ali če zaenkrat
ne želimo reševati lepih URL-jev.
Generira naslove približno v tej obliki:
http://example.com/?presenter=Product&action=detail&id=123
Parameter konstruktorja SimpleRouterja je privzeti presenter & akcija, na katerega naj se usmerja, če odpremo stran brez
parametrov, npr. http://example.com/
.
// privzeti presenter bo 'Home' in akcija 'default'
$router = new Nette\Application\Routers\SimpleRouter('Home:default');
Priporočamo, da SimpleRouter neposredno definirate v konfiguraciji:
services:
- Nette\Application\Routers\SimpleRouter('Home:default')
SEO in kanonizacija
Ogrodje prispeva k SEO (optimizaciji najdljivosti na internetu) s tem, da preprečuje podvojenost vsebine na različnih
URL-jih. Če do določenega cilja vodi več naslovov, npr. /index
in /index.html
, ogrodje prvega od njih
določi za primarnega (kanoničnega) in ostale nanj preusmeri s pomočjo HTTP kode 301. Zahvaljujoč temu vam iskalniki strani
ne indeksirajo dvakrat in ne razpršijo njihovega page ranka.
Temu procesu rečemo kanonizacija. Kanonični URL je tisti, ki ga generira usmerjevalnik, tj. prva ustrezna pot v zbirki brez zastavice OneWay. Zato v zbirki navajamo primarne poti kot prve.
Kanonizacijo izvaja presenter, več v poglavju kanonizacija.
HTTPS
Da bi lahko uporabljali HTTPS protokol, ga je treba omogočiti na gostovanju in pravilno konfigurirati strežnik.
Preusmeritev celotnega spletnega mesta na HTTPS je treba nastaviti na ravni strežnika, na primer s pomočjo datoteke .htaccess v korenskem direktoriju naše aplikacije, in to s HTTP kodo 301. Nastavitev se lahko razlikuje glede na gostovanje in izgleda približno takole:
<IfModule mod_rewrite.c>
RewriteEngine On
...
RewriteCond %{HTTPS} off
RewriteRule .* https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
...
</IfModule>
Usmerjevalnik generira URL z istim protokolom, s katerim je bila stran naložena, zato ni treba ničesar več nastavljati.
Če pa izjemoma potrebujemo, da različne poti tečejo pod različnimi protokoli, ga navedemo v maski poti:
// Generiral bo naslov s HTTP
$router->addRoute('http://%host%/<presenter>/<action>', /* ... */);
// Generiral bo naslov s HTTPS
$router->addRoute('https://%host%/<presenter>/<action>', /* ... */);
Razhroščevanje usmerjevalnika
Usmerjevalna plošča, ki se prikazuje v Tracy Baru, je koristen pomočnik, ki prikazuje seznam poti in tudi parametrov, ki jih je usmerjevalnik pridobil iz URL-ja.
Zelena vrstica s simbolom ✓ predstavlja pot, ki je obdelala trenutni URL, z modro barvo in simbolom ≈ so označene poti, ki bi prav tako obdelale URL, če jih zelena ne bi prehitela. Nato vidimo trenutni presenter & akcijo.

Hkrati, če pride do nepričakovane preusmeritve zaradi kanonizacije, je koristno pogledati v ploščo v vrstici redirect, kjer ugotovite, kako je usmerjevalnik URL prvotno razumel in zakaj je preusmeril.
Pri razhroščevanju usmerjevalnika priporočamo, da v brskalniku odprete Developer Tools (Ctrl+Shift+I ali Cmd+Option+I) in v plošči Network izklopite predpomnilnik, da se vanj ne shranjujejo preusmeritve.
Zmogljivost
Število poti vpliva na hitrost usmerjevalnika. Njihovo število zagotovo ne bi smelo preseči nekaj deset. Če ima vaše spletno mesto preveč zapleteno strukturo URL-jev, si lahko napišete po meri Lasten usmerjevalnik.
Če usmerjevalnik nima nobenih odvisnosti, na primer od podatkovne baze, in njegova tovarna ne sprejema nobenih argumentov, lahko njegovo sestavljeno obliko serializiramo neposredno v DI vsebnik in s tem aplikacijo nekoliko pospešimo.
routing:
cache: true
Lasten usmerjevalnik
Naslednje vrstice so namenjene zelo naprednim uporabnikom. Lahko si ustvarite lasten usmerjevalnik in ga popolnoma naravno vključite v zbirko poti. Usmerjevalnik je implementacija vmesnika Nette\Routing\Router z dvema metodama:
use Nette\Http\IRequest as HttpRequest;
use Nette\Http\UrlScript;
class MyRouter implements Nette\Routing\Router
{
public function match(HttpRequest $httpRequest): ?array
{
// ...
}
public function constructUrl(array $params, UrlScript $refUrl): ?string
{
// ...
}
}
Metoda match
obdela trenutni zahtevek $httpRequest, iz
katerega lahko pridobimo ne samo URL, ampak tudi glave itd., v polje, ki vsebuje ime presenterja in njegove parametre. Če
zahtevka ne zna obdelati, vrne null. Pri obdelavi zahtevka moramo vrniti vsaj presenter in akcijo. Ime presenterja je popolno in
vsebuje tudi morebitne module:
[
'presenter' => 'Front:Home',
'action' => 'default',
]
Metoda constructUrl
nasprotno sestavi iz polja parametrov končni absolutni URL. Pri tem lahko uporabi informacije
iz parametra $refUrl
, kar je
trenutni URL.
V zbirko poti ga dodate s pomočjo add()
:
$router = new Nette\Application\Routers\RouteList;
$router->add($myRouter);
$router->addRoute(/* ... */);
// ...
Samostojna uporaba
Samostojna uporaba pomeni uporabo sposobnosti usmerjevalnika v aplikaciji, ki ne uporablja Nette Application in presenterjev. Zanj velja skoraj vse, kar smo si v tem poglavju pokazali, s temi razlikami:
- za zbirke poti uporabljamo razred Nette\Routing\RouteList
- kot preprost usmerjevalnik razred Nette\Routing\SimpleRouter
- ker ne obstaja par
Presenter:action
, uporabljamo Razširjeni zapis
Torej spet ustvarimo metodo, ki nam bo sestavila usmerjevalnik, npr.:
namespace App\Core;
use Nette\Routing\RouteList;
class RouterFactory
{
public static function createRouter(): RouteList
{
$router = new RouteList;
$router->addRoute('rss.xml', [
'controller' => 'RssFeedController',
]);
$router->addRoute('article/<id \d+>', [
'controller' => 'ArticleController',
]);
// ...
return $router;
}
}
Če uporabljate DI vsebnik, kar priporočamo, spet metodo dodamo v konfiguracijo in nato usmerjevalnik skupaj s HTTP zahtevkom pridobimo iz vsebnika:
$router = $container->getByType(Nette\Routing\Router::class);
$httpRequest = $container->getByType(Nette\Http\IRequest::class);
Ali pa objekte neposredno izdelamo:
$router = App\Core\RouterFactory::createRouter();
$httpRequest = (new Nette\Http\RequestFactory)->fromGlobals();
Zdaj preostane le še, da usmerjevalnik spustimo k delu:
$params = $router->match($httpRequest);
if ($params === null) {
// ni bila najdena ustrezna pot, pošljemo napako 404
exit;
}
// obdelamo pridobljene parametre
$controller = $params['controller'];
// ...
In obratno uporabimo usmerjevalnik za sestavljanje povezave:
$params = ['controller' => 'ArticleController', 'id' => 123];
$url = $router->constructUrl($params, $httpRequest->getUrl());