Symfony 3中的全捕获路由

5

我在Symfony2中有一个万能路由,但我无法在Symfony3中使其正常工作。我尝试使用完全相同的语法(与我的Symfony2路由一模一样),但那行不通。

fallback:
    path:     /{req}
    defaults: { _controller: MyBundle:Default:catchAll }
    requirements:
        req: ".+"

我该如何在Symfony3中实现这个功能?(这是唯一阻止我使用Symfony3并使我停留在v2.8的原因)

3个回答

16

这应该能帮助你:

route1:
  path: /{req}
  defaults: { _controller: 'AppBundle:Default:index' }
  requirements:
      req: ".+"

我的控制器叫做"DefaultController",我有一个名为"indexAction()"的函数。

这是我DefaultController的代码:

class DefaultController extends Controller
{
    /**
     * @Route("/", name="homepage")
     */
    public function indexAction(Request $request)
...

我实际在我的环境中尝试了你说的方法,直到我指定正确的控制器设置才起作用。


编辑:

为了使其起作用,需要将参数Request $request类型提示)添加到操作方法的签名中。


1
@TylerSebastian,我更新了我的帖子以展示我的DefaultController代码。顺便说一下,我测试了ops代码以验证它不像他说的那样工作,然后进行了如上所示的更改,它确实提供了一个捕获所有路由。我只是通过在我的URL中添加“/home”来验证。 - Alvin Bunk
@AlvinBunk 很有趣,你认为 Request $request 参数是必要的吗?几乎没有关于这个的文档,这也是我首先提出问题的原因。非常感谢,看起来这很有效! - Yes Barry
嗨,@bought777。你不需要那个。我只是剪切和粘贴了很多代码。你可以使用这个:public function indexAction() - Alvin Bunk
我尝试过不将$request作为参数,但是它没有起作用。 :O - Yes Barry
我需要看到你控制器中的其余代码才能复制正在发生的事情。无论如何,我认为你已经准备好了。享受吧! - Alvin Bunk

6

我发现当前被接受的回答对于Symfony 4只是“几乎”有用,所以我要添加我的解决方案:


这就是我在Symfony 4中让它正常工作的方法:

  • Open /src/Controller/DefaultController.php, make sure there is a function called index(){}
    • It's not required to add the Request $request as first param as some comment suggest.
    • This is the method that will handle all urls caught by the routes.yaml
  • Open /config/routes.yaml, add this:

    yourRouteNameHere:
      path: /{req}
      defaults: { _controller: 'App\Controller\DefaultController::index' }
      requirements:        #  the controller --^     the method --^
        req: ".*"`  # not ".+"
    

1
为什么你需要索引呢?只需使您的控制器可调用即可。 - Mike Doe
1
因为这样对于初学者更容易,如果需要扩展,比如一个/admin,也更容易。 - Martijn
1
@emix 魔术方法?不用了,我很少使用它们,这也是我给大多数初学者的建议:要谨慎使用。 - Yes Barry
我不是在谈论__set__get__invoke方法非常方便,特别是对于控制器和CQ处理程序。这样的对象也可以使用callable类型进行类型提示。 - Mike Doe

0

你也可以覆盖异常控制器

# app/config/config.yml
twig:
    exception_controller:  app.exception_controller:showAction

# app/config/services.yml
services:
    app.exception_controller:
        class: AppBundle\Controller\ExceptionController
        arguments: ['@twig', '%kernel.debug%']

namespace AppBundle\Controller;

use Symfony\Component\Debug\Exception\FlattenException;
use Symfony\Component\HttpKernel\Log\DebugLoggerInterface;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;

class ExceptionController
{
    protected $twig;

    protected $debug;

    public function __construct(\Twig_Environment $twig, $debug)
    {
        $this->twig = $twig;
        $this->debug = $debug;
    }

    public function showAction(Request $request, FlattenException $exception, DebugLoggerInterface $logger = null)
    {
        // some action

        return new Response($this->twig->render('error/template.html.twig', [
                'status_code' => $exception->getStatusCode()
            ]
        ));
    }
}

谢谢,这很有帮助,但这不是用于异常处理。 - Yes Barry

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接