Vägledning för prestandajustering för Storm i HDInsight och Azure Data Lake Storage Gen1
Förstå de faktorer som bör beaktas när du justerar prestandan för en Azure Storm-topologi. Det är till exempel viktigt att förstå egenskaperna hos det arbete som utförs av piparna och bultarna (oavsett om arbetet är I/O eller minnesintensivt). Den här artikeln beskriver en rad riktlinjer för prestandajustering, inklusive felsökning av vanliga problem.
Förutsättningar
- En Azure-prenumeration. Se Hämta en kostnadsfri utvärderingsversion av Azure.
- Ett Azure Data Lake Storage Gen1-konto. Anvisningar om hur du skapar en finns i Kom igång med Azure Data Lake Storage Gen1.
- Ett Azure HDInsight-kluster med åtkomst till ett Data Lake Storage Gen1-konto. Se Skapa ett HDInsight-kluster med Data Lake Storage Gen1. Se till att du aktiverar Fjärrskrivbord för klustret.
- Riktlinjer för prestandajustering för Data Lake Storage Gen1. Allmänna prestandabegrepp finns i Data Lake Storage Gen1 Vägledning för prestandajustering.
Justera topologins parallellitet
Du kanske kan förbättra prestanda genom att öka samtidigheten för I/O till och från Data Lake Storage Gen1. En Storm-topologi har en uppsättning konfigurationer som bestämmer parallelliteten:
- Antal arbetsprocesser (arbetarna fördelas jämnt över de virtuella datorerna).
- Antal spout-exekutorinstanser.
- Antal bultexekutorinstanser.
- Antal spout-uppgifter.
- Antal bultuppgifter.
Överväg till exempel följande i ett kluster med 4 virtuella datorer och 4 arbetsprocesser, 32 spout-utförare och 32 spout-uppgifter samt 256 bultexekutorer och 512 bultuppgifter:
Varje övervakare, som är en arbetsnod, har en JVM-process (Single Worker Java Virtual Machine). Den här JVM-processen hanterar 4 spouttrådar och 64 bulttrådar. Aktiviteter körs sekventiellt i varje tråd. Med den föregående konfigurationen har varje spout-tråd en uppgift och varje bulttråd har två uppgifter.
Här är de olika komponenterna i Storm och hur de påverkar den parallellitetsnivå som du har:
- Huvudnoden (kallas Nimbus i Storm) används för att skicka och hantera jobb. Dessa noder har ingen inverkan på graden av parallellitet.
- Övervakarnoderna. I HDInsight motsvarar detta en virtuell Azure-dator med arbetsnod.
- Arbetsuppgifterna är Storm-processer som körs på de virtuella datorerna. Varje arbetsuppgift motsvarar en JVM-instans. Storm distribuerar antalet arbetsprocesser som du anger till arbetsnoderna så jämnt som möjligt.
- Spout- och bultexekutorinstanser. Varje körinstans motsvarar en tråd som körs inom arbetarna (JVM).
- Storm-uppgifter. Det här är logiska uppgifter som var och en av dessa trådar kör. Detta ändrar inte graden av parallellitet, så du bör utvärdera om du behöver flera uppgifter per utförare eller inte.
Få bästa prestanda från Data Lake Storage Gen1
När du arbetar med Data Lake Storage Gen1 får du bästa möjliga prestanda om du gör följande:
- Slå ihop dina små tillägg i större storlekar (helst 4 MB).
- Gör så många samtidiga begäranden som möjligt. Eftersom varje bulttråd utför blockeringsläsningar vill du ha någonstans i intervallet 8-12 trådar per kärna. Detta håller nätverkskortet och processorn väl utnyttjat. En större virtuell dator möjliggör fler samtidiga begäranden.
Exempeltopologi
Anta att du har ett kluster med åtta arbetsnoder med en virtuell D13v2 Azure-dator. Den här virtuella datorn har åtta kärnor, så bland de åtta arbetsnoderna har du totalt 64 kärnor.
Låt oss säga att vi gör åtta bulttrådar per kärna. Med tanke på 64 kärnor innebär det att vi vill ha 512 totala bultexekutorinstanser (det vill säga trådar). I det här fallet ska vi anta att vi börjar med en JVM per virtuell dator och främst använder trådens samtidighet i JVM för att uppnå samtidighet. Det innebär att vi behöver åtta arbetsuppgifter (en per virtuell Azure-dator) och 512 bultexekutorer. Med tanke på den här konfigurationen försöker Storm distribuera arbetarna jämnt över arbetsnoder (även kallade övervakarnoder), vilket ger varje arbetsnod en JVM. Nu inom övervakarna försöker Storm fördela exekutorerna jämnt mellan övervakarna, vilket ger varje övervakare (dvs. JVM) åtta trådar vardera.
Justera ytterligare parametrar
När du har den grundläggande topologin kan du överväga om du vill justera någon av parametrarna:
- Antal JVM:er per arbetsnod. Om du har en stor datastruktur (till exempel en uppslagstabell) som du är värd för i minnet kräver varje JVM en separat kopia. Du kan också använda datastrukturen i många trådar om du har färre JVM:er. För bultens I/O gör inte antalet JVM:er lika stor skillnad som antalet trådar som läggs till mellan dessa JVM:er. För enkelhetens skull är det en bra idé att ha en JVM per arbetare. Beroende på vad bulten gör eller vilken programbearbetning du behöver kan du dock behöva ändra det här numret.
- Antal spout-utförare. Eftersom bultar används i föregående exempel för att skriva till Data Lake Storage Gen1 är antalet pipar inte direkt relevanta för bultens prestanda. Beroende på hur mycket bearbetning eller I/O som sker i pipen är det dock en bra idé att justera piparna för bästa prestanda. Se till att du har tillräckligt med pipar för att kunna hålla bultarna upptagna. Utdatahastigheterna för piparna ska matcha bultarnas dataflöde. Den faktiska konfigurationen beror på pipen.
- Antal uppgifter. Varje bult körs som en enda tråd. Ytterligare uppgifter per bult ger ingen ytterligare samtidighet. Den enda gången de är till nytta är om din process för att erkänna tuppeln tar en stor del av din bultkörningstid. Det är en bra idé att gruppera många tupplar i ett större tillägg innan du skickar en bekräftelse från bulten. Så i de flesta fall ger flera uppgifter ingen ytterligare fördel.
- Lokal gruppering eller blandningsgruppering. När den här inställningen är aktiverad skickas tupplar till bultar i samma arbetsprocess. Detta minskar kommunikationen mellan processer och nätverksanrop. Detta rekommenderas för de flesta topologier.
Det här grundläggande scenariot är en bra utgångspunkt. Testa med dina egna data för att justera föregående parametrar för att uppnå optimala prestanda.
Justera pipen
Du kan ändra följande inställningar för att justera pipen.
Tuppelns timeout: topology.message.timeout.secs. Den här inställningen avgör hur lång tid ett meddelande tar att slutföra och ta emot bekräftelse innan det anses vara misslyckat.
Maximalt minne per arbetsprocess: worker.childopts. Med den här inställningen kan du ange ytterligare kommandoradsparametrar för Java-arbetare. Den vanligaste inställningen här är XmX, som bestämmer det maximala minne som allokeras till en JVM-heap.
Maximalt antal väntande utdata: topology.max.spout.pending. Den här inställningen bestämmer hur många tupplar som kan köras (som ännu inte har bekräftats på alla noder i topologin) per spout-tråd när som helst.
En bra beräkning att göra är att uppskatta storleken på var och en av dina tupplar. Ta sedan reda på hur mycket minne en spout-tråd har. Det totala minne som allokerats till en tråd, dividerat med det här värdet, bör ge dig den övre gränsen för den maximala pipen som väntar på parametern.
Justera bulten
När du skriver till Data Lake Storage Gen1 anger du en storlekssynkroniseringsprincip (buffert på klientsidan) till 4 MB. En tömning eller hsync() utförs sedan endast när buffertstorleken ligger på det här värdet. Den Data Lake Storage Gen1 drivrutinen på den virtuella arbetsdatorn buffrar automatiskt, såvida du inte uttryckligen utför en hsync().
Standard Data Lake Storage Gen1 Storm-bult har en principparameter för storlekssynkronisering (fileBufferSize) som kan användas för att justera den här parametern.
I I/O-intensiva topologier är det en bra idé att låta varje bulttråd skriva till sin egen fil och ange en filrotationsprincip (fileRotationSize). När filen når en viss storlek rensas strömmen automatiskt och en ny fil skrivs till. Den rekommenderade filstorleken för rotation är 1 GB.
Hantera tuppelns data
I Storm håller en pip på en tuppeln tills den uttryckligen bekräftas av bulten. Om en tuppeln har lästs av bulten men inte har bekräftats ännu, kanske pipen inte har sparats i Data Lake Storage Gen1 serverdelen. När en tuppeln har bekräftats kan pipen garanteras beständighet av bulten och kan sedan ta bort källdata från den källa som den läser från.
För bästa prestanda på Data Lake Storage Gen1, ha bultbufferten 4 MB tupppeldata. Skriv sedan till Data Lake Storage Gen1 serverdelen som en skrivning på 4 MB. När data har skrivits till arkivet (genom att anropa hflush()) kan bulten bekräfta data tillbaka till pipen. Detta är vad exempelbulten som tillhandahålls här gör. Det är också acceptabelt att hålla ett större antal tupplar innan hflush()-anropet görs och tupplar bekräftas. Detta ökar dock antalet tupplar under flygning som spouten måste innehålla och ökar därför mängden minne som krävs per JVM.
Anteckning
Program kan ha ett krav på att bekräfta tupplar oftare (i datastorlekar som är mindre än 4 MB) av andra icke-prestandaskäl. Det kan dock påverka I/O-dataflödet till lagringens serverdel. Väg försiktigt denna kompromiss mot bultens I/O-prestanda.
Om inkommande tupplar inte är hög, så det tar lång tid att fylla bufferten på 4 MB, bör du överväga att minimera detta genom att:
- Minska antalet bultar, så det finns färre buffertar att fylla.
- Att ha en tidsbaserad eller räkningsbaserad princip, där en hflush() utlöses varje x-tömning eller var y millisekunder, och tupplar som ackumulerats hittills bekräftas tillbaka.
Dataflödet i det här fallet är lägre, men med en långsam händelsehastighet är maximalt dataflöde ändå inte det största målet. De här åtgärderna hjälper dig att minska den totala tid det tar för en tupplar att flöda till butiken. Det här kan vara viktigt om du vill ha en pipeline i realtid även med låg händelsefrekvens. Observera också att om din inkommande tupplar är låg bör du justera parametern topology.message.timeout_secs, så att tupplar inte överskrider tidsgränsen när de buffrar eller bearbetas.
Övervaka din topologi i Storm
När topologin körs kan du övervaka den i Storm-användargränssnittet. Här är de viktigaste parametrarna att titta på:
Total processkörningsfördröjning. Det här är den genomsnittliga tid det tar för en tuppeln att genereras av pipen, bearbetas av bulten och bekräftas.
Total svarstid för bultprocess. Detta är den genomsnittliga tid som tuppeln spenderar vid bulten tills den får en bekräftelse.
Total svarstid för körning av bult. Det här är den genomsnittliga tid som bulten använder i körningsmetoden.
Antal fel. Detta refererar till antalet tupplar som inte kunde bearbetas helt innan tidsgränsen överst.
Kapacitet. Det här är ett mått på hur upptaget systemet är. Om det här numret är 1 fungerar bultarna så fort de kan. Om den är mindre än 1 ökar du parallelliteten. Om den är större än 1 minskar du parallelliteten.
Felsöka vanliga problem
Här följer några vanliga felsökningsscenarier.
Många tupplar håller på att ta time out. Titta på varje nod i topologin för att avgöra var flaskhalsen finns. Den vanligaste orsaken till detta är att bultarna inte kan hänga med i piparna. Detta leder till att tupplar täpper till de interna buffertarna i väntan på att bearbetas. Överväg att öka timeout-värdet eller minska den maximala pipen som väntar.
Det finns en hög total svarstid för processkörning, men en kort svarstid för bultprocessen. I det här fallet är det möjligt att tupplar inte erkänns tillräckligt snabbt. Kontrollera att det finns tillräckligt många bekräftelser. En annan möjlighet är att de väntar i kön för länge innan bultarna börjar bearbeta dem. Minska den maximala pipen som väntar.
Det finns en lång svarstid för körning av bultar. Det innebär att metoden execute() för bulten tar för lång tid. Optimera koden eller titta på skrivstorlekar och tömningsbeteende.
Data Lake Storage Gen1 begränsning
Om du når gränsen för bandbredd som tillhandahålls av Data Lake Storage Gen1 kan det uppstå aktivitetsfel. Kontrollera om det finns begränsningsfel i aktivitetsloggarna. Du kan minska parallelliteten genom att öka containerstorleken.
Om du vill kontrollera om du blir begränsad aktiverar du felsökningsloggningen på klientsidan:
- I Ambari>Storm>Config>Advanced storm-worker-log4j ändrar du <root level="info"> till <root level="debug">. Starta om alla noder/tjänst för att konfigurationen ska börja gälla.
- Övervaka Storm-topologiloggarna på arbetsnoder (under /var/log/storm/worker-artifacts/<TopologyName>/<port>/worker.log) för Data Lake Storage Gen1 begränsningsfel.
Nästa steg
Ytterligare prestandajustering för Storm kan refereras i den här bloggen.
Ytterligare ett exempel att köra finns i det här på GitHub.