为什么symfony中service.yml中的侦听器设置不起作用?

时间:2017-01-24 22:16:52

标签: symfony

应用程序/配置/ services.yml

services:    
    myApp.event_listener:
        class: Test\EventListener\MyListener
        tags:
            - { name: myApp.event_listener, event: onDoSomething }

命名空间Test \ EventListener

use Test\Event\MyEvent;

class MyListener 
{
    public function onDoSomething(MyEvent $event)
    {
        echo "I m on listener";
    }
}

命名空间Test \ Event;

use TEST\Entity\MyEntity;
use Symfony\Component\EventDispatcher\Event;

class MyEvent extends Event 
{
    const DO_SOMETHING = 'event.do_something';

    protected $myEntity;

    public function __construct(MyEntity $myEntity)
    {
        $this->myEntity = $myEntity;
    }

    public function getMyEntity()
    {
        return $this->myEntity;
    }
}

来自控制器:

$dispatcher = new EventDispatcher();
$dispatcher->dispatch(MyEvent::DO_SOMETHING, new Event());

你能帮助为什么它不能将这个事件添加到监听器中吗?

1 个答案:

答案 0 :(得分:1)

请阅读documentation about event listener。根据您要监听的事件,您需要在服务定义中修复标记声明。如果您想要监听内核事件,这是一个示例:

<强> YAML

# app/config/services.yml
services:
    app.exception_listener:
        class: AppBundle\EventListener\ExceptionListener
        tags:
            - { name: kernel.event_listener, event: kernel.exception }

如果您想要收听自定义事件,则需要事先创建适当的事件类,并且可能使用标记定义的method属性,如文档中所述:

  

有一个名为method的可选标记属性,用于定义触发事件时要执行的方法。默认情况下,方法的名称为+“camel-cased event name”。如果事件是kernel.exception,则默认执行的方法是onKernelException()。

如果您想创建和发送自己的活动,请阅读documentation about the EventDispatcher component

您需要修复代码中的几个问题!

事件侦听器的服务定义应使用标记名称 kernel.event_listener 以及 event.do_something 的事件名称(MyEvent :: DO_SOMETHING):

services:    
    myApp.event_listener:
        class: Test\EventListener\MyListener
        tags:
            - { name: kernel.event_listener, event: event.do_something }

在不指定方法参数的情况下调用的侦听器中的方法是 onEventDoSomething

use Test\Event\MyEvent;

class MyListener 
{
    public function onEventDoSomething(MyEvent $event)
    {
        echo "I m on listener";
    }
}

在你的控制器中你应该从容器中获取调度程序,创建一个MyEvent类的实例并传递它的实体(参见Events构造函数):

/** @var $dispatcher EventDispatcherInterface */
$dispatcher = $this->get('event_dispatcher');
$event = new MyEvent($myEntity);
$dispatcher->dispatch(MyEvent::DO_SOMETHING, $event);

正如@Cerad评论的那样:如果你想创建一个新的调度程序实例,你不需要服务定义,但你需要将监听器添加到新的调度程序:

// create dispatcher and add listener to it
$dispatcher = new EventDispatcher();
$listener = new MyListener();
$dispatcher->addListener('event.do_something', array($listener, 'onEventDoSomething'));

// dispatch event
$event = new MyEvent($myEntity);
$dispatcher->dispatch(MyEvent::DO_SOMETHING, $event);