Laravel - 对所有路由使用 (:any?) 通配符?

2022-01-02 00:00:00 wildcard routes php laravel laravel-3

我在路由方面遇到了一些麻烦.

我正在研究 CMS,我需要两条主要路线./admin/(:any).admin 控制器用于路由 /admin,而 view 控制器应该用于除 /admin.在 view 控制器中,我将解析 url 并显示正确的内容.

这就是我所拥有的:

Route::get(array('admin', 'admin/dashboard'), array('as' => 'admin', 'uses' =>'admin.dashboard@index'));Route::any('(:any)', 'view@index');

第一条路线有效,但第二条路线无效.我玩了一会儿,似乎如果我使用 (:any) 而不带问号,它只有在我在 / 之后放一些东西时才有效.如果我确实把问号放在那里,它根本不起作用.

我希望以下所有路由都转到 view@index:

<预><代码>//某物/某事/某事/某事/某事/某事/某事/某事/某事/某事...等等...

这是否可以不硬编码一堆 (:any?)/(:any?)/(:any?)/(:any?)(我什至不知道有效))?

解决这个问题的最佳方法是什么?

解决方案

自从 Laravel 4 发布以来,关于这个话题一直存在一些混乱,这个答案是针对 Laravel 3 的.

有几种方法可以解决这个问题.

第一种方法是匹配(:any)/(:all?):

Route::any('(:any)/(:all?)', function($first, $rest=''){$page = $rest ?"{$first}/{$rest}" : $first;dd($page);});

不是最好的解决方案,因为它被分解成多个参数,并且由于某种原因 (:all) 本身无法工作(错误?)

第二种解决方案是使用正则表达式,我认为这是一种比上面更好的方法.

Route::any( '(.*)', function( $page ){dd($page);});

还有一种方法,即使路由可能匹配其他模式,也可以让您检查是否有 cms 页面,前提是这些路由返回 404.此方法修改了 routes.php 中定义的事件侦听器:

Event::listen('404', function() {$page = URI::current();//自定义逻辑,否则返回响应::错误('404');});

然而,我更喜欢的方法是#2.我希望这有帮助.无论您做什么,请确保您在上面定义了所有其他路由,这些路由可以捕获所有路由,之后定义的任何路由都不会触发.

I am having a bit of trouble with the routing.

I'm working on a CMS, and I need two primary routes. /admin and /(:any). The admin controller is used for the route /admin, and the view controller should be used for anything else than /admin. From the view controller, I will then parse the url and show the correct content.

This is what I have:

Route::get(array('admin', 'admin/dashboard'), array('as' => 'admin', 'uses' =>'admin.dashboard@index'));
Route::any('(:any)', 'view@index');

The first route works, but the second one doesn't. I played around with it a little bit, and it seems if I use (:any) without the question mark, it only works if I put something after /. If i do put the question mark there, it doesn't work at all.

I want all of the following routes to go to view@index:

/
/something
/something/something
/something/something/something
/something/something/something/something
...etc...

Is this possible without hardcoding a bunch of (:any?)/(:any?)/(:any?)/(:any?) (which I don't even know works)?

What's the best way to go about this?

解决方案

Edit: There has been some confusion since the release of Laravel 4 regarding this topic, this answer was targeting Laravel 3.

There are a few ways to approach this.

The first method is matching (:any)/(:all?):

Route::any('(:any)/(:all?)', function($first, $rest=''){
    $page = $rest ? "{$first}/{$rest}" : $first;
    dd($page);
});

Not the best solution because it gets broken into multiple parameters, and for some reason (:all) doesn't work by itself (bug?)

The second solution is to use a regular expression, this is a better way then above in my opinion.

Route::any( '(.*)', function( $page ){
    dd($page);
});

There is one more method, which would let you check if there are cms pages even when the route may have matched other patterns, provided those routes returned a 404. This method modifies the event listener defined in routes.php:

Event::listen('404', function() {
    $page = URI::current();
    // custom logic, else
    return Response::error('404');
});

However, my preferred method is #2. I hope this helps. Whatever you do, make sure you define all your other routes above these catch all routes, any routes defined after will never trigger.

相关文章