Reaktiva system
Tillbaka till världen av vanliga servrar som svarar på anrop från webbläsare. Idén med ett system som är “reactive” är att det genom att var smidigt och tåligt kan reagera (react) till variationer i last och miljö. Reagera och hantera att nätverk kommer och går, att last går upp och ner och att maskiner går sönder.
De som kommit på “reactive manifesto” menar att sättet att uppnå detta är att använda meddelanden mellan fristående processer. Tankarna om systemet känns igen från telekom med Erlang som språk. Det mest uppenbara alternativet är node.js som använder JavaScript vilket ju är asynkront till sin natur och även node.js var representerat på konferensen.
Det traditionella sättet att ta hand om anrop från webbläsare med en tråd per request är väldigt lätt att förstå och debugga men gör förstås att en server inte kan hantera fler samtidiga requests än storleken på dess trådpool. Dagens webbsystem behöver vara flexiblare än så.
Vi servar inte webbsidor idag, vi kör program i browsern som hämtar data med ajax eller till och med håller en uppkoppling öppen och blir anropade från servern för uppdateringar. Med async servlet kan vi göra processning i bakgrunden medan trådpoolen fortsätter med nästa request. Spring 4 har också detta stöd.
Processning i bakgrunden utgörs typiskt inte av en process utan vi behöver ofta hämta data från flera olika källor, databaser, andra servrar, kanske någon uträkning etc. Vi vill inte göra det seriellt utan skicka iväg alla frågor, få in svar och sedan kombinera ihop slutresultatet.
Det här blir väldigt snabbt väldigt snårigt om vi inte har praktiska abstraktioner. I en enklare nivå kan vi tänka oss Javas Executors och att använda Futures och för att hantera resultat som kommer att komma senare. För att göra större system kommer Akka in i bilden. I Akka har vi typiskt många (tusen eller miljontals) enkla processer som kallas Actors som vi skickar meddelanden till och som även mellan pratar mellan sig genom meddelanden.
Actors har väldigt lite overhead så det kostar inget att dela upp problem genom att skapa flera actors för att ta hand om delar av problemet. I ramverket ingår också att ta hand om fel om en actor kraschar. Det hela är moget och mycket användbart.
Det enda tråkiga men som knappast går att undvika är att system med många löst kopplade processer är bra mycket svårare att debugga och testa än den gamla varianten med en tråd genom hela processningen. Kanske något så enkelt som transaktionsid och logg-aggregering kan räcka en bra bit.
Akka, Futures, Promises, Rx extensions m fl abstraktioner finns för både Java och Scala men många saker blir betydligt elegantare i Scala.
Men Java 8 då?
Jo konferensen innehöll ett antal föredrag om Java 8 med dess funktionella delar men ämnet är rätt gammalt så det kan du läsa om på andra håll.
Bild av Stephen Chin under CC BY 2.0