【问题标题】:Trying to swap a controller using an event listener with Symfony2尝试使用带有 Symfony2 的事件侦听器交换控制器
【发布时间】:2011-06-27 10:28:08
【问题描述】:

我一直在阅读 Symfony2 文档中的内部章节,它说如果我向 kernel.controller 事件添加一个侦听器,我可以交换运行的控制器,我得到的东西有点像这样:

public function onKernelController(FilterControllerEvent $event)    
{
    $controller = $event->getController();

    $replacementControllerName = .... //Some logic to work out the name of the new controller
    $replacementController = ?? //Not sure what goes here

    $event->setController($replacementController);
}

我不确定的是,一旦我确定了替换控制器的名称,我如何获得可以传递给 setController 的实例?

【问题讨论】:

    标签: symfony


    【解决方案1】:

    您可以将控制器设置为任何可调用,这意味着类似

    • 静态方法array('class', 'method')
    • 一个实例方法array($instance, 'method')
    • 一个匿名函数function() { ... }
    • 一个常规的全局函数'function';
    • 实现__invoke()方法new MyClassImplementingInvoke()的类的实例
    • 特殊语法'class::method' 强制ControllerResolver 创建class 的新实例(不带任何参数调用构造函数)并返回可调用的array($instanceOfClass, 'method')

    编辑:

    我查错了ControllerResolver。在标准设置中运行 Symfony 时,它将使用Symfony\Bundle\FrameworkBundle\Controller\ControllerResolver(而不是Symfony\Component\HttpKernel\Controller\ControllerResolver)。所以控制器名称的处理会和我上面写的有点不同。

    以下示例总结了您在设置控制器时的所有可能选项。

    public function onKernelController(FilterControllerEvent $event)    
    {
        $controller = $event->getController();
        // call method in Controller class in YourBundle
        $replacementController = 'YourBundle:Controller:method';
        // call method in service (which is a service registered in the DIC)
        $replacementController = 'service:method';
        // call method on an instance of Class (created by calling the constructor without any argument)
        $replacementController = 'Class::method';
        // call method on Class statically (static method)
        $replacementController = array('Class', 'method');
        // call method on $controller
        $controller            = new YourController(1, 2, 3);
        $replacementController = array($controller, 'method');
        // call __invoke on $controller
        $replacementController = new YourController(1, 2, 3);
        $event->setController($replacementController);
    }
    

    【讨论】:

    • 感谢您的回复,但我仍然无法让某些东西正常工作,这些选项中的哪一个是获得控制器设置的最佳方式,这样它就可以像 Symfony 创建它一样工作?
    • 对不起,我可能是愚蠢的,但我仍然不知道如何使这项工作,你能发布一些示例代码吗?我有点困惑,因为我认为 class::method 总是引用静态方法,所以我看不到它们如何触发 ControllerResolver 做任何事情。
    • 我添加了一些例子。请查看ControllerResolver 类中的createController() 方法和Symfony\Component\HttpKernel\Controller\ControllerResolver 中的getController() 方法以了解其工作原理。
    • 感谢您的帮助,我认为这正在工作。我必须向我的控制器添加一个 getContainer() 方法,以便我可以将容器添加到新控制器,但它现在似乎可以工作了。
    • 该方法('bundle:controller:method')在最新的 2.0.10 版本中是否仍然有效?我无法让它工作:见 (stackoverflow.com/questions/9256386/…)
    猜你喜欢
    • 2013-09-25
    • 1970-01-01
    • 2012-12-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-09-04
    • 1970-01-01
    • 2016-08-11
    相关资源
    最近更新 更多