selene / events
Selene 事件组件
Requires
- php: >=5.4.0
- selene/common: dev-development
Requires (Dev)
- league/phpunit-coverage-listener: dev-master
- phpunit/phpunit: ~4.0
- selene/di: dev-development
- selene/testsuite: dev-development
Suggests
This package is not auto-updated.
Last update: 2016-02-07 09:58:45 UTC
README
安装
安装通过 composer 完成。
将 selene/events
添加为 composer.json
文件的要求。
{ "require": { "selene/events":"dev-development" } }
运行 composer install
或 composer update
$ composer install --dev
测试
使用以下命令运行测试
$ vendor/bin/phpunit
设置
<?php use Selene\Components\Events; $events = new Dispatcher;
用法
事件分发器
附加事件处理器事件处理器可以是任何有效的可调用对象。如果您使用分发器与 DIC(依赖注入容器),也可以将服务作为处理器附加。例如 myservice@handleStuff
或如果服务实现了 EventListenerInterface
,则只需 myservice
。
<?php $events->on('event_name', $callback); $events->on('event_name', function () { // … }); $events->on('event_name', [$object, 'method']); $events->on('event_name', 'Static::method');
您还可以附加事件监听器。事件监听器必须实现 EventListenerInterface
。
<?php $events->addListener('event_name', $eventListener); // same as $events->on('event_name', $eventListener);执行优先级
Dispatcher::on()
以及 Dispatcher::addListener
都接受一个整数值作为第三个参数,指定处理器回调的执行优先级。具有更高优先级值的回调将在较低优先级的回调之前执行。
<?php $events->on('event_name', $callbackBefore, 10); $events->on('event_name', $callbackMid, 5); $events->on('event_name', $callbackAfter, 0);仅附加一次事件处理器
您可以将事件处理器附加一次执行。处理器将在第一次调用后自行解绑。
<?php $events->once('event_name', $callback);解绑事件处理器
您可以选择从给定事件中删除特定监听器,或者删除事件的所有监听器。
如果没有提供事件处理器,则取消所有注册在给定事件名下的所有事件。
<?php // will cancel all eventhandlers for `event_name` $events->off('event_name'); // will detach `$callback` for `event_name` // other handlers bound to `event_name` remain untouched $events->off('event_name', $callback);与服务一起使用事件分发器
可以使用 服务容器 使用事件分发器。
<?php use Selene\Component\Events\Dispatcher; use Selene\Component\DI\Container; $container = new Container; $events = new Dispatcher($container); //… or set the container: $events = new Dispatcher($container); $events->setContainer($container);
您可以使用 @
符号在服务 id 上注释处理方法,例如 mysevice@mycallback
。如果您的服务实现了 EventListenerInterface
,则可以省略处理注释。
<?php $events->on('event_name', 'my_listener'); // assuming SeviceListener implements `EventListenerInterface`
如果您想针对不同的处理器方法,请将 @
后跟方法名称附加到服务 id 上。
<?php $events->on('event_name', 'my_service@eventCallbackMethod');派发事件
派发方法接受三个参数 $event_name
、$event
和 $stopOnFirstResult
。第二个和第三个参数是可选的。如果没有传入第二个参数作为事件,分发器将创建
<?php use \Selene\Components\Event\Event; $event = new Event; $events->dispatch('event_name', $event); // returns an array containing the results returned by the attached handlers. // will stop broadcasting the event as soon as the first result is being returned: $events->dispatch('event_name', $event, true); // same as $events->until('event_name', $event);
事件派发后,事件对象将始终具有一个名称属性,其值等于事件名称。此外,调用 Event::getDispatcher()
将调用分发器实例。
当然,您可以创建自己的自定义事件对象。
<?php namespace Acme\Eventing use \Selene\Components\Events\Event. class AcmeEvent extends Event { public function __construct(…) { // do your setup } }获取所有附加处理器
<?php // returns an array of all attached handlers $events->getEventHandlers(); // returns an array of all handlers attached to `my_event` $events->getEventHandlers('my_event');事件订阅者
事件订阅者是实用程序类,可以订阅多个事件,一次将一个或多个事件处理器附加到每个事件。
事件订阅者必须实现 Selene\Components\Event\SubscriberInterface
。
<?php namespace Acme\Foo; use \Selene\Components\Events\EventInterface; use \Selene\Components\Events\SubscriberInterface; class EventSubscriber implements SubscriberInterface { public static $event; public function getSubscriptions() { return [ 'foo_event' => [ ['onFooEventPre', 100], ['onFooEventMid', 10], ['onFooEventAfter', 0] ], 'bar_event' => ['onBarEvent', 10] ]; } public function onFooEventPre(EventInterface $event) { return $event->getEventName() . '.pre'; // 'foo_event.pre' } public function onFooEventMid(EventInterface $event) { return $event->getEventName() . '.mid'; // 'foo_event.mid' } public function onFooEventAfter(EventInterface $event) { return $event->getEventName() . '.after'; // 'foo_event.after' } public function onBarEvent(EventInterface $event) { return $event->getEventName(); // 'bar_event' } }
现在将订阅者添加到事件分发器。
<?php $subscriber = new Acme\Foo\EventSubscriber; $events->addSubscriber($subscriber); $events->dispatch('foo_event'); // => ['foo_event.pre', 'foo_event.mid', 'foo_event.after'] $events->dispatch('bar_event'); // => ['bar_event']
移除订阅者
<?php $events->removeSubscriber($subscriber);
事件队列分发器
EventQueueDispatcher
可以注册事件监听器并直接分发事件数组。默认情况下,如果事件对象继承自 Selene\Components\Events\Event
,事件名称将与你的事件类名称匹配,其中驼峰式命名法通过点分隔(例如,FooEvent
变为 foo.event
)。
否则,确保在通过 EventQueueDispatcher
分发之前,在你的事件对象上设置事件名称。
<?php use \Acme\Eventing\Event; use \Acme\Eventing\EmergencyEvent; use \Acme\Eventing\Listeners\EventListener; use \Acme\Eventing\Listeners\EmergencyListener; use \Selene\Components\Events\EventQueueDispatcher; $dispatcher = new EventQueueDispatcher; $eventListener = new EventListener; $emergencyListener = new EmergencyListener; $event = new QueueListener; $dispatcher->addListener('event', $eventListener, 100); $dispatcher->addListener('emergency.event', $emergencyListener, 100); $events = [ new Event, new EmergencyEvent ]; $dispatcher->dispatch($events);