Php 嵌套类别的路由

Php 嵌套类别的路由,php,cakephp,routing,Php,Cakephp,Routing,我在CakePHP应用程序中设置了一个支持嵌套类别的类别结构。也就是说,类别可以有子类别和/或父类别。类别表的数据库列为:id,parent\u id,lft,rght,name,slug 我已经为类别和与这些类别相关的帖子编写了所有CRUD逻辑 例如,假设我有一个名为about的类别和一个名为me的子类别。我希望像mysite.com/about/me这样的URL显示与me类别相关的所有帖子 我无法确定如何发送此请求。如果我只做Router::connect('/:category',arra

我在CakePHP应用程序中设置了一个支持嵌套类别的类别结构。也就是说,类别可以有子类别和/或父类别。
类别
表的数据库列为:
id
parent\u id
lft
rght
name
slug

我已经为类别和与这些类别相关的帖子编写了所有CRUD逻辑

例如,假设我有一个名为
about
的类别和一个名为
me
的子类别。我希望像
mysite.com/about/me
这样的URL显示与
me
类别相关的所有帖子

我无法确定如何发送此请求。如果我只做
Router::connect('/:category',array('controller'=>'categories','action'=>'view'))
它只适用于
mysite.com/about
,我不能只做
/:category/:categority/:categority
,因为它根本无法扩展


如何实现嵌套类别的路由?

您可以使用
*

如果您知道路线只有一个子类别,那么您的路线应该是

Router::connect('/:category/*', 
                 array('controller' => 'categories', 'action' => 'view'))
这将匹配
mysite.com/about/me
,并将其传递给如下操作

CategoriesController->view('me')
me
将作为参数传递,您可以在该操作中执行所有查询等操作

但是,如果类别嵌套的长度无法定义,则方法不同。假设您还想映射一个url,如
mysite.com/about/me/2012/march
。这样就可以创建路由规则

Router::connect('/:category/**', 
                 array('controller' => 'categories', 'action' => 'view'))
该双
**
在文档中称为

使用尾随的双星,将捕获URL的剩余部分作为单个传递的参数。当您想要使用包含/的参数时,这非常有用

因此,类别之后的所有内容都将作为参数传递。在本例中,它将调用

CategoriesController->view('me/2012/march')
在该操作中,您必须对参数进行解析,以获得所需的嵌套。我建议将该函数提取为控制器中的受保护函数或私有函数

class Categories as AppController {
    public function view($url_params) {
        //it could be a string or an array or etc, depends on how you want to handle it
        $array = $this->_parseCategories($url_params);
    }

    protected function _parseCategories($stringUrl) {
        $subcategories = explode('/', $stringUrl);
        //add whatever else you want to do
        return $subcategories;
    }
}

您应该根据需要调整路线(我没有包括传递
:category
),还可以稍微更改控制器,但它应该具有足够的可扩展性

***
正是我所需要的,谢谢!然而,我刚刚发现了另一个问题,我的posts路由被定义为
/:category/:slug
,因此该路由和
/:category/**
在某些情况下不会“冲突”吗?是的,在某些情况下它会冲突。您应该将
/:category/:slug
放在
/:category/**
之前。对于像
about/me
这样的URL,cake将使用
/:category/:slug
,对于
about/me/please
它应该使用
**
。例如,一个解决方案是使用
/post/:category/:slug
更改slug路径,这样每个帖子都会有一个类似
post/about/me
的url。或者只保留
**
,如果只是一篇文章或子类别文章列表,则让
CategoryController->view($params)
处理。(我喜欢第二个选项,更漂亮的URL…但第一个选项对控制器来说压力更小…)