In Part 2 of our exploration of Symfony components in Drupal, we focus on the event dispatcher.
Spotlight on Symfony in Drupal
- Part 1: HttpKernel in Drupal
- Part 2: EventDispatcher in Drupal
- Part 3: Routing in Drupal
- Part 4: Utility Components in Drupal
The event dispatcher is a tool that enables the application to communicate across objects by subscribing to and listening for events. It achieves this by creating a directory for various event types, and the corresponding registered listeners for each event type. When a specific type of event occurs, the code that has registered a listener for that event is invoked. If you're familiar with the Mediator and Observer design patterns you might recognize similarities here.
Symfony's EventDispatcher component in Drupal
When Drupal receives and incoming request, the HttpKernel
eventually executes this code:
$event = new RequestEvent($this, $request, $type);
$this->dispatcher->dispatch($event, KernelEvents::REQUEST);
This code dispatches RequestEvent
to the EventDispatcher component, along with the $request
object.
Find the code for the EventDispatcher in the vendor/symfony/event-dispatcher/ directory. Let's examine the EventDispatcher.php file in that directory. It contains the class that makes up the core of this component.
The event dispatcher includes methods for adding and removing both listeners and subscribers. It has a dispatch()
method that is responsible for collecting and invoking registered listeners for a particular event.
public function dispatch(object $event, string $eventName = null): object
{
$eventName ??= $event::class;
if (isset($this->optimized)) {
$listeners = $this->optimized[$eventName] ?? (empty($this->listeners[$eventName]) ? [] : $this->optimizeListeners($eventName));
} else {
$listeners = $this->getListeners($eventName);
}
if ($listeners) {
$this->callListeners($listeners, $eventName, $event);
}
return $event;
}
Tip: This code uses ??=
, PHP's null coalescing assignment operator.
The callListeners
method executes the code that has been registered for a specific event.
Drupal's ContainerAwareEventDispatcher class
Drupal optimizes the performance of Symfony's EventDispatcher component. Drupal's customized version, Drupal\Component\EventDispatcher\ContainerAwareEventDispatcher
, runs an initial compilation step which prepares a list of all event listeners and subscribers and stores them in an optimized fashion. Drupal's version is faster by an order of magnitude due to these customizations!
Apart from this additional compiler pass, the 2 components are highly similar.
Learn more
- Read the Symfony docs on its Event Dispatcher component.
- All of our events-related tutorials, blog posts, and curated external resources are listed on our Events topic.
Next up
Stay tuned for our next article in this Spotlight on Symfony series: the Routing component.
Add new comment