2011-12-28 60 views
0

我有一個uri方案,就像<country>/<id>_<action>/<name>,它從一箇舊網站下降,我將該網站移植到Kohana framewerk。一個可能的URL是http://www.example.com/us/1234_1/fooKohana 3.2路由重寫動作

<action>的值是從0到9的數字:\d。每個數字指的是一個動作,例如0overview

如何在bootstrap中設置我的路由,請求的操作正確移植。

這是我現在,但顯然它不正確的行爲,因爲它試圖調用的函數的Action_0代替Action_Overview,給出的例子網址:

Route::set('default'), '<country>/<id>_<action>/<name>') 
    ->defaults(array(
     'controller' => 'index', 
     'action'  => 'index' 
    )); 

回答

2

一個解決辦法是命名action_0到action_9,但我們中的任何一個都喜歡。

另一種解決辦法是「重新路由」在控制器::動作之前()是這樣的:

public function before() 
{ 
    parent::before(); 

    $actions = array(0 => 'overview', ...); 

    $this->request->action($actions[$this->request->action()]); 
} 

或者你可以做,在一個lambda /回調路線,但我會保持它的控制器::之前()。

0

乾淨的解決方案當然會很好,但恐怕沒有一個可用。我可以想出幾個辦法來處理它,但是,沒有一個是理想的。

否1.將由Darsstar

提供的subrouter想法否2.將類似的解決方案沒有。 1,但使用的是雙路由系統,沿着線:

Route::set('default'), '<country>/<id>/<action>/<name>', array ('country' => '.+', 'name' => '.+',)) /* new */ 
->defaults(array(
    'controller' => 'new', 
    'action'  => 'index' 
)); 

Route::set('legacy'), '<country>/<id>_<oldaction>/<name>', array ('country' => '.+', 'name' => '.+', 'oldaction' => '\d+',)) /* legacy */ 
->defaults(array(
    'controller' => 'legacy', 
    'action'  => 'route' 
)); 

新的控制器將使用action_overview()等根據自己的喜好和傳統將舉行只有一個動作,action_route()做這樣的事情:

public function action_route() 
{ 
    $actions = array (0 => 'overview', ...); 

    $params = array (
    'country' => $this->request->param ('country'), 
    'id' => $this->request->param ('id'), 
    'action' => $actions[$this->request->param ('oldaction')], 
    'name' => $this->request->param ('name'), 
); 
    $this->request->redirect (Route::get ('legacy')->uri ($params)); 
} 

否3.是簡單地使用多個途徑,如果動作的次數是不是很大,可以考慮使用每一個行動路線是這樣的:

Route::set('overview'), '<country>/<id>_0/<name>') 
->defaults(array(
    'controller' => 'index', 
    'action'  => 'overview' 
)); 

Route::set('details'), '<country>/<id>_1/<name>') 
->defaults(array(
    'controller' => 'index', 
    'action'  => 'details' 
)); 

你可以做這個有點更易於管理使用沿此線foreach()

$actions = array (
    'overview', 
    'details', 
); 
foreach ($actions as $idx => $action) 
{ 
    Route::set($action), '<country>/<id>_' . $idx . '/<name>') 
    ->defaults(array(
     'controller' => 'index', 
     'action'  => $action, 
    )); 
} 

當這是完成後,您可以使用帶有動作action_overview()的控制器。在生產中,爲路線使用緩存,以避免在每個請求中重新定義它們。

就我個人而言,如果它是一個直接的端口,我不會選擇3,並且沒有計劃用新的功能擴展站點。否則,我會不帶2,因爲它允許一個可以逐步淘汰的傳統模式。此外,它允許更靈活的「新」路線。
我不會選擇沒有1只因爲它是 - 在我的腦海 - 不符合編碼的Kohana的風格保持一致,我個人希望找到路由規則無論是在bootstrap.php中的init.php(在模塊的情況下)。否則這是一個完全有效的解決方案(從某種意義上說,它是Kohana的風格,因爲Kohana足夠靈活以允許解決方案違背它的一般風格...... :))