我尝试使用ControllerResolver获取Controller的类并在kernel.request
事件侦听器中执行某些操作但是我的代码在Controller表示为服务(例如fos_user.security.controller
)。 Symfony 3.4和4.1都会发生这种情况。
所以这是我的代码,没什么特别的..
public function onKernelRequest(GetResponseEvent $event)
{
if (!$event->isMasterRequest()) return;
$cr = new ControllerResolver();
$request = $event->getRequest();
$controller = $cr->getController($request);
...
}
,只要我拨打$cr->getController($request)
,就会抛出异常。
所以我开始使用调试器,我发现ControllerResolver->createController($controller)
protected function createController($controller)
{
if (false === strpos($controller, '::')) {
throw new \InvalidArgumentException(sprintf('Unable to find controller "%s".', $controller));
}
...
}
事实上,可以在Request->attributes->get('_controller')
中找到一个控制器,通常格式为Class::Function
:
getController()方法依赖于与我们相同的约定 之前定义过:_controller请求属性必须包含 与请求关联的控制器。除了内置的PHP callbacks,getController()也支持由类组成的字符串 name后跟两个冒号,一个方法名称作为有效回调, 喜欢' class :: method'
但是对于某些控制器(例如FOS\UserBundle\Controller\SecurityController
),使用了相对的服务ID(即。fos_user.security.controller
),并使用_controller
对Service:function
属性进行了不同的格式化(请注意一个:
)。因此,很明显createController()
会抛出异常。
即使ControllerResolver
类在4.1上的实现略有不同,也会在同样的情况下抛出异常。实际上,在此版本中,Request中的_controller
属性始终格式化为Class::Function
,即使该类是服务ID:
// $class will be 'fos_user.security.controller'
list($class, $method) = explode('::', $controller, 2);
try {
return array($this->instantiateController($class), $method);
...
然后抛出异常
protected function instantiateController($class)
{
return new $class();
}
因为new fos_user.security.controller()
显然会导致
尝试加载类" fos_user.security.controller"来自全球 命名空间。你忘记了"使用"声明?
现在看来很奇怪,根据文件
,没有人注意到这个错误...在Symfony中,getController()被增强以支持控制器 服务......
我错过了什么或者这个组件真的有错误吗?