Nesprávné pořadí parametrů v URL generovaném v Presenteru
- honza martinek
- Člen | 22
Našel jsem problém (a předpokládám též bug), který je na mě trochu moc komplexní – prohledal jsem fórum i trochu prošel kód a řešení nevidím. Pokud jsem něco přehlédl, bude mi stačit odkaz. Díky.
K věci: když vytvořím link v presenteru, dopadne to např. takto:
<?php
$this->link('Article:read', array('a' => 'x', 'b' => 'y'))
// výsledek: /article/read/?a=x&b=y
?>
Pokud je však v presenteru proměnná b persistentní, proměnná b se zařadí na začátek query části URL (?b=y&a=x). Problém ovšem je, že nikoli ve vygenerovaném odkazu v presenteru, ale až po requestu na server, při jehož vyřizování se provede přesměrování na canonical URL.
Praktický problém nastává kvůli tomu, že při přesměrování se ztratí anchor, který byl v URL užitý. (Pokud k prohození proměnných nedojde, anchor samozřejmě „projde“, protože se s ním nijak nemanipuluje.) Příklad:
<?php
$this->link('Article:read#anchor', array('a' => 'x', 'b' => 'y'))
// výsledek: /article/read/?a=x&b=y#anchor
// následuje redirect na: /article/read/?b=y&a=x
?>
Moje otázky zní:
- Jako bug vidím to, že se URL nesestaví správně hned v presenteru. Je to feature? Jde to přepnout? (Podle Nette\Application\Route předpokládám, že by to měl být bug.)
- Dá se to případně obejít nějakým fíglem např. s PresenterRequest nebo routrem (kromě vypnutí canonical URLs)?
(Verze nette je 1.0-alpha.)
Editoval honza martinek (9. 8. 2010 0:55)
- Filip Procházka
- Moderator | 4668
V metodě Presenter::canonicalize() se nepředává #anchor ale jenom $presenter->action, problém bude asi v tom že fragment (kotvu) nejde pomocí php zjistit, čili jedině vypnout kanonizaci
A co se týče těch persistentních parametrů, je to, dá se říct, feature, protože při vytváření requestu se použijí persistentní proměnné a přičtou se k nim aktuální parametry, výsledkem je sčíná dvou polí array()+array(). Pokud je v prvním definován klíč tak si bude držet pozici a je jedno kolikátý je v aktuálních params
Editoval HosipLan (10. 8. 2010 4:17)
- Filip Procházka
- Moderator | 4668
spíš by se hodil nějaký „priority-merge“ argumentů, něco jako
dump( $userArgs + $persistentArgs + $userArgs );
což by teoreticky mělo upřednostnit uživatelem nastavené pořadí parametrů a zachovat jejich hodnotu :)
- honza martinek
- Člen | 22
Jde tam spíš o to, co navrhuje HosipLan, ale držel bych se
původního znění odkazů (update nette měnící podobu všech odkazů by asi
populární nebyl ;-)). Co jsem to tak zkoumal, tak na začátek se mi vyřadí
ještě parametry z komponent, takže je to ještě
komplikovanější.
Jinak nejde ani tolik o to, aby se nějak řešil ten fragment, jako
o to, aby Presenter se zapnutou kanonizací vracel stejnou URL jako
Router->constructUrl() – tím se problém s fragmentem vyřeší
(většinou myslím není nutné (nedokážu si nic takového představit), aby
fragment prošel nějakým redirectem, stačí když přežije
request).
Zatím jsem se pokusil vytvořit v presenteru metodu, která si nechá
vygenerovat link přes $this->link() a pak ji proběhne routerem, který
vrátí správnou variantu. Ale ještě do toho úplně nevidím, tak se mi to
nepodařilo zprovoznit.
Ehm, tak jsem si to pořádně prošel a trochu lépe to pochopil – a ten ksort() to vážně řeší. Jsem myslel, že jádro je jinde (že se routuje při běhu aplikace ještě jinde než v presenteru). Půjde to do distribuce? Změní to spoustu kanonických adres na jiný tvar.
Editoval honza martinek (10. 8. 2010 11:06)
- Filip Procházka
- Moderator | 4668
$this->link('Article:read#anchor', array('c' => 'x', 'a' => 'y'))
// výsledek: /article/read/?c=x&a=y&a-something=persistent#anchor
řeší ksort i tohle ? nebo mi to změní pořadí na ?
// výsledek: /article/read/?a=y&a-something=persistent&c=x#anchor
Mně osobně to pořadí vůbec nevzrušuje, protože pokud někdo na pořadí query prvků v URL staví nějakou logiku v aplikaci, tak si koleduje o problém.
- honza martinek
- Člen | 22
Jde o to, aby procedura, která generuje link v presenteru, jej generovala vždy stejně. Ksort řadí i podle druhého, třetího etc. znaku klíče, takže to řeší.
Až teď jsem našel issue na githubu, kde je to zatím otevřené.
Editoval honza martinek (10. 8. 2010 14:22)
- Majkl578
- Moderator | 1364
HosipLan napsal(a):
Mně osobně to pořadí vůbec nevzrušuje, protože pokud někdo na pořadí query prvků v URL staví nějakou logiku v aplikaci, tak si koleduje o problém.
V tom případě by na to měl mít routu, nemyslíš?
Nicméně tyhle přesměrování, která jen promíchají pořadí se mi taky moc nelíbí a jsem pro vyřešení.
- Filip Procházka
- Moderator | 4668
měl jsem na mysli pořadí query prvků, path v routě zaměnit pravděpodobně nejde :)