CakePHP路由:与MVC混淆

时间:2010-04-23 23:06:31

标签: cakephp routes

因此,我们有一个与房地产相关的网站,其中包含“家/视图”,“房地产经纪人/编辑”等控制器/操作对。从高处起,重构网站被认为是一个好主意,以便URLS现在采用“/ realtorname / homes / view / id”格式,也可能是“/ admin / homes / view / id”和/或“ /区域/..."

仅仅作为CakePHP的新手,我发现很难在routes.php中实现这一点。我可以这样做:

Router::connect('/:filter/h/:id', array('controller'=>'homes','action'=>'view'));
Router::connect('/admin/:controller/:action/:id');

但是我发现id不再简单而优雅地传递给动作,现在控制器和动作不直接跟随域。因此,问题:

  • 用这种方式快速松散地使用/ controller / action格式是一个愚蠢的想法吗?
  • 是否有更好的方式来陈述这些路线,以便事情不会发生严重破坏?
  • 我们会更好地回到子域名(实现此类功能的最初方法,以潜在的虚假搜索引擎优化相关理由进行击落)?

非常感谢任何建议!对不起,我是一个新手,我不知道我是否在问愚蠢的问题......

1 个答案:

答案 0 :(得分:2)

你想要建造的路线并没有什么特别的异国情调。如果没有完全描述如何您的路线/调度正在破坏,很难确定您可能遇到的任何深奥的路由行为(并且相信我,有一些)。

在详细说明之前,我强烈建议您始终使用反向路由来构建您的网址(例如。$html->url(array('controller'=>'homes','action'=>'index'));而不是$html->url('/homes/index')。这是一个小小的性能影响,最终将使您免于一些巨大的头痛。

让我们浏览一下您的示例路线,然后我将尝试解释如何在您的视图中构建匹配的网址,并突出您遇到的潜在问题。

Router::connect('/:filter/h/:id', array('controller'=>'homes','action'=>'view'));

您将在视图中使用以下反向路径构建URL:

$html->url( array(
    'controller'=>'homes','action'=>'view',
    'id'=>$some_id,'filter'=>$some_filter
));

请注意,我已传入'id''filter'个键,而不只是传递相应的变量。这是因为Cake按顺序处理没有​​键的反向路由参数。所以,如果你打电话:

$some_filter = 'foobar';
$some_id = 1234;
$html->url( array('controller'=>'homes','action'=>'view',$some_id,$some_filter));

您最终会得到以下网址:

/1234/h/foobar

哪个是倒退。

您可能遇到的另一个问题是如何将此路由分派到控制器操作。默认情况下,Cake将按路径定义中出现的顺序传递路径请求的所有参数,除非另有说明。所以,通过上面的路线,Cake会调用:

HomesController::view( $filter, $id );

如果您希望HomesController::view的第一个参数为$id,则需要在路径定义中指定:

// This route definition...
Router::connect(
    '/:filter/h/:id',
    array( 'controller'=>'homes', 'action'=>'view' ),
    array(
        'pass' => array( 'id', 'filter' )
    )
);
// ...invokes the controller action:
// HomesController::view( $id, $filter );

'pass'的第三个数组参数的Router::connect元素告诉Cake哪些路由参数以及以什么顺序传递给控制器​​操作。您可以从数组中删除'filter',然后Cake将调用该操作:

HomesController::view( $id );

在这种情况下,Cake仍然捕获$filter并将其作为Controller::params属性的元素提供给控制器。您可以通过寻址$this->params['filter']来访问其值。


您提供的第二条路线是:

Router::connect('/admin/:controller/:action/:id');

对于管理员路由,您实际上不需要定义'admin'之前的特定路由。您只需打开admin routing即可。在/app/config/core.php中,查找并取消注释该行:

Configure::write('Routing.admin', 'admin');

这允许您使用admin_前缀(例如admin_editadmin_publish等)定义一组操作,这些操作由{{1}之类的URL调度到}}。在您的视图中,您将构建反向路由,如下所示:

/admin/homes/edit/1234

请注意$html->url( array( 'controller'=>'homes','action'=>'edit',1234 'admin'=>true )); 部分,它会通知Cake您正在请求管理前缀路由。