Url Manager / TranslatePhpMessage / parameters with ('/')

Hi

I thought I should enable beautiful urls on the sites I create, so I started using them in ‘development’.

This doesn’t always work as smooth as one would expect, and it does require some fixes here and there in the way urls are created or used.

Maybe some of you can share experience with regards how to make the configuration of the urlManager more waterproof. In particular - a nice "test case", - there is the TranslaterPhpMessage extension which breaks with the following configuration.

Here is an example of a URL coming from the use of the extension:


http://example.com/TranslatePhpMessage/translate/edit/path/%2Fvar%2Fwww%2Fexample.com%2Fprotected%2F.%2Fmessages

which results in a 404 generated by Apache:


The requested URL /TranslatePhpMessage/translate/edit/path//var/www/example.com/protected/./messages was not found on this server.

When I truncate the url to:


http://example.com/TranslatePhpMessage/translate/edit/path/

I get an error generated from Yii.

So this can likely be fixed (partl) by changing the .htaccess.

Here is the configuration:

Inside config.php/main.php configuration:


                // uncomment the following to enable URLs in path-format

                'urlManager'=>array(

                        'urlFormat'=>'path',

                        'showScriptName'=>false,

                        'rules'=>array(

                                '<controller:\w+>/<id:\d+>'=>'<controller>/view',

                                '<controller:\w+>/<action:\w+>/<id:\d+>'=>'<controller>/<action>',

                                '<controller:\w+>/<action:\w+>'=>'<controller>/<action>',

                                ''=>'',

                        ),

                ),

The .htaccess:


<IfModule mod_headers.c>

Header set Cache-Control "no-transform"

</IfModule>


RewriteEngine on

# if a directory or a file exists, use it directly

RewriteCond %{REQUEST_FILENAME} !-f

RewriteCond %{REQUEST_FILENAME} !-d

RewriteCond %{DOCUMENT_ROOT}%{REQUEST_FILENAME} !-f

RewriteCond %{DOCUMENT_ROOT}%{REQUEST_FILENAME} !-d

# otherwise forward it to index.php


RewriteRule . index.php  [L]



[color="#2E8B57"]/* Note: Deleted the original post */[/color]

The post could not be accessed with the url "http://www.yiiframework.com/forum/index.php/topic/60862-url-manager-translatephpmessage-parameters-with-%2F/", which had been created by the forum system.

The last part of the slug "%2f/" seems to be the cause.

It turns out that the use of cookies is also somewhat tedious when activating the urlManager.

The ‘cookie’ core script typically included with


Yii::app()->getClientScript()->registerCoreScript('cookie');

will store the cookie using the apparent path and apparently retrieve whatever cookie it finds first.

CJuiTabs is using it, but it does not seem critical there.

If you want to set a cookie and be sure that it is on the root of the domain, you have to write something like this (in JavaScript):




jQuery.cookie('key','value',{'path':'/'});



It is not possible to set a default as for some implementations of jquery.cookie.js (it is not possible/usefull to set jQuery.cookie.defaults.path for instance).

Using ‘path’ encoding also results in issues with CGridView filtering.

Example;

  • From one of the menus the user can arrive on the CGridView page with some prefilled filtering based on his click. Example: he filters on a specific user and the path is something like:

http://www.example.com/admin/users/admin/Users%5Bname%5D/John%20Doe

‘John Doe’ is shown in the filter field of the ‘name’ column for the users in the view.

Now the user changes ‘John Doe’ in ‘Jane Doe’ and submits the new filter (by doing enter for instance).

The AJAX request to the server initiated by the CGridView code looks like this (other filter fields removed/‘name’ is the only column shown):


http://www.example.com/admin/users/admin/Users%5Bname%5D/John%20Doe?Users%5Bname%5D/Jane%20Doe

[size="2"]So the new filter value is passed as a get parameter and the url still contains the previous filter value.[/size]

[size=“2”]In fact, ‘CUrlManager::parsePathInfo’ give precedence to the parameters provided in the path and not to the parameters provided as get parameters, unless the get parameters corresponds to an array in which case ‘CMap::mergeArray’ is used. IMHO it would be preferable to give precedence to the GET parameter or at least make this configureable.[/size]