Y4roc
Y4roc

Reputation: 1136

Symfony EventListener

I created some new events like app.client_enter or app.client_leave. Now I want to register a listener to listen on this events. If I add a listener in the same command, it's working.

ClientListener.php

namespace AppBundle\Service;
use AppBundle\Event\ClientEnterEvent;

class ClientListener {

  public function onClientEnter(ClientEnterEvent $event) {
    echo "It could be working";
  }

}

service.yml (update)

services:
  app.client_listener:
    class: AppBundle\Service\ClientListener
    tags:
      - { name: kernel.event_listener, event: app.client_enter, method: onClientEnter }

ClientCommand.php

namespace AppBundle\Command;

use Symfony\Bundle\FrameworkBundle\Command\ContainerAwareCommand;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\EventDispatcher\EventDispatcher;
use AppBundle\Event\ClientEnterEvent;

class ClientCommand extends ContainerAwareCommand {
  protected function configure() { ... }
  protected function execute(InputInterface $input, OutputInterface $output) {
    $dispatcher = new EventDispatcher();
    $dispatcher->dispatch('app.client_enter', new ClientEnterEvent("Maxi"));
}

Upvotes: 2

Views: 756

Answers (3)

Tomas Votruba
Tomas Votruba

Reputation: 24280

Just a tip hoẃ to make this even better.

Since great Dependency Injection changes in Symfony 3.3+ you can delegate many error prone code to Symfony.


Simplify Service Registration

# app/config/services.yml

services:
    _defaults:
        autowire: true

    AppBundle\:
        resouce: '../../src/AppBundle'

It doesn't work for listeners, because of extra tags, but it does for subscribers - I recommend to use them to prevent any extra redundant config proramming.


Get Arguments The Clean Way - Via Constructor

Using that, you can use constructor injection in your commands out of the box.

use Symfony\Component\EventDispatcher\EventDispatcherInterface

class ClientCommand extends Command
{
    /**
     * @var EventDispatcherInterface
     */
    private $eventDispatcher;

    public function __construct(EventDispatcherInterface $eventDispatcher)
    {
        $this->eventDispatcher = $eventDispatcher;
    }

    protected function execute(InputInterface $input, OutputInterface $output)
    {
        $this->eventDispatcher->dispatch(...);
    }  
}

To read more about DI changes, see this post with before/after examples.

Upvotes: 1

Y4roc
Y4roc

Reputation: 1136

Thank you to all. I found the solution, in ContainerAwareCommand you have to use the service of event_dispatcher.

ClientCommand.php

namespace AppBundle\Command;

use Symfony\Bundle\FrameworkBundle\Command\ContainerAwareCommand;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\EventDispatcher\EventDispatcher;
use AppBundle\Event\ClientEnterEvent;

class ClientCommand extends ContainerAwareCommand {
  protected function configure() { ... }
  protected function execute(InputInterface $input, OutputInterface $output) {
    $dispatcher = $this->getContainer->get('event_dispatcher');
    $dispatcher->dispatch('app.client_enter', new ClientEnterEvent("Maxi"));
}

After I used this service, my event trigger the listener.

Upvotes: 3

mblaettermann
mblaettermann

Reputation: 1943

It's name: kernel.event_listener for the tag

Upvotes: 3

Related Questions