- falkon
- Člen | 17
Chcel by som reportovat chybu v
Route::constructUrl()
v stable verzii
Nette 0.9.1. Routa, ktora ma ako mask
zadany vyraz
<module>/<presenter>/<action>
a
zaroven ma udanu defaultnu hodnotu parametra module
nepracuje spravne pri generovani URL na niektore moduly.
Symptomy:
V bootstrap.php je nadefinovana routa:
ktorej tvar je tak-nejak intuitivny. Problem je, ze pre
niektore moduly (napr. modul ‚auth‘) je vyhadzovana chyba
No route for Auth:Homepage:default().
Zda sa, ze takato routa
nefunguje pre moduly, ktore maju dlzku nazvu roznu od
dlzky hodnoty udanej ako defaultna hodnota parametru
module
(v tomto pripade ‚public‘, cize dlzky 6).
Preto napr. modul ‚Auth‘ nefunguje, ale ‚Authhh‘ funguje.
Problem spociva v generovani URL na dany modul – co sa prejavuje bud pri
canonizacii URL (ak je zapnuta, vyhodenim vynimky
No route for <module>:<presenter>:<action>().
),
alebo pri generovani linkov v sablone).
To, ze dana chyba ma nieco spolocne s defaultnou hodnotou parametru
module
naznacuje aj to, ze takato definicia:
routuje korektne a generuje korektne linky. Problemom je, ze taketo zadanie samozrejme nie je semanticky ekvivalentne tomu vyssieuvedenemu – pride sa o funkcionalitu (ne)doplnania nazvu implicitneho modulu do URL.
Myslim si, ze chyba je v triede Route
v subore
Nette\Application\Routers\Route.php
okolo riadku
273:
Napr. pri spracovani dotazu <host>/auth/bar/baz
sa
v polozke $metadata[self::MODULE_KEY]['fixity']
nachadza hodnota
1
a v polozke
$metadata[self::MODULE_KEY][self::VALUE]
hodnota
'public'
(co je definovana defaultna hodnota parametru
module
z definicie routy). V pripade, ze sa defaultna hodnota
parametra module
v definicii routy nezada, tak polozka
$metadata[self::MODULE_KEY]['fixity']
ani
$metadata[self::MODULE_KEY][self::VALUE]
v danom mieste kodu nie
je nastavena (pre rovnaky dotaz).
Bohuzial, zmysel niektorych premennych a priznakov (ako napr. zmysel priznaku „fixinity“ a presny vyznam vsetkych atributov v poli $metadata) mi zostava mierne utajeny, a tak sa neodvazujem navrhnut patch.
Vzorovy projekt, ktory demonstruje popisovanu chybu je dostupny k stiahnutiu na http://stoki.pasique.sk/…ting-bug.zip. Je to Skeleton projekt, ktory je rozsireny o par modulov/prezenterov/template-ov. Su v nom vytvorene 3 moduly – ‚Public‘ (ktory je nastaveny ako implicitny a funguje spravne), ‚Auth‘ (ktory nefunguje) a ‚Authhh‘ (ktoreho nazov bol predlzeny na 6 znakov, aby fungoval).
P.S.: Zbeznym hladanim na fore sa mi zdalo, ze s podobnym problemom sa potykalo uz davnejsie niekolko uzivatelov (napr. 1 , 2 ), no vzdy dostali skor rady na workaround, nez odpoved kde je chyba. Preto by som sa chcel obratit priamo na Davida a poprosit ho o vyjadrenie, ci je to naozaj chyba, alebo ci to je feature a nieco mi tak seredne unika.
Vopred dakujem!
- Ondřej Mirtes
- Člen | 1536
Hezký bugreport, uvidíme co na to David.
Já bych zkusil dát v definicích rout velká písmena pro modul a pro presenter, tak to má totiž být.
- falkon
- Člen | 17
Ano, pravda, niekde som videl doporucenie, ze by sa to malo pisat velkymi – ale na tom to nezavisi. Ja som to povodne mal s velkymi pismenami, ale po dlhom case testovania a skusania roznych verzii mi tam zostali tie male pismena… nicmenej „na funkci rostlinare to vplyv nema“ :)
- Jan Jakeš
- Člen | 177
Další BUG report – pravděpodobně jsou významné chyby v Route!
1. BUG:
Mějme routu:
V nejnovější unstable verzi neprojde touto routo ani
document_root/nejakeid?action=edit
. Problém nastává už ve fázi
match
, zřejmě se šaptně podle masky vygeneruje regexp.
Navíc pokud změním masku na toto:
Výraz routou sice projde, ale nastaví mi action na hodnotu
default
(!) a vygeneruje URL
document_root/nejakeid
.
2. BUG:
Další chyba se projevuje zajímavým způsobem. Mějme routu:
Když do ní pošleme document_root/nejakeid
, vše proběhne OK.
Jenže… Když v definici routy zaměním slovo Page
za
page
, najednou routa uvedenou adresu nevezme. To by ještě tak
nevadilo, ale když routu změníme na:
Vezme najednou obě varianty…
Třída Route se teď chová opravdu podivně. Sám nevím, jestli už delší dobu nebo až od nejnovějších revizí. Zatímco druhý mnou popsaný bug je spíš detail (který ale ukazuje na nějakou nekonzistenci uvnitř Route), první bug mi připadá dost závažný. Zdá se mi, že Route selže i v naprosto jednoduché kombinaci masky a defaultních dat.
Editoval Juan (11. 10. 2009 0:42)
- David Grudl
- Nette Core | 8229
Juan napsal(a):
Z technických důvodů bylo potřeba kolem otazníku mít mezeru, dnes jsem toto omezení odstranil.
Tento zápis skutečně podporován není, maska se kolem otazníku rozpadne na dvě samostatné části.
Další chyba se projevuje zajímavým způsobem. Mějme routu:
Když do ní pošleme
document_root/nejakeid
, vše proběhne OK. Jenže… Když v definici routy zaměním slovoPage
zapage
, najednou routa uvedenou adresu nevezme. To by ještě tak nevadilo, ale když routu změníme
Co znamená „adresu nevezme“? Routa pracuje správně, jiná věc je, že
aplikace nemusí umět najít pagePresenter
.
- Jan Jakeš
- Člen | 177
Z technických důvodů bylo potřeba kolem otazníku mít mezeru, dnes jsem toto omezení odstranil.
Aha, to jsem netušil :) Místo toho tu vytvářím flame, jak je tam závažný bug. Sorry…
Co znamená „adresu nevezme“? Routa pracuje správně, jiná věc je, že aplikace nemusí umět najít pagePresenter.
Nevezme nemyslím, že nenajde presenter, ale jako
No route for Page:default(id=nejakeid)
. Jen pro shrnutí – uvedl
jsem tam dvě routy, v první je presenter volitelný, v druhé konstantní.
Obě routy správně matchnou 'presenter' => 'Page'
, ale
'presenter' => 'page'
první routa nematchne, zatímco
druhá ano…
- David Grudl
- Nette Core | 8229
falkon napsal(a):
Chcel by som reportovat chybu v
Route::constructUrl()
v stable verzii Nette 0.9.1. Routa, ktora ma akomask
zadany vyraz<module>/<presenter>/<action>
a zaroven ma udanu defaultnu hodnotu parametramodule
nepracuje spravne pri generovani URL na niektore moduly.
Díky za výborný report včetně ukázkového kódu. Mělo by to být opravené.
- David Grudl
- Nette Core | 8229
Juan napsal(a):
Aha, to jsem netušil :) Místo toho tu vytvářím flame, jak je tam závažný bug. Sorry…
V poho, potřeboval jsem nakopnout, abych to upravil ;)
Nevezme nemyslím, že nenajde presenter, ale jako
No route for Page:default(id=nejakeid)
. Jen pro shrnutí – uvedl jsem tam dvě routy, v první je presenter volitelný, v druhé konstantní. Obě routy správně matchnou'presenter' => 'Page'
, ale'presenter' => 'page'
první routa nematchne, zatímco druhá ano…
Ono se tím ‚matchne‘ obvykle spíš myslí akceptování URL než generování, ale už rozumím. Změnil jsem interní cache v MultiRouter na case-insensitive, takže by mělo fungovat i použití malého písmenka.