Bioyino - porazdeljen, razširljiv zbiralnik metrik

Итак, вы собираете метрики. Как и мы. Мы тоже собираем метрики. Конечно же, нужные для бизнеса. Сегодня мы расскажем о самом первом звене системы нашего мониторинга — statsd-совместимом сервере агрегации biojino, zakaj smo ga napisali in zakaj smo brubeck opustili.

Bioyino - porazdeljen, razširljiv zbiralnik metrik

Iz naših prejšnjih člankov (1, 2) lahko ugotovite, da smo do nekaj časa zbirali oznake z uporabo Brubeck. Napisana je v C. Z vidika kode je preprosta kot vtič (to je pomembno, ko želite prispevati) in, kar je najpomembnejše, obdeluje naše količine 2 milijona metrik na sekundo (MPS) na vrhuncu brez težav. V dokumentaciji je navedena podpora za 4 milijone MPS z zvezdico. To pomeni, da boste dobili navedeno številko, če pravilno konfigurirate omrežje v Linuxu. (Ne vemo, koliko MPS lahko dobite, če pustite omrežje takšno, kot je). Kljub tem prednostim smo imeli več resnih pritožb glede brubecka.

Претензия 1. Github, razvijalec projekta, ga je prenehal podpirati: objavljati popravke in popravke, sprejemati naš in (ne samo naš) PR. V zadnjih nekaj mesecih (nekje februar-marec 2018) se je aktivnost ponovno začela, pred tem pa je bilo skoraj 2 leti popolnega zatišja. Poleg tega se projekt razvija za notranje potrebe Gihub, kar lahko postane resna ovira za uvedbo novih funkcij.

Претензия 2. Natančnost izračunov. Brubeck zbere skupno 65536 vrednosti za združevanje. V našem primeru lahko za nekatere metrike med obdobjem združevanja (30 sekund) prispe veliko več vrednosti (1 na vrhuncu). Kot rezultat tega vzorčenja se največje in najmanjše vrednosti zdijo neuporabne. Na primer takole:

Bioyino - porazdeljen, razširljiv zbiralnik metrik
Kot je bilo

Bioyino - porazdeljen, razširljiv zbiralnik metrik
Kako bi moralo biti

Iz istega razloga so zneski praviloma napačno izračunani. Sem dodajte hrošč z 32-bitnim prelivom s plavajočim elementom, ki na splošno pošlje strežnik v segfault, ko prejme na videz nedolžno metriko, in vse postane super. Mimogrede, napaka ni bila odpravljena.

In končno, Zahtevek X. V času pisanja smo ga pripravljeni predstaviti vsem 14 bolj ali manj delujočim implementacijam statsd, ki smo jih lahko našli. Predstavljajmo si, da je neka posamezna infrastruktura tako zrasla, da sprejem 4 milijonov MPS ni več dovolj. Ali tudi če še ni zrasel, vendar so metrike za vas že tako pomembne, da že kratki, 2-3 minutni padci na grafikonih lahko postanejo kritični in povzročijo napade nepremostljive depresije med menedžerji. Ker je zdravljenje depresije nehvaležna naloga, so potrebne tehnične rešitve.

Prvič, toleranca napak, tako da nenadna težava na strežniku ne povzroči psihiatrične zombi apokalipse v pisarni. Drugič, skaliranje, da lahko sprejme več kot 4 milijone MPS, brez kopanja globoko v omrežni sklad Linuxa in mirno raste "v širino" do zahtevane velikosti.

Ker smo imeli prostor za skaliranje, smo se odločili začeti s toleranco napak. "O! Toleranca napak! Preprosto je, zmoremo,« smo pomislili in zagnali 2 strežnika, na vsakem dvignili kopijo brubecka. Da bi to naredili, smo morali kopirati promet z metrikami na oba strežnika in celo pisati za to majhna korist. S tem smo rešili problem tolerance napak, vendar ... ne zelo dobro. Sprva se je vse zdelo super: vsak brubeck zbere svojo različico združevanja, zapiše podatke v Graphite enkrat na 30 sekund in prepiše stari interval (to se naredi na strani Graphite). Če en strežnik nenadoma odpove, imamo vedno drugega s svojo kopijo združenih podatkov. Ampak tukaj je težava: če strežnik odpove, se na grafih pojavi "žaga". To je posledica dejstva, da brubeckovi 30-sekundni intervali niso sinhronizirani in v trenutku trka eden od njih ni prepisan. Ko se zažene drugi strežnik, se zgodi isto. Precej znosno, vendar želim boljše! Tudi problem razširljivosti ni izginil. Vse metrike še vedno "letijo" na en strežnik, zato smo omejeni na iste 2-4 milijone MPS, odvisno od nivoja omrežja.

Če malo razmislite o problemu in hkrati kopljete sneg z lopato, vam lahko pride na misel naslednja očitna ideja: potrebujete statsd, ki lahko deluje v porazdeljenem načinu. To je tisto, ki izvaja sinhronizacijo med vozlišči v času in meritvah. “Seveda, takšna rešitev verjetno že obstaja,” smo rekli in šli na Google…. In niso našli ničesar. Po pregledu dokumentacije za različne statistike (https://github.com/etsy/statsd/wiki#server-implementations od 11.12.2017. decembra XNUMX), nismo našli popolnoma ničesar. Očitno se niti razvijalci niti uporabniki teh rešitev še niso srečali s TOLIKI metrikami, sicer bi zagotovo kaj iznašli.

In potem smo se spomnili na "igračo" statsd - bioyino, ki je bila napisana na hackathonu Just for Fun (ime projekta je ustvaril skript pred začetkom hackathona) in ugotovili, da nujno potrebujemo svoj statsd. Za kaj?

  • ker je na svetu premalo statsd klonov,
  • ker je mogoče zagotoviti želeno ali skoraj želeno toleranco napak in razširljivost (vključno s sinhronizacijo agregiranih metrik med strežniki in reševanjem problema pošiljanja konfliktov),
  • ker je mogoče meritve izračunati natančneje kot brubeck,
  • ker lahko sami zberete podrobnejšo statistiko, ki nam je brubeck praktično ni posredoval,
  • ker sem imel priložnost programirati lastno hiperzmogljivo laboratorijsko aplikacijo za porazdeljeno merilo, ki ne bo v celoti ponovila arhitekture druge podobne hiperfore ... no, to je to.

Na kaj pisati? Seveda v Rustu. Zakaj?

  • ker je že obstajal prototip rešitve,
  • ker je avtor članka že takrat poznal Rust in je želel vanj napisati nekaj za produkcijo z možnostjo, da bi ga dal v odprto kodo,
  • ker jeziki z GC niso primerni za nas zaradi narave prejetega prometa (skoraj v realnem času) in so premori GC praktično nesprejemljivi,
  • ker potrebujete največjo zmogljivost, primerljivo s C
  • ker nam Rust zagotavlja neustrašno sočasnost, in če bi ga začeli pisati v C/C++, bi si nakopali še več ranljivosti, prelivanja medpomnilnika, pogojev tekmovanja in drugih strašnih besed kot brubeck.

Obstajal je tudi argument proti Rustu. Podjetje ni imelo izkušenj z ustvarjanjem projektov v Rustu, zdaj pa ga tudi ne nameravamo uporabiti v glavnem projektu. Zato so bili resni strahovi, da se ne bo nič izšlo, a smo se odločili tvegati in poskusiti.

Čas je minil ...

Končno je bila po več neuspelih poskusih pripravljena prva delujoča različica. Kaj se je zgodilo? To se je zgodilo.

Bioyino - porazdeljen, razširljiv zbiralnik metrik

Vsako vozlišče prejme svoj nabor metrik in jih kopiči ter ne združuje metrik za tiste tipe, kjer je njihov celoten nabor potreben za končno združevanje. Vozlišča so med seboj povezana z nekakšnim protokolom porazdeljenega zaklepanja, ki vam omogoča, da med njimi izberete edino (tu smo jokali), ki je vredno pošiljanja metrik Velikemu. To težavo trenutno rešuje Konzul, v prihodnje pa avtorjeve ambicije segajo v lasten izvajanje Splav, kjer bo najbolj vreden seveda vodja konsenza. Poleg konsenza vozlišča precej pogosto (privzeto enkrat na sekundo) pošiljajo svojim sosedom tiste dele vnaprej agregiranih metrik, ki jim jih je uspelo zbrati v tisti sekundi. Izkazalo se je, da sta skaliranje in toleranca napak ohranjena – vsako vozlišče še vedno hrani celoten nabor metrik, vendar se metrike pošiljajo že združene, prek TCP in kodirane v binarni protokol, tako da so stroški podvajanja bistveno nižji v primerjavi z UDP. Kljub dokaj velikemu številu vhodnih meritev kopičenje zahteva zelo malo pomnilnika in še manj procesorja. Za naše visoko stisljive meritve je to le nekaj deset megabajtov podatkov. Kot dodaten bonus, v Graphitu nimamo nepotrebnih prepisov podatkov, kot je bilo to v primeru burbecka.

Paketi UDP z metriko so neuravnoteženi med vozlišči v omrežni opremi s preprostim Round Robin. Seveda omrežna strojna oprema ne razčlenjuje vsebine paketov in zato lahko potegne veliko več kot 4M paketov na sekundo, da ne omenjamo metrik, o katerih ne ve prav nič. Če upoštevamo, da metrike ne prihajajo ena za drugo v vsakem paketu, potem na tem mestu ne predvidevamo težav z zmogljivostjo. Če se strežnik zruši, omrežna naprava hitro (v 1-2 sekundah) zazna to dejstvo in odstrani zrušeni strežnik iz rotacije. Zaradi tega je mogoče pasivna (tj. nevodilna) vozlišča vklopiti in izklopiti tako rekoč, ne da bi opazili padce na grafikonih. Največ, kar izgubimo, je del metrike, ki je prišla v zadnji sekundi. Nenadna izguba/izklop/preklop vodilnega bo še vedno povzročil manjšo anomalijo (30-sekundni interval še vedno ni sinhroniziran), če pa obstaja komunikacija med vozlišči, je te težave mogoče zmanjšati, na primer s pošiljanjem sinhronizacijskih paketov .

Malo o notranji strukturi. Aplikacija je seveda večnitna, vendar je arhitektura niti drugačna od tiste, ki se uporablja v brubecku. Niti v brubecku so enake - vsaka od njih je odgovorna za zbiranje in združevanje informacij. V bioyinu so delavci razdeljeni v dve skupini: tisti, ki so odgovorni za omrežje, in tisti, ki so odgovorni za združevanje. Ta delitev vam omogoča bolj fleksibilno upravljanje aplikacije glede na vrsto metrike: kjer je potrebno intenzivno združevanje, lahko dodate agregatorje, kjer je veliko omrežnega prometa, lahko dodate število omrežnih tokov. Trenutno na naših strežnikih delujemo v 8 omrežnih in 4 agregacijskih tokovih.

Del za štetje (odgovoren za združevanje) je precej dolgočasen. Medpomnilniki, ki jih napolnijo omrežni tokovi, se porazdelijo med štetje tokov, kjer se nato razčlenijo in združijo. Na zahtevo so podane metrike za pošiljanje drugim vozliščem. Vse to, vključno s pošiljanjem podatkov med vozlišči in delom s Consulom, se izvaja asinhrono in teče v ogrodju Tokio.

Veliko več težav pri razvoju je povzročal omrežni del, ki je odgovoren za sprejemanje metrik. Glavni cilj ločevanja omrežnih tokov v ločene entitete je bila želja po zmanjšanju časa, ki ga tok porabi ne za branje podatkov iz vtičnice. Možnosti, ki uporabljajo asinhroni UDP in običajni recvmsg, so hitro izginile: prva porabi preveč CPU uporabniškega prostora za obdelavo dogodkov, druga zahteva preveč preklopov konteksta. Zato se zdaj uporablja recvmmsg z velikimi blažilniki (in blažilniki vam, gospodje častniki, niso nič!). Podpora za običajni UDP je rezervirana za lahke primere, ko recvmmsg ni potreben. V večsporočilnem načinu je mogoče doseči glavno stvar: veliko večino časa omrežna nit grabi čakalno vrsto OS - bere podatke iz vtičnice in jih prenaša v medpomnilnik uporabniškega prostora, le občasno preklopi na posredovanje napolnjenega medpomnilnika agregatorji. Čakalna vrsta v vtičnici se praktično ne kopiči, število izpuščenih paketov praktično ne raste.

Obvestilo

V privzetih nastavitvah je velikost medpomnilnika nastavljena na precej veliko. Če se nenadoma odločite, da boste sami preizkusili strežnik, boste morda naleteli na dejstvo, da po pošiljanju majhnega števila metrik ne bodo prispele v Graphite in bodo ostale v medpomnilniku omrežnega toka. Za delo z majhnim številom metrik morate v konfiguraciji nastaviti bufsize in task-queue-size na manjše vrednosti.

Za konec še nekaj lestvic za ljubitelje lestvic.

Statistični podatki o številu dohodnih metrik za vsak strežnik: več kot 2 milijona MPS.

Bioyino - porazdeljen, razširljiv zbiralnik metrik

Onemogočanje enega od vozlišč in prerazporeditev dohodnih meritev.

Bioyino - porazdeljen, razširljiv zbiralnik metrik

Statistika o odhodnih metrikah: vedno pošilja le eno vozlišče - šef napada.

Bioyino - porazdeljen, razširljiv zbiralnik metrik

Statistika delovanja vsakega vozlišča ob upoštevanju napak v različnih sistemskih modulih.

Bioyino - porazdeljen, razširljiv zbiralnik metrik

Podrobnosti dohodnih metrik (imena metrik so skrita).

Bioyino - porazdeljen, razširljiv zbiralnik metrik

Kaj nameravamo z vsem tem narediti naprej? Seveda, napiši kodo, prekleto ...! Projekt je bil prvotno načrtovan kot odprtokoden in bo tak ostal skozi celotno življenjsko dobo. Naši takojšnji načrti vključujejo prehod na lastno različico Rafta, spremembo enakovrednega protokola v bolj prenosljivega, uvedbo dodatne notranje statistike, nove vrste meritev, popravke napak in druge izboljšave.

Seveda je vsakdo dobrodošel, da pomaga pri razvoju projekta: ustvarja PR, Issues, če je le mogoče se bomo odzvali, izboljšali itd.

Glede na to, to je vse, ljudje, kupujte naše slone!



Vir: www.habr.com

Dodaj komentar