Im vergangenen Jahr hat
PHP-FIG , die
PHP Compatibility Concepts Group, mehrere neue Spezifikationen veröffentlicht. Der letzte,
PSR-14 , ist dem Event-Dispatching gewidmet. Wie andere PSRs ist dies eine lokale Spezifikation, hat jedoch einen großen Einfluss auf viele Aspekte der Standardisierung.
Von einem Übersetzer: Dies ist eine Übersetzung des ersten Teils einer Reihe von Veröffentlichungen, in denen Larry (Crell) Garfield, einer der Mitglieder von PHP-FIG, erklärt, was PSR-14 ist, wozu es fähig ist und was nicht und wie es am besten verwendet werden kann ihre Projekte.Zweck
Event Dispatching wird seit langem in vielen Sprachen verwendet. Wenn Sie jemals EventDispatcher in
Symfony , Event System in
Laravel , Hooks in Drupal,
Event Manager im Zend-Framework,
League \ Event- Paket oder ähnliches verwendet haben, dann verstehen Sie, worum es geht.
Im Allgemeinen sind alle diese Systeme eine Form eines „Mediator-Beobachters“. Ein Codeteil sendet eine Nachricht vom Typ "Ereignis", und der Vermittler sendet sie an andere einzelne Codeteile - "Listener". Manchmal ist das Signal nur in eine Richtung gerichtet, manchmal kann der „Hörer“ Daten an den Anrufer zurücksenden. Natürlich sind sie alle unterschiedlich und nicht sehr kompatibel miteinander.
Dies ist ein Problem für eigenständige Bibliotheken, die eine Verbindung zu verschiedenen Bibliotheken und Anwendungen herstellen möchten. Viele Bibliotheken können erweitert werden, indem Ereignisse in der einen oder anderen Form gesendet werden, damit anderer Code sie kontaktieren kann. Eine solche Zwischenschicht ist jedoch tatsächlich proprietär. Die Bibliothek, in der Symfony EventDispatcher ausgeführt wird, wird dann mit Symfony zusammengeführt. Wenn Sie es dann an einem anderen Ort verwenden möchten, müssen Sie EventDispatcher installieren und eine Verbindung zu den Bibliotheken im Programm herstellen. Die Bibliothek, die das Bindungssystem von Drupal
module_invoke_all()
wird dann mit Drupal verknüpft. Usw.
Das Ziel von PSR-14 ist es, die Bibliotheken von dieser Abhängigkeit zu befreien. Auf diese Weise können Bibliotheken über eine dünne gemeinsame Ebene erweitert und anschließend ohne zusätzlichen Aufwand in eine andere Umgebung übertragen werden, z. B. in Symfony, Zend Framework, Laravel, TYPO3, eZ Platform oder Slim. Solange die Umgebung mit dem PSR-14 kompatibel ist, funktioniert alles.
Spezifikation
Wie bereits erwähnt, ist die Spezifikation recht leicht. Dies sind drei Schnittstellen in einer Methode und eine Meta-Beschreibung ihrer Verwendung. Alles ist einfach und bequem. Unten finden Sie den Code für diese Schnittstellen (kein Kommentar, um Platz zu sparen).
namespace Psr\EventDispatcher; interface EventDispatcherInterface { public function dispatch(object $event); } interface ListenerProviderInterface { public function getListenersForEvent(object $event) : iterable; } interface StoppableEventInterface { public function isPropagationStopped() : bool; }
Die ersten beiden sind der Kern der Spezifikation.
StoppableEventInterface
ist eine Erweiterung, auf die wir später zurückkommen werden.
Ich denke, dass
EventDispatcher
den meisten von Ihnen vertraut
EventDispatcher
- es ist nur ein Objekt mit der Methode, an die Sie das Ereignis übergeben - der Vermittler, über den Sie bereits gesprochen haben. Das Ereignis selbst ist jedoch nicht definiert - es kann ein
beliebiges PHP-Objekt sein . Dazu später mehr.
Die meisten vorhandenen Implementierungen haben ein Objekt oder eine Reihe von Funktionen, die als Vermittler oder Dispatcher fungieren, und einen Ort zum Registrieren des Codes, der das Ereignis empfängt (Listener). Für PSR-14 haben wir diese beiden Verantwortlichkeiten bewusst in separate Objekte unterteilt. Der Dispatcher empfängt eine Liste von Listenern vom Provider-Objekt, aus dem diese Liste besteht.
Woher bezieht der Anbieter die Liste der Hörer? Ja, wo will er! Es gibt eine Milliarde und eine Möglichkeit, den Hörer und das Ereignis zu verbinden. Alle sind absolut gültig und inkompatibel. Zu Beginn haben wir beschlossen, dass die Standardisierung des „One True Way“ für die Registrierung von Studenten zu begrenzt ist. Indem Sie jedoch den Prozess des Verbindens des Listeners mit dem Dispatcher standardisieren, erhalten Sie eine hervorragende Flexibilität, ohne den Benutzer zu etwas Seltsamem und Unverständlichem zu zwingen.
Außerdem gibt der Code nicht an, was der Listener ist. Es kann jedes PHP-Fragment sein, das zur Signalwahrnehmung fähig ist: eine Funktion, eine anonyme Funktion, eine Objektmethode, alles. Da das aufgerufene Objekt alles kann, ist es zulässig, als Listener eine anonyme Funktion zu haben, die das verzögerte Laden eines Dienstes aus einem DI-Container ausführt und die Methode im Dienst aufruft, die tatsächlich den Abhörcode enthält.
Kurz gesagt, der Dispatcher ist eine einfache API für Bibliotheksautoren. Listener-Anbieter bieten eine robuste und flexible API für Framework-Integratoren, und die Beziehung zwischen dem Dispatcher und dem Anbieter bringt sie zusammen.
Einfaches Beispiel
Im Allgemeinen sieht das Schema, alle Teile zu einem Ganzen zu kombinieren, ungefähr so aus.
class Dispatcher implements EventDispatcherInterface { public function __construct(ListenerProviderInterface $provider) { $this->provider = $provider; } public function dispatch(object $event) { foreach ($this->provider->getListenersForEvent($event) as $listener) { $listener($event); } return $event; } } $dispatcher = new Dispatcher($provider); $event = new SomethingHappened(); $dispatcher->dispatch($event);
Dieser kleine Code bietet große Möglichkeiten und ist sehr flexibel. In den folgenden Artikeln werden wir detailliert auf seine Eigenschaften eingehen, einige strukturelle Lösungen analysieren und die vielen Möglichkeiten zur Verwendung solcher leichtgewichtigen Ereignisse betrachten.
Code
PSR-14 wird bereits von wichtigen Frameworks und Anwendungen unterstützt.
- Matthew Weier O'Phinney hat bereits zugesagt, die Unterstützung für PSR-14 in zend-eventmanager 4.0 im Zend-Framework einzuführen.
- Symfony hat kürzlich Änderungen an EventDispatcher angekündigt , um die Kompatibilität mit PSR-14 zu gewährleisten, die in 5.0 / 5.1 volle Unterstützung bieten wird.
- Das Yii-Framework gab seine Absicht bekannt, das PSR-14 in Version 3.0 zu integrieren.
- Benni Mack von TYPO3 CMS sagte, dass in der nächsten TYPO3-Version alle vorhandenen Trap + Signal / Slot-Konzepte den PSR-14 unterstützen werden.
PSR-14 verfügt außerdem über drei voll funktionsfähige unabhängige Implementierungen, die Sie bereits in jeder Anwendung verwenden können.
- Tukio von Larry Garfield, Autor dieses Artikels.
- Phly Event Dispatcher von Matthew Weier O'Phinney.
- Kart von Benni Mack, der als eingebettetes Plugin arbeitet.
Der Autor dankt der gesamten PSR-Arbeitsgruppe:
Larry Garfield ,
Cees-Jan Kiewiet ,
Benjamin Mack ,
Elizabeth Smith ,
Ryan Weaver und
Matthew Weier O'Phinney . Während der gesamten Arbeit war der Prozess äußerst produktiv: Alle arbeiteten gemeinsam zusammen, wie es sein sollte. Das Ergebnis ist erfreulich, und ich möchte, dass alle weiteren Anstrengungen in der gemeinsamen Arbeit an der Architektur so produktiv sind.
Weitere Details finden Sie entweder im Original des nächsten Teils und in der Dokumentation oder am 17. Mai bei PHP Russia . Die zweite Option ist aus mehreren Gründen attraktiv. Zum Beispiel gehört der Leiter des Programmkomitees, Alexander ( Samdark ) Makarov, zu denjenigen, die die PSR-14 in Yii eingeführt haben. Und im Prinzip ist die Zusammensetzung des Programmkomitees und der Redner unglaublich stark, es gibt kaum ein Thema aus dem Bereich des professionellen Einsatzes von PHP, das auf dieser Konferenz nicht diskutiert werden kann.