Przejdź do treści

Narzędzia Świata: super-event-emitter.js

Framework ze wsparciem eventów? Backbone. Świetny i lekki framework. Jednym z 4 fundamentów jest Backbone.Events. Jego prosta implementacja bardzo przypadła mi do gustu. 4 niezbędne funkcje to: on, once, off, trigger. Zachęciło mnie to do stworzenia nowego projektu: super-event-emitter. Więcej o nim poniżej.

Baner promujący artykuł

Backbone.Events

Przyzwyczajony do składni:

_.extend(MyCustomObject.prototype, Backbone.Events);

Mogłem teraz w mojej definicji MyCustomObject wyzwalać zdarzenia (trigger), oraz na nie nasłuchiwać on.

Jednak nie ma sensu używania całej biblioteki Backbone tylko na potrzeby korzystania ze zdarzeń. Postanowiłem, że w tych aplikacjach, które miały dependency w postaci wyżej wymienionej biblioteki, podmienię na coś. Cokolwiek, co będzie tylko robiło to samo.

Problem ze wspólnym API

Moje poszukiwania skupiły się na kilku bibliotekach:

Żadna z nich nie pomogła mi w tym czego chciałem:

  • Dodać zarządzanie zdarzeniami dla już istniejącego obiektu
  • Callback uruchomiony z przekazanym kontekstem

Nowy projekt

Dlatego postanowiłem, że napiszę swój. Prawdopodobnie gdzieś w czeluściach internetu można znaleźć bliźniaczy projekt, jednak dla mnie to zbyt duże wyzwania, aby przez kilka dni szukać jakiegoś projektu, który mogę kosztem max 2h pracy stworzyć od zera i być z niego zadowolony.

Wybrałem ciekawą nazwę i opublikowałem stary projekt, który był pierwotnie stworzony w celach edukacyjnych. Nazwa nowego projektu to super-event-emitter. Przynajmniej tak nazywa się paczka w npm registry.

W rejestrze paczek npm można znaleźć ogromną liczbę różnych event emitterów. Chciałem mieć najlżejsza wersję (w miarę możliwości) ale również i czytelną.

Super Event Emitter API

Publiczny interfejs jest bardzo prosty. Opieramy się na 4 funkcjach: on, once, off, emit. Nic więcej. Nazwy mówią same za siebie.

  • on - nasłuchujemy na event, który uruchomi callback, w ewentualnym przekazanym kontekście
  • once - podobnie jak on, ale po pierwszym wyzwoleniu zdarzenia, kasujemy tego listenera
  • off - kasujemy przekazany listener według jego nazwy i konkretnej definicji callbacka
  • emit - krótsza nazwa niż trigger, wyzwala zdarzenie
var SuperEventEmitter = require('super-event-emitter');

function MyCar() {
    SuperEventEmitter.mixin(this);
}

var ferrari = new MyCar();

ferrari.on('test', function () {
    console.log('triggered!');
}, this);

ferrari.emit('test');

Przykład dostępny tutaj: https://tonicdev.com/56a74ef27f528a0d002fabb5/56aa9e75c8f1470c0060db4f

Podsumowanie

Jestem bardzo zadowolony, że w projekcie, gdzie dorzucałem 2k linii (Backbone) tylko po to, aby mieć wsparcie zdarzeń, teraz mogę dodać 140 linii i jestem zadowolony, że wszystko działa pięknie!