De pub-sub fruitmand op z'n Twitters | Software Innovators
In mijn voorgaande blog was ik nog van mening dat Twitter het pub-sub (Publisher Subscriber) pattern nieuw leven had ingeblazen met nieuwe features. Ik stelde, in mijn naïviteit, het observer pattern en het pub-sub pattern gelijk aan elkaar, als waren het twee appeltjes in ene fruitmand. Maar niets is minder waar. Het is zelfs ook niet te classificeren als een appel en een peer, in dezelfde fruitmand. Nee, ik zou het zo moeten zeggen: De fruitmand is de pub-sub, en het observer pattern mag dan de appel of de peer wezen. Maar ach, laat het observer pattern een banaan zijn, wat ik niet door had is dat deze puur een implementatie was van het veel grotere pub-sub pattern.
Wat ik in Twitter ontdekte aan nieuwe 'features' van het observer pattern, waren in wezen niet meer dan verschillende soorten fruit uit de o zo rijke vitamine mand. Toegegeven, Twitter heeft de fruitmand aangevuld, met laten we zeggen, de kiwi van het doorsturen op eigen initiatief – retweeten voor Twitter intimi – alsook met de galiameloen van gelijkwaardigheid. Een pub is ook een sub en andersom. Maar, in essentie heeft Twitter niets nieuws onder de zon gebracht en zich enkel flink tegoed gedaan aan al het lekkers dat pub-sub te bieden heeft. En laten we wel wezen, Twitter heeft geen windeieren gelegd.
Maar, laten we nu zelf eens de fruitmand eens ondersteboven kieperen om te zien hoe Twitter zo gezond is geworden. Het duurt even voordat we de mand te pakken hebben, maar als we de architectuur kast open doen zien we hem al snel staan op de message-based plank. Naast een stukje zeep waar de letters 'SOAP' op af te lezen zijn. Dat wat betreft de context. Een blik in de mand leert ons al snel het volgende. Het bevat namelijk drie soorten fruit: List-Based -, Broadcast-Based – en Content-Based Publish/Subscribe. [1]
De eerste categorie bevat ons overbekende observer-pattern. Een publisher houdt een lijst bij (hence the name) met subscribers. Maar in dit pattern heten de publishers dan wel subjects en de subscribers observers. En om het nog lastiger te maken, hoewel een publisher de subscriber notificeert (notify) implementeert de subscriber deze methode omdat die door de publisher wordt aangeroepen. En hoewel de subscriber zich kan abonneren (attach) en deabonneren (detach) worden deze methoden in de publisher verzorgd en dus andersom geïmplementeerd wat het lezen van het klasse-diagram wat lastig maakt. Het gedrag wordt dus verkeerd om afgelezen.
Verder is het een nogal sobere implementatie van het pub-sub met een tight-coupling tussen publishers en subscribers. Nadelen kunnen we snel ontdekken. Met honderden subscribers zal de publisher class niet meer toekomen aan zijn dagelijkse bezigheden maar zal full-time aan het notificeren zijn. Het andere nadeel is de tight-coupling die compile-time wordt gezet. De publishers en subscribers dienen elkaar dan al te kennen. Het is niet mogelijk om run-time een willekeurig subscriber aan een publisher te koppelen als we dat niet van tevoren hebben voorzien en dit in een routine hebben verstopt om die twee, op een bepaald aan elkaar te knopen.
Die tight-coupling is in de tweede categorie – Broadcast-Based -geheel verdwenen. Een publisher bekommert zich niet over eventuele subscribers. Hij mikt gewoon een event in de lucht en laat het daarbij. De subscribers moeten, afhankelijk van de implementatie, zelf hun content uit de vloedgolf van events filteren.
De derde categorie is recent toegevoegd. Het onderscheidt zich van de vorige twee door deze als 'topic-based' te markeren en zichzelf de naam 'content-based' toe te kennen. Dit houdt zoveel in als: bij topic-based wordt er gewerkt met een voorgedefinieerde set aan publishers en subscribers, waarbij content-based puur werkt met de inhoud van het bericht. In Twitter-taal zouden we zeggen: De @-directive is topic-based omdat het een specifiek en bestaande node verondersteld. De #-directive is content-based omdat het niet doelt op een specifieke ontvanger, nee ontvangers mogen zich zelf abonneren op deze content. Zo is het bij deze variant dus mogelijk karrenvrachten vol events te publiceren waar geen enkele subscriber oren naar heeft, wat op Twitter m.i. maar al te vaak gebeurd.
In conclusie kunnen we beamen dat Twitter niet alleen goed heeft gekeken naar het pub-sub pattern, maar deze ook fantastisch heeft geïmplementeerd. Nogmaals [2] een overzicht, die ik wat heb bijgewerkt, met punten die de ik de moeite waard vindt om te vermelden over Twitters implementatie van pub-sub:
De wereld bestaadt uit objecten die zowel publishers als subscribers zijn;
Een pub-sub-object kan een bericht doorsturen (retweeten) naar zijn topic-based-subscribers als hij dit van belang acht;
Een event / message kan zowel topic-based als content-based als wel allebei zijn. Bijvoorbeeld: '@sogyo hello world #sogyo';
Trends geven events een extra dimensie voor content-based-subscribers doordat ze zich kunnen abonneren op de populairste content binnen een geografisch gebied. En dit zou natuurlijk uitgebreid kunnen worden met meerdere zinvolle trends.
Nu jeuken mijn handen om een voorbeeld-app te maken die eens wat meer pub-sub-vitaminen in zich heeft dan enkel het gedoodverfde Observer-pattern. Maar het blogje is al lang genoeg. Wellicht dat ik op een later tijdstip dit zal realiseren.