天天看點

Symfony2 中event的使用

事件機制在一個可擴充的系統裡面尤為重要。通常一個系統我們不想讓使用者對核心代碼進行修改,如何不修改核心代碼卻能對核心部分進行操作呢。symfony中的event機制就很好的解決了這個問題。現在我一步一步的來定制一個事件監聽

1. 首先定義了一個Events的枚舉類用于管理所有的event,通過定義一個枚舉類友善的進行所有事件的管理,避免遺忘定義的事件

<?php
namespace Wolehao\HomeBundle\Event;


final class Events{
  const HOMEPAGE_VISIT = "home.homepage_visit";
}
           

2. 在HomepageBundle定義了一個event

<?php
namespace Wolehao\HomeBundle\Event;
// 這個是sf為你提供的一個基礎類
use Symfony\Component\EventDispatcher\Event;

// 你的事件類
class HomepageVisit extends Event {
  public $container;
  public function __construct($container) {
    $this->container = $container;
  }
}
           

3.在FileBundle中定義了一個listener

<?php
namespace Wolehao\FileBundle\EventListener;

use Wolehao\HomeBundle\Event\HomepageVisit;

class FileListener
{
  public function onHomepageVisit(HomepageVisit $event)
  {

    $event->container->get("logger")->info("我執行了");
    // ...
  }
}

           

4. 在service.xml中注冊服務

<services>
        <service id="file.listener" class="Wolehao\FileBundle\EventListener\FileListener">
                <tag name="kernel.event_listener" event="home.homepage_visit" method="onHomepageVisit"/>
        </service>
    </services>
           

5.在HomepageBundle的controller中觸發事件

<?php

namespace Wolehao\HomeBundle\Controller;

use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use Sensio\Bundle\FrameworkExtraBundle\Configuration\Route;
use Sensio\Bundle\FrameworkExtraBundle\Configuration\Template;
use Wolehao\HomeBundle\Event\HomepageVisit;
use Wolehao\HomeBundle\Event\Events;
use Wolehao\FileBundle\Event\Listener;

class DefaultController extends Controller
{
    /**
     * @Route("/home/{name}")
     * @Template()
     */
    public function indexAction($name)
    {

      $event = new HomepageVisit($this->container);
      // 在controller裡取事件分發器
      $dispatcher = $this->get('event_dispatcher');
      $dispatcher->dispatch(Events::HOMEPAGE_VISIT, $event);
      return array('name' => $name);
    }

}

           

最後通過http://localhost/fm/web/app_dev.php/home/index通路,控制台成功的列印出"我執行了"的日志。

這裡就是一個跨子產品進行執行的一個例子,在Homepage的controller裡面我們通過事先做一個事件的觸發操作。然後在其他的子產品裡面寫入監聽者,最後通過注冊服務把監聽者加入到事件裡面去。然後在我們自己的監聽器類裡面就可以做你自己想要做的事情了。