No ano passado, o
PHP-FIG , o
PHP Compatibility Concepts Group, lançou várias novas especificações. O último,
PSR-14 , é dedicado ao envio de eventos. Como outros PSRs, essa é uma especificação local, mas tem um grande impacto em muitos aspectos da padronização.
De um tradutor: Esta é uma tradução da primeira parte de uma série de publicações em que Larry (Crell) Garfield, um dos membros do PHP-FIG, explica o que é o PSR-14, do que é capaz e do que não é, e qual é a melhor maneira de usá-lo. seus projetos.Finalidade
O envio de eventos é usado há muito tempo em vários idiomas. Se você já usou o EventDispatcher no
Symfony , o sistema de eventos no
Laravel , os ganchos no Drupal, o
Event Manager na estrutura do Zend, o pacote
League \ Event ou algo assim, então você entende do que se trata.
Em um sentido geral, todos esses sistemas são uma forma de "mediador-observador". Um pedaço de código envia uma mensagem do tipo - "evento" e o intermediário a envia para outros pedaços de código individuais - "ouvintes". Às vezes, o sinal é direcionado apenas em uma direção, às vezes o "ouvinte" pode, de alguma forma, transmitir dados de volta ao chamador. Obviamente, eles são todos diferentes e não muito compatíveis entre si.
Esse é um problema para bibliotecas independentes que desejam se conectar a várias bibliotecas e aplicativos. Muitas bibliotecas podem ser expandidas enviando eventos de uma forma ou de outra para que outro código possa contatá-las. Mas essa camada intermediária é, de fato, proprietária. A biblioteca que executa o Symfony EventDispatcher é então mesclada com o Symfony. Para usá-lo em outro lugar, é necessário instalar o EventDispatcher e conectar-se às bibliotecas do programa. A biblioteca que chama o sistema de ligação do Drupal
module_invoke_all()
é então vinculada ao Drupal. E assim por diante
O objetivo do PSR-14 é livrar as bibliotecas dessa dependência. Isso permite que as bibliotecas se expandam por uma fina camada comum e, em seguida, facilitem sua transferência para outro ambiente sem esforço e despesa adicional, por exemplo, no Symfony, Zend Framework, Laravel, TYPO3, eZ Platform ou Slim. Enquanto o ambiente tiver compatibilidade com o PSR-14, tudo funcionará.
Especificação
Como já mencionado, a especificação é bastante leve. Essas são três interfaces em um método e uma meta descrição de como usá-las. Tudo é simples e conveniente. Abaixo está o código para essas interfaces (sem comentários para economizar espaço).
namespace Psr\EventDispatcher; interface EventDispatcherInterface { public function dispatch(object $event); } interface ListenerProviderInterface { public function getListenersForEvent(object $event) : iterable; } interface StoppableEventInterface { public function isPropagationStopped() : bool; }
Os dois primeiros são o núcleo da especificação.
StoppableEventInterface
é uma extensão à qual retornaremos mais tarde.
Acho que
EventDispatcher
familiar para a maioria de vocês - é apenas um objeto com o método pelo qual você passa o evento - o intermediário sobre o qual você já falou. O evento em si, no entanto, não está definido - pode ser
qualquer objeto PHP . Mais sobre isso mais tarde.
A maioria das implementações existentes possui um objeto ou conjunto de funções que atuam como intermediário ou despachante e um local para registrar o código que recebe o evento (ouvintes). Para o PSR-14, deliberadamente dividimos essas duas responsabilidades em objetos separados. O expedidor recebe uma lista de ouvintes do objeto provedor que compõe essa lista.
De onde o provedor obtém a lista de ouvintes? Sim, onde ele quer! Há um bilhão e uma maneira de conectar o ouvinte e o evento, todos eles são absolutamente válidos e incompatíveis. No início, decidimos que a padronização do “One True Way” para o registro de alunos seria muito limitada. No entanto, ao padronizar o processo de conexão do ouvinte ao despachante, você pode obter excelente flexibilidade sem forçar o usuário a fazer algo estranho e incompreensível.
Além disso, o código não indica o que é o ouvinte. Pode ser qualquer fragmento PHP capaz de percepção de sinal: uma função, uma função anônima, um método de objeto, qualquer coisa. Como o objeto chamado pode fazer qualquer coisa, é permitido ter, como ouvinte, uma função anônima que executa o carregamento atrasado de um serviço de um contêiner de DI e chama o método no serviço, que realmente contém o código de escuta.
Em resumo, o expedidor é uma API simples e fácil para os autores da biblioteca. Os provedores de ouvinte oferecem uma API robusta e flexível para integradores de estrutura, e o relacionamento entre o expedidor e o provedor os reúne.
Exemplo simples
Em termos gerais, o esquema de combinar todas as partes em um todo será mais ou menos assim.
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);
Este pequeno pedaço de código oferece grandes oportunidades e é muito flexível. Nos artigos a seguir, falaremos em detalhes sobre suas propriedades, analisaremos algumas soluções estruturais e consideraremos as várias maneiras de usar esses eventos leves.
Código
O PSR-14 já é suportado pelas principais estruturas e aplicativos.
- Matthew Weier O'Phinney já se comprometeu a introduzir o suporte ao PSR-14 no zend-eventmanager 4.0 na estrutura do Zend.
- O Symfony anunciou recentemente alterações no EventDispatcher para compatibilidade com o PSR-14, que fornecerá suporte completo no 5.0 / 5.1.
- A estrutura do Yii anunciou sua intenção de integrar o PSR-14 na versão 3.0 .
- Benni Mack, do TYPO3 CMS, disse que no próximo lançamento do TYPO3, todos os conceitos de interceptação + sinal / slot existentes apoiarão o PSR-14.
O PSR-14 também possui três implementações independentes totalmente funcionais que você já pode usar em qualquer aplicativo.
- Tukio por Larry Garfield, autor deste artigo.
- Phly Event Dispatcher por Matthew Weier O'Phinney.
- Kart de Benni Mack, que funciona como um plug-in incorporado.
O autor agradece a todo o grupo de trabalho do PSR:
Larry Garfield ,
Cees-Jan Kiewiet ,
Benjamin Mack ,
Elizabeth Smith ,
Ryan Weaver e
Matthew Weier O'Phinney . Durante todo o trabalho, o processo foi extremamente produtivo: todos trabalharam juntos, coletivamente, como deveria ser. O resultado é agradável, e eu gostaria que todos os esforços adicionais no trabalho conjunto em arquitetura fossem tão produtivos.
Você pode descobrir mais detalhes no original da próxima parte e na documentação ou em 17 de maio no PHP Russia . A segunda opção é atraente por vários motivos. Por exemplo, o chefe do Comitê de Programa, Alexander ( samdark ) Makarov, está entre os que introduziram o PSR-14 em Yii. E, em princípio, a composição do Comitê de Programa e dos palestrantes é incrivelmente forte, quase não existe nenhum tópico da esfera do uso profissional do PHP que não possa ser discutido nesta conferência.