2011-09-28 5 views
4

Similaire au promises pattern Je cherche un modèle d'événement qui évite d'avoir besoin de polluer des objets avec les méthodes addEventListener/etc, je veux être capable de retourner un objet, que peut être annulé ainsi que "résolu" plusieurs fois.Similaire aux promesses/différées qui supportent plusieurs résultats et annulation

Par exemple, je peux écrire une méthode qui retourne un objet « intervalle », quelque chose comme ceci:

var ticker = createTicker(1000); 
var subscription = ticker.then(function() { console.log('tick') }); 
... later on ... 
subscription.cancel(); 

Les principales différences étant ici, semblable à une promesse des événements sont standardisés, afin que je puisse abonnez-vous sans avoir besoin de connaître le nom de l'événement, mais contrairement à une promesse, le "achèvement" peut arriver plusieurs fois, et peut même être annulé (cela équivaudrait à removeEventListener). Je suis intéressé de voir si cela est légal avec des promesses, telles que le gestionnaire de progression pourrait être utilisé pour plusieurs rappels, et le gestionnaire complet jamais utilisé, mais plus important encore, qu'il existe un concept de désabonnement à partir d'une promesse .

Si ce n'est pas le cas, et que les promesses sont spécifiques à ce scénario, existe-t-il un modèle normalisé pour faire ce que j'ai décrit?

+0

Que diriez-vous de regarder le modèle EventEmitter? – HaxElit

+0

Personnellement, je suis contre les modèles traditionnels comme EventEmitter, car cela a une dépendance de prototype (ie que tous les objets eventables implémentent des membres émetteurs d'événements, ou si vous avez un EventEmitter statique, chaque librairie doit être d'accord avec un EventEmitter) , le modèle de promesse est bon car il encapsule l '«événement» et n'exige pas que les bibliothèques s'accordent sur un objet de promesse standard, car le modèle de promesses est tout polymorphique – meandmycode

Répondre

2

La possibilité d'annuler peut être ajoutée à une implémentation de promesse, sans rompre le paradigme principal d'avoir des rappels de succès/échec uniques.

En fait, jQuery a déjà annulation pour les cas de promesse qu'il revient de jQuery.ajax appels:

Pour la compatibilité ascendante avec XMLHttpRequest, un objet jqXHR va exposer les propriétés et méthodes suivantes:

  • readyState
  • état
  • statusText
  • responseXML et/ou responseText lorsque la requête sous-jacente a répondu avec xml et/ou text, respectivement
  • setRequestHeader (nom, valeur) qui s'écarte de la norme en remplaçant l'ancienne valeur par la nouvelle plutôt que de concaténer la nouvelle valeur l'ancien
  • getAllResponseHeaders()
  • getResponseHeader()
  • abort()

Vous pouvez écrire un wrapper setTimeout qui expose une interface de promesse avec une méthode d'annulation supplémentaire.

Cependant, une fois que vous entrez dans le territoire multi-feu, je pense que ce n'est pas ce à quoi les promesses sont destinées. Vous devrez définir un grand nombre de règles et d'exceptions sur la façon dont les tirs multiples se dérouleront parallèlement à la fonctionnalité de promesse régulière. Cela n'a pas beaucoup de sens pour moi d'utiliser les promesses de cette façon.


Mise à jour (sur la base de discussion dans les commentaires):

Voici un exemple d'implémentation d'une promesse "proxy" qui permet l'interruption relayage plus des faits/échec callbacks:

http://jsfiddle.net/atesgoral/qvtqu/

+0

Merci, je suis d'accord que je ne peux pas avoir plusieurs appels complets Une implémentation correcte de la promesse devrait être une erreur si le code de contrôle essayait de le faire, donc si une fausse promesse tentait de le faire, cela causerait des problèmes immédiats avec d'autres promesses si on les enchaînait ensemble. En ce qui concerne l'annulation j'aurais dû être plus clair à ce sujet, c'est l'annulation de l'abonnement vs annulation de l'opération .. par exemple, un appel ajax je voudrais annuler mon rappel étant tiré, pas l'opération réelle. – meandmycode

+0

Je suppose plus que tout que j'essaie de trouver un modèle existant comme je l'ai décrit, ou s'il y a une discussion sur les rappels de désinscription d'une promesse. – meandmycode

+0

Vous pouvez écrire un proxy qui relaie les rappels d'une promesse cible. Ce proxy lui-même exposerait une interface de promesse et peut être annulé. À l'annulation, il cesserait de relayer les rappels. Au lieu d'écrire votre propre proxy, vous pouvez également utiliser deferred.pipe(): http://api.jquery.com/deferred.pipe/ –

Questions connexes