在OnmernelController中使用setController后,Symfony2.4容器为null

时间:2014-06-04 16:35:11

标签: symfony

我尝试从onKernelController事件侦听器重定向到我的bundle中的另一个控制器。重定向成功但在$ newController中容器是NULL,所以我不能像渲染页面那样对它做任何事情。 为什么容器在这样创建时是NULL?如何在这种情况下将容器服务注入$ newController?

谢谢! :)

事件监听器的最终工作版本:

namespace MyApp\MainBundle\EventListener;

use MyApp\MainBundle\Interfaces\UserCheckInterface;
use Symfony\Component\HttpKernel\Event\FilterControllerEvent;
use Symfony\Component\HttpKernel\Controller\ControllerResolver;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;

class ControllerListener
{
    private $resolver;

    /**
     * @param ControllerResolver $resolver The injected controller_resolver service
     */
    public function __construct($resolver)
    {
        $this->resolver = $resolver;
    }

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

        if (!is_array($controller))
        {
            // not an object but a different kind of callable. Do nothing
            return;
        }

        /* @var $controllerObject Controller  */
        $controllerObject = $controller[0];

        if ( $controllerObject instanceof UserCheckInterface )
        {
            $newRequest = $event->getRequest()->duplicate(null, null, array('_controller' => 'MyApp\MainBundle\Controller\ErrorController::notLoggedInAction'));

            /* @var $newController Controller  */
            $newController = $this->resolver->getController($newRequest);
            $event->setController($newController);
        }
    }
}

这是config.yml

kernel.listener.ControllerListener:
        class: MyApp\MainBundle\EventListener\ControllerListener
        arguments: [ "@controller_resolver" ]
        tags:
            - { name: kernel.event_listener, event: kernel.controller, method: onKernelController }

2 个答案:

答案 0 :(得分:2)

组件解析器(Symfony \ Component \ HttpKernel \ Controller \ ControllerResolver)对容器一无所知。

相反,Symfony FrameworkBundle提供了容器感知的Symfony \ Bundle \ FrameworkBundle \ Controller \ ControllerResolver。值得一看的是代码,看看setContainer的调用位置。

将controller_resolver服务注入您的侦听器,然后使用它而不是创建新的解析器。

答案 1 :(得分:2)

好的......我找到了答案......

像我一样创建$ newController时,默认情况下容器为NULL,需要使用原始控制器的容器设置,如下所示

$newController[0]->setContainer($controllerObject->get("service_container"));