Netramesh – lengvas paslaugų tinklelio sprendimas

Kai pereiname nuo monolitinės programos prie mikro paslaugų architektūros, susiduriame su naujais iššūkiais.

Monolitinėje programoje paprastai gana lengva nustatyti, kurioje sistemos dalyje įvyko klaida. Greičiausiai problema yra pačiame monolito kode arba duomenų bazėje. Bet kai pradedame ieškoti problemos mikroservisų architektūroje, viskas nebe taip akivaizdu. Turime rasti visą užklausos kelią nuo pradžios iki pabaigos ir pasirinkti jį iš šimtų mikro paslaugų. Be to, daugelis iš jų taip pat turi savo saugyklas, kurios taip pat gali sukelti loginių klaidų, taip pat problemų dėl veikimo ir atsparumo gedimams.

Netramesh – lengvas paslaugų tinklelio sprendimas

Ilgai ieškojau įrankio, kuris padėtų susidoroti su tokiomis problemomis (apie tai rašiau Habré: 1, 2), bet galiausiai sukūriau savo atvirojo kodo sprendimą. Šiame straipsnyje kalbu apie paslaugų tinklelio metodo naudą ir dalinuosi nauju jos įgyvendinimo įrankiu.

Paskirstytasis sekimas yra įprastas klaidų nustatymo paskirstytose sistemose problemos sprendimas. O kas, jei toks informacijos rinkimo apie tinklo sąveikas metodas dar neįdiegtas sistemoje arba, dar blogiau, dalis sistemos jau veikia tinkamai, bet iš dalies ne, nes nebuvo pridėta prie senų paslaugų ? Norint nustatyti tikslią problemos priežastį, būtina turėti išsamų vaizdą apie tai, kas vyksta sistemoje. Ypač svarbu suprasti, kurios mikropaslaugos dalyvauja svarbiausiuose verslui svarbiuose keliuose.

Čia mums gali padėti paslaugų tinklo metodas, kuris susidoros su visais tinklo informacijos rinkimo mechanizmais žemesniu lygiu, nei veikia pačios paslaugos. Šis metodas leidžia perimti visą srautą ir jį analizuoti. Be to, programos net neturi nieko apie tai žinoti.

Paslaugų tinklelio metodas

Pagrindinė paslaugų tinklelio metodo idėja yra pridėti dar vieną infrastruktūros sluoksnį tinkle, kuris leis mums atlikti bet kokius veiksmus, susijusius su sąveika tarp paslaugų. Dauguma diegimų veikia taip: prie kiekvienos mikropaslaugos pridedamas papildomas šoninių priekabų konteineris su skaidriu tarpiniu serveriu, per kurį perduodamas visas įeinantis ir išeinantis paslaugos srautas. Būtent čia galime atlikti klientų balansavimą, taikyti saugumo politiką, riboti užklausų skaičių ir rinkti svarbią informaciją apie paslaugų sąveiką gamyboje.

Netramesh – lengvas paslaugų tinklelio sprendimas

Sprendimai

Jau yra keletas šio metodo įgyvendinimų: Tas pats и linkerd2. Jie suteikia daug funkcijų iš dėžutės. Tačiau tuo pat metu atsiranda didelių išteklių išlaidų. Be to, kuo didesnis klasteris, kuriame veikia tokia sistema, tuo daugiau išteklių reikės naujai infrastruktūrai išlaikyti. „Avito“ valdome „kubernetes“ grupes, kuriose yra tūkstančiai paslaugų egzempliorių (ir jų skaičius toliau sparčiai auga). Šiuo metu Istio sunaudoja ~ 300 Mb RAM vienam paslaugos egzemplioriui. Dėl daugybės galimybių skaidrus balansavimas turi įtakos ir bendram paslaugų reakcijos laikui (iki 10ms).

Dėl to pasižiūrėjome, kokių būtent galimybių šiuo metu mums reikia, ir nusprendėme, kad pagrindinė priežastis, kodėl pradėjome diegti tokius sprendimus, buvo galimybė skaidriai rinkti sekimo informaciją iš visos sistemos. Taip pat norėjome kontroliuoti paslaugų sąveiką ir atlikti įvairias manipuliacijas su antraštėmis, kurios perkeliamos tarp paslaugų.

Dėl to priėjome prie savo sprendimo:  Netramešas.

Netramešas

Netramešas yra lengvas paslaugų tinklelio sprendimas su galimybe keisti mastelį be galo, nepriklausomai nuo paslaugų skaičiaus sistemoje.

Pagrindiniai naujojo sprendimo tikslai buvo mažos pridėtinės sąnaudos ir didelis našumas. Tarp pagrindinių funkcijų iš karto norėjome turėti galimybę skaidriai siųsti sekimo intervalus į mūsų Jaeger sistemą.

Šiandien dauguma debesų sprendimų įdiegta Golange. Ir, žinoma, tam yra priežasčių. Rašyti tinklo programas Golang, kurios veikia asinchroniškai su įvesties/išvesties ir prireikus keičiasi per branduolius, yra patogu ir gana paprasta. Ir, kas taip pat labai svarbu, našumo pakanka šiai problemai išspręsti. Todėl ir pasirinkome Golangą.

Našumas

Mes sutelkėme savo pastangas siekdami maksimalaus produktyvumo. Sprendimui, kuris yra įdiegtas šalia kiekvieno paslaugos egzemplioriaus, reikia nedaug RAM ir procesoriaus laiko. Ir, žinoma, atsakymo vėlavimas taip pat turėtų būti mažas.

Pažiūrėkime, kokių rezultatų gavome.

RAM

„Netramesh“ sunaudoja ~ 10 Mb be srauto ir 50 Mb daugiausiai su apkrova iki 10000 XNUMX RPS vienam egzemplioriui.

Istio envoy proxy mūsų klasteriuose su tūkstančiais egzempliorių visada sunaudoja ~300Mb. Tai neleidžia jo keisti visame klasteryje.

Netramesh – lengvas paslaugų tinklelio sprendimas

Netramesh – lengvas paslaugų tinklelio sprendimas

Su „Netramesh“ atminties suvartojimas sumažėjo ~10 kartų.

CPU

CPU naudojimas yra palyginti vienodas esant apkrovai. Tai priklauso nuo užklausų skaičiaus per laiko vienetą prie šoninės priekabos. Vertės esant 3000 užklausų per sekundę piko metu:

Netramesh – lengvas paslaugų tinklelio sprendimas

Netramesh – lengvas paslaugų tinklelio sprendimas

Yra dar vienas svarbus momentas: Netramesh – sprendimas be valdymo plokštumos ir be apkrovos nenaudoja CPU laiko. Naudojant Istio, šoninės priekabos visada atnaujina aptarnavimo galinius taškus. Dėl to šį paveikslėlį galime matyti be apkrovos:

Netramesh – lengvas paslaugų tinklelio sprendimas

Ryšiui tarp paslaugų naudojame HTTP/1. Istio atsako laikas pailgėjo iki 5-10 ms, o tai yra gana daug tarnyboms, kurios pasiruošusios atsakyti per milisekundę. Naudojant „Netramesh“, šis laikas sumažėjo iki 0.5–2 ms.

Mastelis

Nedidelis kiekvieno tarpinio serverio sunaudojamų išteklių kiekis leidžia jį įdėti šalia kiekvienos paslaugos. „Netramesh“ buvo sąmoningai sukurtas be valdymo plokštumos komponento, kad kiekviena šoninė priekabė būtų lengva. Dažnai techninės priežiūros tinklelio sprendimuose valdymo plokštuma paskirsto paslaugų aptikimo informaciją kiekvienai priekabai. Kartu su ja pateikiama informacija apie skirtąjį laiką ir balansavimo nustatymus. Visa tai leidžia nuveikti daug naudingų dalykų, tačiau, deja, tai išpučia šonines priekabas.

Paslaugos atradimas

Netramesh – lengvas paslaugų tinklelio sprendimas

„Netramesh“ neprideda jokių papildomų paslaugų aptikimo mechanizmų. Visas eismas skaidriai perduodamas per „Netra“ šoninę priekabą.

Netramesh palaiko HTTP/1 programos protokolą. Norėdami jį apibrėžti, naudojamas konfigūruojamas prievadų sąrašas. Paprastai sistemoje yra keli prievadai, per kuriuos vyksta HTTP ryšys. Pavyzdžiui, paslaugų ir išorinių užklausų sąveikai naudojame 80, 8890, 8080. Šiuo atveju jas galima nustatyti naudojant aplinkos kintamąjį NETRA_HTTP_PORTS.

Jei naudojate „Kubernetes“ kaip organizatorių ir jo paslaugų objekto mechanizmą, skirtą ryšiams tarp paslaugų klasterio viduje, mechanizmas išlieka toks pat. Pirma, mikroservisas gauna paslaugos IP adresą naudodamas kube-dns ir atidaro naują ryšį su juo. Šis ryšys pirmiausia užmezgamas su vietiniu „netra“ šonu, o visi TCP paketai iš pradžių patenka į „Netra“. Tada „netra-sidecar“ užmezga ryšį su pradine paskirties vieta. NAT pod IP mazge išlieka lygiai toks pat, kaip ir be netros.

Paskirstytas sekimas ir konteksto persiuntimas

„Netramesh“ suteikia funkciją, reikalingą HTTP sąveikos sekimo intervalams siųsti. Netra-sidecar analizuoja HTTP protokolą, matuoja užklausų delsą ir iš HTTP antraščių ištraukia reikiamą informaciją. Galiausiai visus pėdsakus gauname vienoje Jaeger sistemoje. Smulkiai konfigūracijai taip pat galite naudoti oficialios bibliotekos pateiktus aplinkos kintamuosius jaeger go biblioteka.

Netramesh – lengvas paslaugų tinklelio sprendimas

Netramesh – lengvas paslaugų tinklelio sprendimas

Tačiau yra problema. Kol paslaugos nesugeneruos ir neišsiųs specialios uber antraštės, sistemoje nematysime susietų sekimo intervalų. Ir to reikia, kad greitai surastume problemų priežastį. Netramesh vėl turi sprendimą. Įgaliotieji serveriai nuskaito HTTP antraštes ir, jei juose nėra uber sekimo ID, sugeneruoja jį. „Netramesh“ taip pat saugo informaciją apie gaunamas ir siunčiamas užklausas šoninėje priekaboje ir suderina jas praturtindamas jas reikiamomis išeinančių užklausų antraštėmis. Paslaugose tereikia išsiųsti tik vieną antraštę X-Request-Id, kurį galima konfigūruoti naudojant aplinkos kintamąjį NETRA_HTTP_REQUEST_ID_HEADER_NAME. Norėdami valdyti „Netramesh“ konteksto dydį, galite nustatyti šiuos aplinkos kintamuosius: NETRA_TRACING_CONTEXT_EXPIRATION_MILLISECONDS (laikas, kurį kontekstas bus saugomas) ir NETRA_TRACING_CONTEXT_CLEANUP_INTERVAL (konteksto valymo dažnis).

Taip pat galima sujungti kelis kelius sistemoje, pažymint juos specialiu seanso prieigos raktu. „Netra“ leidžia įdiegti HTTP_HEADER_TAG_MAP paversti HTTP antraštes atitinkamomis sekimo intervalo žymomis. Tai gali būti ypač naudinga atliekant bandymus. Išlaikę funkcinį testą, galite pamatyti, kuriai sistemos daliai įtakos turėjo filtravimas pagal atitinkamą seanso raktą.

Užklausos šaltinio nustatymas

Norėdami nustatyti, iš kur gauta užklausa, galite naudoti automatinio antraštės pridėjimo prie šaltinio funkciją. Naudojant aplinkos kintamąjį NETRA_HTTP_X_SOURCE_HEADER_NAME Galite nurodyti antraštės pavadinimą, kuris bus automatiškai įdiegtas. Naudojant NETRA_HTTP_X_SOURCE_VALUE galite nustatyti reikšmę, kuriai bus nustatyta X-Source antraštė visoms siunčiamoms užklausoms.

Tai leidžia tolygiai paskirstyti šią naudingą antraštę visame tinkle. Tada galėsite jį naudoti paslaugose ir įtraukti į žurnalus bei metrikas.

Eismo maršrutas ir „Netramesh“ vidinės dalys

Netramesh susideda iš dviejų pagrindinių komponentų. Pirmasis, netra-init, nustato tinklo taisykles, kad perimtų srautą. Jis naudoja iptables peradresavimo taisykles perimti visą ar dalį eismo šoninėje priekaboje, kuri yra antrasis pagrindinis „Netramesh“ komponentas. Galite konfigūruoti, kuriuos prievadus reikia perimti įeinantiems ir išeinantiems TCP seansams: INBOUND_INTERCEPT_PORTS, OUTBOUND_INTERCEPT_PORTS.

Įrankis taip pat turi įdomią funkciją – tikimybinį maršrutą. Jei „Netramesh“ naudojate išskirtinai sekimo intervalams rinkti, tada gamybinėje aplinkoje galite sutaupyti išteklių ir įgalinti tikimybinį maršrutą naudodami kintamuosius. NETRA_INBOUND_PROBABILITY и NETRA_OUTBOUND_PROBABILITY (nuo 0 iki 1). Numatytoji reikšmė yra 1 (visas srautas perimamas).

Po sėkmingo perėmimo „Netra“ priekaba priima naują ryšį ir naudoja SO_ORIGINAL_DST lizdo parinktis, kad gautumėte pradinę paskirties vietą. Tada „Netra“ atidaro naują ryšį su pradiniu IP adresu ir užmezga dvipusį TCP ryšį tarp šalių, išklausydama visą einantį srautą. Jei prievadas apibrėžtas kaip HTTP, „Netra“ bando jį išanalizuoti ir atsekti. Jei HTTP analizavimas nepavyksta, Netra grįžta prie TCP ir skaidriai perduoda baitus.

Priklausomybės grafiko kūrimas

Gavęs daug sekimo informacijos Jaeger, noriu gauti visą sistemos sąveikų grafiką. Tačiau jei jūsų sistema yra gana apkrauta ir per dieną susikaupia milijardai sekimo intervalų, juos sukaupti nėra taip lengva užduotis. Yra oficialus būdas tai padaryti: kibirkšties priklausomybės. Tačiau užtruks kelias valandas, kol bus sukurta visa diagrama, ir bus priverstas atsisiųsti visą pastarųjų XNUMX valandų duomenų rinkinį iš „Jaeger“.

Jei naudojate Elasticsearch sekimo intervalams saugoti, galite naudoti paprastas „Golang“ įrankis, kuri per kelias minutes sukurs tą patį grafiką, naudodama Elasticsearch funkcijas ir galimybes.

Netramesh – lengvas paslaugų tinklelio sprendimas

Kaip naudoti Netramesh

„Netra“ galima lengvai pridėti prie bet kurios paslaugos, kurioje veikia bet koks orkestrantas. Galite pamatyti pavyzdį čia.

Šiuo metu „Netra“ neturi galimybės automatiškai įdiegti šoninių priekabų į servisus, tačiau planų juos įgyvendinti yra.

Netramesh ateitis

Pagrindinis tikslas Netramešas yra pasiekti minimalias išteklių sąnaudas ir aukštą našumą, suteikiant pagrindines tarptarnybinio ryšio stebėjimo ir kontrolės galimybes.

Ateityje „Netramesh“ palaikys ne tik HTTP, bet ir kitus programų lygmens protokolus. L7 maršrutas bus pasiekiamas artimiausiu metu.

Jei susiduriate su panašiomis problemomis, naudokite „Netramesh“ ir parašykite mums su klausimais ir pasiūlymais.

Šaltinis: www.habr.com

Добавить комментарий