Event dispatcher založený na rozhraních

Upozornění: Tohle vlákno je hodně staré a informace nemusí být platné pro současné Nette.
Martk
Člen | 661
+
0
-

Měl jsem trochu času, tak jsem vytvořil event dispatcher inspirovaným symfony založený na rozhraních.

Eventy v symfony:

class Subscriber implements \Symfony\Component\EventDispatcher\EventSubscriberInterface {

	public static function getSubscribedEvents() {
		return [
			OrderPlacedEvent::NAME => 'onStoreOrder'
		];
	}

	public function onStoreOrder(OrderPlacedEvent $event) {}

}

class OrderPlacedEvent extends \Symfony\Component\EventDispatcher\Event {

	const NAME = 'order.placed';

	protected $order;

	public function __construct(Order $order) {
		$this->order = $order;
	}

	public function getOrder() {
		return $this->order;
	}
}

$dispatcher = new \Symfony\Component\EventDispatcher\EventDispatcher();
$dispatcher->addSubscriber(new Subscriber());

$dispatcher->dispatch(OrderPlacedEvent::NAME, new OrderPlacedEvent(new Order()));

Eventy v tomto rozšíření:

interface IOrderEvent {

	public function onOrder(Order $order);

}

class Subscriber implements IOrderEvent {

	public function onOrder(Order $order) {}

}

$dispatcher = new \WebChemistry\Dispatcher\Dispatcher();
$dispatcher->addSubscriber(new Subscriber());

$dispatcher->dispatch(IOrderEvent::class, new Order());

Výhody oproti symfony dispatcheru:

  • compile time chyby, díky rozhraní.
  • nalezení použití a vytvoření eventu IOrderEvent v phpstormu nalezeno velmi rychle.

Git

Klidně kritizujte, od toho tu je ta diskuze.

Tomáš Votruba
Moderator | 1114
+
+3
-

Ahoj, úplně moc nechápu rozdíly a výhody. Proč bych měl používat tento dispatcher místo defaultního Symfonního?

Vidím, že místo Event třídy jsi použil rovnou argumenty, které bys jí předal. To už je pro mě trochu magické, protože jich může být větší počet.

Zapouzdření v Event třídě mi dává flexibilitu v počtu a jednotu v API dispatch() metody.

pepakriz
Člen | 246
+
0
-

Když už magie, pak lze udělat i něco takového (na vlastní nebezpečí, také nemám rád magii):

<?php
$dispatcher->dispatch(IOrderEvent::class)->onOrder(new Order());
?>

Dispatch by ti vrátil nějaký magický proxy objekt, který by měl implementovanou metodu __call a ta by pak volala správné subscribery. K tomu ještě naučit statickou analýzu, že metoda dispatch ti vrací typ objektu podle prvního argumentu. V PhpStormu třeba pomocí .phpstorm.meta.php.

Něco podobného používám pro fronty s rabbitmq.

mkoubik
Člen | 728
+
0
-

Nebo si počkat na https://wiki.php.net/rfc/generics