Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Iesaku izlasÄ«t 2019. gada beigu ziņojuma atÅ”ifrējumu, ko sagatavojis Aleksandrs Valjaļkins ā€œOptimizÄ“Å”ana programmā VictoriaMetricsā€.

VictoriaMetrics ā€” ātra un mērogojama DBVS datu glabāŔanai un apstrādei laikrindu veidā (ieraksts veido laiku un vērtÄ«bu kopu, kas atbilst Å”im laikam, piemēram, kas iegÅ«ta, periodiski aptaujājot sensoru statusu vai apkopojot datus metrika).

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Å eit ir saite uz Ŕī ziņojuma video - https://youtu.be/MZ5P21j_HLE

Slaidi

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Pastāsti mums par sevi. Es esmu Aleksandrs Valjaļkins. Šeit mans GitHub konts. Es aizraujos ar Go un veiktspējas optimizāciju. Es uzrakstīju daudz noderīgu un ne tik noderīgu bibliotēku. Viņi sākas ar vienu vai otru fast, vai ar quick priedēklis.

PaŔlaik es strādāju pie VictoriaMetrics. Kas tas ir un ko es tur daru? Par to es runāŔu Ŕajā prezentācijā.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Ziņojuma izklāsts ir Ŕāds:

  • Pirmkārt, es jums pastāstÄ«Å”u, kas ir VictoriaMetrics.
  • Tad es jums pastāstÄ«Å”u, kas ir laikrindas.
  • Tad es jums pastāstÄ«Å”u, kā darbojas laikrindu datubāze.
  • Tālāk es jums pastāstÄ«Å”u par datu bāzes arhitektÅ«ru: no kā tā sastāv.
  • Un tad pāriesim pie optimizācijas, ko piedāvā VictoriaMetrics. Å Ä« ir optimizācija apgrieztajam indeksam un optimizācija bitkopas ievieÅ”anai Go.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Vai kāds no skatÄ«tājiem zina, kas ir VictoriaMetrics? Oho, daudzi jau zina. Tā ir laba ziņa. Tiem, kas nezina, Ŕī ir laikrindu datubāze. Tas ir balstÄ«ts uz ClickHouse arhitektÅ«ru, uz dažām ClickHouse ievieÅ”anas detaļām. Piemēram, uz tādiem kā: MergeTree, paralēli aprēķini uz visiem pieejamajiem procesora kodoliem un veiktspējas optimizācija, strādājot pie datu blokiem, kas tiek ievietoti procesora keÅ”atmiņā.

VictoriaMetrics nodroŔina labāku datu saspieŔanu nekā citas laikrindu datu bāzes.

Tas mērogojas vertikāli - tas ir, jÅ«s varat pievienot vairāk procesoru, vairāk RAM vienā datorā. VictoriaMetrics veiksmÄ«gi izmantos Å”os pieejamos resursus un uzlabos lineāro produktivitāti.

VictoriaMetrics mērogojas arī horizontāli - tas ir, jūs varat pievienot papildu mezglus VictoriaMetrics klasterim, un tā veiktspēja palielināsies gandrīz lineāri.

Kā jÅ«s uzminējāt, VictoriaMetrics ir ātra datu bāze, jo es nevaru rakstÄ«t citus. Un tas ir rakstÄ«ts Go, tāpēc es par to runāju Å”ajā tikÅ”anās reizē.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Kas zina, kas ir laikrindas? ViņŔ arÄ« pazÄ«st daudzus cilvēkus. Laika rinda ir pāru sērija (timestamp, Š·Š½Š°Ń‡ŠµŠ½ŠøŠµ), kur Å”ie pāri ir sakārtoti pēc laika. VērtÄ«ba ir peldoŔā komata skaitlis ā€“ float64.

Katra laika rinda ir unikāli identificēta ar atslēgu. No kā sastāv Ŕī atslēga? Tas sastāv no atslēgu un vērtÄ«bu pāru kopas, kas nav tukÅ”a.

Å eit ir laika rindas piemērs. Å Ä«s sērijas atslēga ir pāru saraksts: __name__="cpu_usage" ir metrikas nosaukums, instance="my-server" - Å”is ir dators, kurā tiek apkopota Ŕī metrika, datacenter="us-east" - Å”is ir datu centrs, kurā atrodas Å”is dators.

Mēs nonācām pie laikrindas nosaukuma, kas sastāv no trim atslēgu-vērtÄ«bu pāriem. Å Ä« atslēga atbilst pāru sarakstam (timestamp, value). t1, t3, t3, ..., tN - tie ir laikspiedoli, 10, 20, 12, ..., 15 ā€” atbilstoŔās vērtÄ«bas. Tas ir CPU lietojums noteiktā laikā noteiktai rindai.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Kur var izmantot laika rindas? Vai kādam ir kāda ideja?

  • Programmā DevOps varat izmērÄ«t centrālo procesoru, RAM, tÄ«klu, rps, kļūdu skaitu utt.
  • IoT - mēs varam izmērÄ«t temperatÅ«ru, spiedienu, Ä£eogrāfiskās koordinātas un kaut ko citu.
  • ArÄ« finanses ā€“ varam sekot lÄ«dzi visu veidu akcijām un valÅ«tām cenas.
  • Turklāt laikrindas var izmantot ražoÅ”anas procesu uzraudzÄ«bā rÅ«pnÄ«cās. Mums ir lietotāji, kuri izmanto VictoriaMetrics, lai uzraudzÄ«tu vēja turbÄ«nas robotiem.
  • Laika rindas ir noderÄ«gas arÄ« informācijas vākÅ”anai no dažādu ierīču sensoriem. Piemēram, dzinējam; riepu spiediena mērÄ«Å”anai; ātruma, attāluma mērÄ«Å”anai; benzÄ«na patēriņa mērÄ«Å”anai utt.
  • Laika rindas var izmantot arÄ« gaisa kuÄ£u uzraudzÄ«bai. Katrai lidmaŔīnai ir melnā kaste, kurā tiek apkopotas laika rindas dažādiem lidmaŔīnas veselÄ«bas parametriem. Laika rindas tiek izmantotas arÄ« kosmosa rÅ«pniecÄ«bā.
  • VeselÄ«bas aprÅ«pe ir asinsspiediens, pulss utt.

Var bÅ«t vairāk lietojumprogrammu, par kurām es aizmirsu, bet es ceru, ka jÅ«s saprotat, ka laikrindas tiek aktÄ«vi izmantotas mÅ«sdienu pasaulē. Un to izmantoÅ”anas apjoms ar katru gadu pieaug.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Kāpēc jums ir nepiecieÅ”ama laikrindu datu bāze? Kāpēc jÅ«s nevarat izmantot parastu relāciju datu bāzi, lai saglabātu laika rindas?

Tā kā laikrindas parasti satur lielu daudzumu informācijas, kuru ir grÅ«ti uzglabāt un apstrādāt parastajās datubāzēs. Tāpēc parādÄ«jās specializētas datu bāzes laikrindām. Å Ä«s bāzes efektÄ«vi uzglabā punktus (timestamp, value) ar doto atslēgu. Tie nodroÅ”ina API, lai nolasÄ«tu saglabātos datus pēc atslēgas, pēc viena atslēgas-vērtÄ«bas pāra, pēc vairākiem atslēgu un vērtÄ«bu pāriem, vai pēc regulārā izteiksmes. Piemēram, ja vēlaties atrast visu savu pakalpojumu CPU noslodzi kādā datu centrā Amerikā, tad jums ir jāizmanto Å”is pseidovaicājums.

Parasti laikrindu datu bāzes nodroÅ”ina specializētas vaicājumu valodas, jo laikrindu SQL nav Ä«paÅ”i piemērota. Lai gan ir datu bāzes, kas atbalsta SQL, tas nav Ä«paÅ”i piemērots. Vaicājumu valodas, piemēram, PromQL, InfluxQL, PlÅ«dums, Q. Ceru, ka kāds ir dzirdējis vismaz vienu no Ŕīm valodām. Daudzi cilvēki droÅ”i vien ir dzirdējuÅ”i par PromQL. Å Ä« ir Prometheus vaicājumu valoda.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Šādi izskatās mūsdienu laikrindu datu bāzes arhitektūra, izmantojot VictoriaMetrics kā piemēru.

Tas sastāv no divām daļām. Å Ä« ir apgrieztā indeksa glabāŔana un laikrindu vērtÄ«bu glabāŔana. Å Ä«s krātuves ir atdalÄ«tas.

Kad datu bāzē nonāk jauns ieraksts, mēs vispirms piekļūstam apgrieztajam indeksam, lai atrastu noteiktas kopas laikrindas identifikatoru. label=value noteiktai metrikai. Mēs atrodam Å”o identifikatoru un saglabājam vērtÄ«bu datu krātuvē.

Kad tiek saņemts pieprasÄ«jums izgÅ«t datus no TSDB, mēs vispirms pārejam uz apgriezto indeksu. Saņemsim visu timeseries_ids ieraksti, kas atbilst Å”ai kopai label=value. Un tad mēs iegÅ«stam visus nepiecieÅ”amos datus no datu noliktavas, ko indeksē timeseries_ids.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

ApskatÄ«sim piemēru, kā laikrindu datu bāze apstrādā ienākoÅ”o atlases vaicājumu.

  • Pirmkārt, viņa saņem visu timeseries_ids no apgriezta indeksa, kas satur dotos pārus label=value, vai atbilst noteiktai regulārai izteiksmei.
  • Pēc tam tas izgÅ«st visus datu punktus no datu krātuves noteiktā laika intervālā atrastajiem timeseries_ids.
  • Pēc tam datu bāze veic dažus aprēķinus par Å”iem datu punktiem atbilstoÅ”i lietotāja pieprasÄ«jumam. Un pēc tam tas atgriež atbildi.

Å ajā prezentācijā pastāstÄ«Å”u par pirmo daļu. Å Ä« ir meklÄ“Å”ana timeseries_ids pēc apgrieztā indeksa. Par otro daļu un treÅ”o daļu varēsiet noskatÄ«ties vēlāk VictoriaMetrics avoti, vai pagaidiet, kamēr sagatavoÅ”u citus ziņojumus :)

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Pāriesim pie apgrieztā indeksa. Daudzi var domāt, ka tas ir vienkārÅ”i. KurÅ” zina, kas ir apgrieztais indekss un kā tas darbojas? Ak, vairs nav tik daudz cilvēku. Mēģināsim saprast, kas tas ir.

PatiesÄ«bā tas ir vienkārÅ”i. Tā ir vienkārÅ”i vārdnÄ«ca, kas kartē atslēgu uz vērtÄ«bu. Kas ir atslēga? Å is pāris label=valueKur label Šø value - tās ir lÄ«nijas. Un vērtÄ«bas ir kopums timeseries_ids, kas ietver doto pāri label=value.

Apgrieztais indekss ļauj ātri atrast visu timeseries_ids, kas ir devuŔi label=value.

Tas arī ļauj ātri atrast timeseries_ids laikrindas vairākiem pāriem label=value, vai pāriem label=regexp. Kā tas notiek? Atrodot kopas krustpunktu timeseries_ids katram pārim label=value.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

ApskatÄ«sim dažādas apgrieztā indeksa realizācijas. Sāksim ar visvienkārŔāko naivu ievieÅ”anu. Viņa izskatās Ŕādi.

Funkcija getMetricIDs iegūst virkņu sarakstu. Katra rinda satur label=value. Šī funkcija atgriež sarakstu metricIDs.

Kā tas strādā? Šeit mums ir globāls mainīgais, ko sauc invertedIndex. Šī ir parasta vārdnīca (map), kas kartēs virkni, lai sadalītu ints. Līnija satur label=value.

Funkciju Ä«stenoÅ”ana: iegÅ«t metricIDs par pirmo label=value, tad ejam cauri visam pārējam label=value, mēs to sapratām metricIDs viņiem. Un izsauciet funkciju intersectInts, kas tiks apspriests tālāk. Un Ŕī funkcija atgriež Å”o sarakstu krustpunktu.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Kā redzat, apgrieztā indeksa ievieÅ”ana nav Ä«paÅ”i sarežģīta. Bet tā ir naiva Ä«stenoÅ”ana. Kādi mÄ«nusi tai ir? Galvenais naivās ievieÅ”anas trÅ«kums ir tāds, ka Ŕāds apgriezts indekss tiek saglabāts RAM. Pēc lietojumprogrammas restartÄ“Å”anas mēs zaudējam Å”o indeksu. Å is rādÄ«tājs netiek saglabāts diskā. Šāds apgriezts indekss, visticamāk, nebÅ«s piemērots datu bāzei.

Otrs trūkums ir saistīts arī ar atmiņu. Apgrieztajam indeksam jāiekļaujas RAM. Ja tas pārsniedz RAM lielumu, tad acīmredzot mēs saņemsim - no atmiņas kļūdas. Un programma nedarbosies.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Šo problēmu var atrisināt, izmantojot gatavus risinājumus, piemēram, LevelDBVai RocksDB.

ÄŖsāk sakot, mums ir vajadzÄ«ga datu bāze, kas ļauj ātri veikt trÄ«s darbÄ«bas.

  • Pirmā darbÄ«ba ir ierakstÄ«Å”ana ŠŗŠ»ŃŽŃ‡-Š·Š½Š°Ń‡ŠµŠ½ŠøŠµ uz Å”o datu bāzi. Viņa to dara ļoti ātri, kur ŠŗŠ»ŃŽŃ‡-Š·Š½Š°Ń‡ŠµŠ½ŠøŠµ ir patvaļīgas virknes.
  • Otrā darbÄ«ba ir ātra vērtÄ«bas meklÄ“Å”ana, izmantojot doto taustiņu.
  • Un treŔā darbÄ«ba ir ātra visu vērtÄ«bu meklÄ“Å”ana pēc noteiktā prefiksa.

LevelDB un RocksDB ā€“ Ŕīs datu bāzes izstrādāja Google un Facebook. Vispirms parādÄ«jās LevelDB. Tad puiÅ”i no Facebook paņēma LevelDB un sāka to uzlabot, viņi izveidoja RocksDB. Tagad gandrÄ«z visas iekŔējās datu bāzes darbojas pakalpojumā RocksDB Facebook iekÅ”ienē, ieskaitot tās, kas ir pārsÅ«tÄ«tas uz RocksDB un MySQL. Viņi viņu nosauca MyRocks.

Apgrieztu indeksu var ieviest, izmantojot LevelDB. Kā to izdarīt? Mēs saglabājam kā atslēgu label=value. Un vērtība ir tās laikrindas identifikators, kurā atrodas pāris label=value.

Ja mums ir daudz laika rindu ar doto pāri label=value, tad Å”ajā datu bāzē bÅ«s daudz rindu ar vienu un to paÅ”u atslēgu un atŔķirÄ«gu timeseries_ids. Lai iegÅ«tu visu sarakstu timeseries_ids, kas sākas ar Å”o label=prefix, mēs veicam diapazona skenÄ“Å”anu, kurai Ŕī datu bāze ir optimizēta. Tas ir, mēs atlasām visas rindas, kas sākas ar label=prefix un saņemt nepiecieÅ”amo timeseries_ids.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Šeit ir piemērs tam, kā tas izskatītos Go. Mums ir apgriezts indekss. Tas ir LevelDB.

Funkcija ir tāda pati kā naivai ievieÅ”anai. Tā gandrÄ«z rindu pēc rindas atkārto naivo ievieÅ”anu. VienÄ«gais ir tas, ka tā vietā, lai pievērstos map mēs piekļūstam apgrieztajam indeksam. Mēs iegÅ«stam visas vērtÄ«bas pirmajai label=value. Tad mēs ejam cauri visiem atlikuÅ”ajiem pāriem label=value un iegÅ«stiet tām atbilstoŔās metrikas ID kopas. Tad atrodam krustojumu.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Å Ä·iet, ka viss ir kārtÄ«bā, taču Å”im risinājumam ir trÅ«kumi. VictoriaMetrics sākotnēji ieviesa apgrieztu indeksu, pamatojoties uz LevelDB. Bet galu galā man nācās no tā atteikties.

Kāpēc? Tā kā LevelDB ir lēnāka nekā naivā ievieÅ”ana. Naivā ievieÅ”anā, ņemot vērā doto atslēgu, mēs nekavējoties izgÅ«stam visu Ŕķēli metricIDs. Å Ä« ir ļoti ātra darbÄ«ba ā€“ visa Ŕķēle ir gatava lietoÅ”anai.

LevelDB katru reizi, kad tiek izsaukta funkcija GetValues jums ir jāiet cauri visām rindiņām, kas sākas ar label=value. Un iegÅ«stiet katras rindas vērtÄ«bu timeseries_ids. No Ŕāda timeseries_ids savāc Ŕķēli no tiem timeseries_ids. AcÄ«mredzot tas ir daudz lēnāk nekā vienkārÅ”a piekļuve parastai kartei, izmantojot taustiņu.

Otrs trÅ«kums ir tas, ka LevelDB ir rakstÄ«ts C valodā. C funkciju izsaukÅ”ana no Go nav ļoti ātra. Tas aizņem simtiem nanosekunžu. Tas nav Ä«paÅ”i ātri, jo, salÄ«dzinot ar parastu go rakstÄ«tu funkciju izsaukumu, kas aizņem 1-5 nanosekundes, veiktspējas atŔķirÄ«ba ir desmitiem reižu. Uzņēmumam VictoriaMetrics tas bija liktenÄ«gs trÅ«kums :)

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Tāpēc es uzrakstÄ«ju savu apgrieztā indeksa ievieÅ”anu. Un viņŔ viņai piezvanÄ«ja apvienot.

Mergeset pamatā ir MergeTree datu struktÅ«ra. Å Ä« datu struktÅ«ra ir aizgÅ«ta no ClickHouse. AcÄ«mredzot Mergeset ir jāoptimizē ātrai meklÄ“Å”anai timeseries_ids saskaņā ar doto atslēgu. Mergeset ir pilnÄ«bā uzrakstÄ«ts Go. Tu vari redzēt VictoriaMetrics avoti vietnē GitHub. Mergeset ievieÅ”ana atrodas mapē /lib/mergeset. JÅ«s varat mēģināt noskaidrot, kas tur notiek.

Mergeset API ir ļoti līdzīga LevelDB un RocksDB. Tas ir, tas ļauj ātri saglabāt jaunus ierakstus un ātri atlasīt ierakstus pēc noteiktā prefiksa.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Par mergeset trÅ«kumiem mēs runāsim vēlāk. Tagad parunāsim par to, kādas problēmas radās ar VictoriaMetrics ražoÅ”anā, ievieÅ”ot apgrieztu indeksu.

Kāpēc tie radās?

Pirmais iemesls ir augstais atteikÅ”anās lÄ«menis. Tulkojumā krievu valodā tā ir bieža laika rindas maiņa. Tas ir tad, kad beidzas laikrindas un sākas jauna sērija vai sākas daudzas jaunas laikrindas. Un tas notiek bieži.

Otrs iemesls ir lielais laikrindu skaits. Sākumā, kad monitorings kļuva arvien populārāks, laikrindu skaits bija neliels. Piemēram, katram datoram ir jāuzrauga CPU, atmiņas, tīkla un diska noslodze. 4 laikrindas uz datoru. Pieņemsim, ka jums ir 100 datori un 400 laikrindas. Tas ir ļoti maz.

Laika gaitā cilvēki saprata, ka viņi var izmērÄ«t detalizētāku informāciju. Piemēram, mēra slodzi nevis visam procesoram, bet gan atseviŔķi katram procesora kodolam. Ja jums ir 40 procesora kodoli, jums ir 40 reizes vairāk laikrindu, lai izmērÄ«tu procesora slodzi.

Bet tas vēl nav viss. Katram procesora kodolam var bÅ«t vairāki stāvokļi, piemēram, dÄ«kstāve, kad tas ir dÄ«kstāvē. Un arÄ« strādāt lietotāju telpā, strādāt kodola telpā un citos stāvokļos. Un katru Ŕādu stāvokli var arÄ« izmērÄ«t kā atseviŔķu laikrindu. Tas papildus palielina rindu skaitu 7-8 reizes.

No vienas metrikas mēs saņēmām 40 x 8 = 320 metriku tikai vienam datoram. Reizinot ar 100, mēs iegÅ«stam 32 000, nevis 400.

Tad nāca Kubernetes. Un tas kļuva sliktāks, jo Kubernetes var mitināt daudz dažādu pakalpojumu. Katrs pakalpojums Kubernetes sastāv no daudzām pākstīm. Un tas viss ir jāuzrauga. Turklāt mēs pastāvīgi izvietojam jaunas jūsu pakalpojumu versijas. Katrai jaunai versijai ir jāizveido jaunas laikrindas. Rezultātā laikrindu skaits pieaug eksponenciāli, un mēs saskaramies ar liela skaita laikrindu problēmu, ko sauc par augstu kardinalitāti. VictoriaMetrics ar to tiek galā veiksmīgi, salīdzinot ar citām laikrindu datu bāzēm.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Apskatīsim tuvāk augsto atteikŔanās līmeni. Kas izraisa augstu ražoŔanas pārtraukŔanas līmeni? Jo dažas etiķeŔu un tagu nozīmes pastāvīgi mainās.

Piemēram, ņemam Kubernetes, kurai ir koncepcija deployment, t.i., kad tiek izlaista jauna lietojumprogrammas versija. Kādu iemeslu dēļ Kubernetes izstrādātāji nolēma etiÄ·etei pievienot izvietoÅ”anas ID.

Pie kā tas noveda? Turklāt ar katru jaunu izvietoÅ”anu visas vecās laikrindas tiek pārtrauktas, un to vietā sākas jaunas laikrindas ar jaunu etiÄ·etes vērtÄ«bu. deployment_id. Šādu rindu var bÅ«t simtiem tÅ«kstoÅ”u un pat miljonu.

SvarÄ«gi Å”ajā visā ir tas, ka kopējais laikrindu skaits pieaug, bet to laikrindu skaits, kuras paÅ”laik ir aktÄ«vas un saņem datus, paliek nemainÄ«gs. Å o stāvokli sauc par augstu atteikÅ”anās ātrumu.

Galvenā problēma, kas saistÄ«ta ar lielu novirzÄ«Å”anas ātrumu, ir nodroÅ”ināt nemainÄ«gu meklÄ“Å”anas ātrumu visām laikrindām noteiktai etiÄ·eÅ”u kopai noteiktā laika intervālā. Parasti tas ir pēdējās stundas vai pēdējās dienas laika intervāls.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Kā atrisināt Å”o problēmu? Å eit ir pirmā iespēja. Tas ir paredzēts, lai laika gaitā sadalÄ«tu apgriezto indeksu neatkarÄ«gās daļās. Tas ir, paiet kāds laika intervāls, mēs pabeidzam darbu ar paÅ”reizējo apgriezto indeksu. Un izveidojiet jaunu apgrieztu indeksu. Paiet cits laika intervāls, mēs veidojam vēl vienu un vēl vienu.

Un, veicot izlasi no Å”iem apgrieztajiem indeksiem, mēs atrodam apgriezto indeksu kopu, kas ietilpst dotajā intervālā. Un attiecÄ«gi mēs no turienes izvēlamies laikrindas ID.

Tas ietaupa resursus, jo mums nav jāmeklē daļas, kas neietilpst dotajā intervālā. Tas ir, parasti, ja atlasām datus par pēdējo stundu, tad iepriekŔējos laika intervālos mēs izlaižam pieprasÄ«jumus.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Ir vēl viena iespēja atrisināt Å”o problēmu. Tas ir paredzēts, lai katrai dienai saglabātu atseviŔķu tajā dienā notikuÅ”o laikrindu ID sarakstu.

Å Ä« risinājuma priekÅ”rocÄ«ba salÄ«dzinājumā ar iepriekŔējo risinājumu ir tāda, ka mēs nedublējam laikrindu informāciju, kas laika gaitā nepazÅ«d. Viņi pastāvÄ«gi atrodas un nemainās.

TrÅ«kums ir tāds, ka Ŕādu risinājumu ir grÅ«tāk ieviest un grÅ«tāk atkļūdot. Un VictoriaMetrics izvēlējās Å”o risinājumu. Tā tas notika vēsturiski. Å is risinājums arÄ« darbojas labi, salÄ«dzinot ar iepriekŔējo. Jo Å”is risinājums netika ieviests tāpēc, ka ir nepiecieÅ”ams dublēt datus katrā nodalÄ«jumā laikrindām, kuras nemainās, t.i., kas laika gaitā nepazÅ«d. VictoriaMetrics galvenokārt tika optimizēts diska vietas patēriņam, un iepriekŔējā ievieÅ”ana pasliktināja diska vietas patēriņu. Bet Ŕī ievieÅ”ana ir labāk piemērota diska vietas patēriņa samazināŔanai, tāpēc tā tika izvēlēta.

Man bija jācÄ«nās ar viņu. Cīņa bija tāda, ka Å”ajā Ä«stenoÅ”anā jums joprojām ir jāizvēlas daudz lielāks skaits timeseries_ids datiem nekā tad, ja apgrieztais indekss ir sadalÄ«ts laikā.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Kā mēs atrisinājām Å”o problēmu? Mēs to atrisinājām oriÄ£inālā veidā ā€“ katrā apgrieztā indeksa ierakstā saglabājot vairākus laikrindu identifikatorus viena identifikatora vietā. Tas ir, mums ir atslēga label=value, kas notiek katrā laika rindā. Un tagad mēs saglabājam vairākus timeseries_ids vienā ierakstā.

Å eit ir piemērs. IepriekÅ” mums bija N ieraksti, bet tagad mums ir viens ieraksts, kura prefikss ir tāds pats kā visiem pārējiem. IepriekŔējā ieraksta vērtÄ«bā ir ietverti visi laikrindu ID.

Tas ļāva palielināt Ŕāda apgrieztā indeksa skenÄ“Å”anas ātrumu lÄ«dz 10 reizēm. Un tas ļāva mums samazināt atmiņas patēriņu keÅ”atmiņai, jo tagad mēs saglabājam virkni label=value tikai vienu reizi keÅ”atmiņā kopā N reizes. Un Ŕī rinda var bÅ«t liela, ja savos tagos un etiÄ·etēs glabājat garas rindas, kuras Kubernetes labprāt tur iespiež.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Vēl viena iespēja, lai paātrinātu meklÄ“Å”anu apgrieztā rādÄ«tājā, ir sadalÄ«Å”ana. Vairāku apgrieztu indeksu izveidoÅ”ana viena vietā un datu sadalÄ«Å”ana starp tiem pēc atslēgas. Å is ir komplekts key=value tvaiks. Tas ir, mēs iegÅ«stam vairākus neatkarÄ«gus apgrieztus indeksus, kurus varam veikt paralēli vairākos procesoros. IepriekŔējās ievieÅ”anas ļāva darboties tikai viena procesora režīmā, t.i., skenēt datus tikai vienā kodolā. Å is risinājums ļauj skenēt datus vairākos kodolos vienlaikus, kā tas patÄ«k ClickHouse. Tas ir tas, ko mēs plānojam Ä«stenot.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Tagad atgriezÄ«simies pie mÅ«su aitām ā€“ pie krustojuma funkcijas timeseries_ids. Apsvērsim, kādi varianti var bÅ«t. Å Ä« funkcija ļauj atrast timeseries_ids noteiktam komplektam label=value.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Pirmā iespēja ir naiva Ä«stenoÅ”ana. Divas ligzdotas cilpas. Å eit mēs iegÅ«stam funkcijas ievadi intersectInts divas Ŕķēles - a Šø b. Izejā tai vajadzētu atgriezties pie mums Å”o Ŕķēlumu krustpunktā.

Naiva Ä«stenoÅ”ana izskatās Ŕādi. Mēs atkārtojam visas vērtÄ«bas no Ŕķēluma a, Å”ajā cilpā mēs ejam cauri visām Ŕķēluma vērtÄ«bām b. Un mēs tos salÄ«dzinām. Ja tie sakrÄ«t, tad esam atraduÅ”i krustojumu. Un saglabājiet to result.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Kādi ir trÅ«kumi? Kvadrātiskā sarežģītÄ«ba ir tās galvenais trÅ«kums. Piemēram, ja jÅ«su izmēri ir Ŕķēle a Šø b vienu miljonu vienlaikus, tad Ŕī funkcija nekad neatgriezÄ«s jums atbildi. Jo tam bÅ«s jāveic triljons iterāciju, kas ir daudz pat mÅ«sdienu datoriem.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Otrā ievieÅ”ana ir balstÄ«ta uz karti. Mēs veidojam karti. Mēs ievietojām visas vērtÄ«bas no Ŕķēles Å”ajā kartē a. Tad mēs ejam cauri Ŕķēlei atseviŔķā cilpā b. Un mēs pārbaudām, vai Ŕī vērtÄ«ba ir no Ŕķēles b kartē. Ja tas pastāv, pievienojiet to rezultātam.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Kādi ir ieguvumi? PriekÅ”rocÄ«ba ir tāda, ka ir tikai lineāra sarežģītÄ«ba. Tas nozÄ«mē, ka lielākām ŔķēlÄ«tēm funkcija tiks izpildÄ«ta daudz ātrāk. Miljona lieluma Ŕķēlei Ŕī funkcija tiks izpildÄ«ta 2 miljonos iterāciju, pretstatā triljoniem iepriekŔējās funkcijas iterāciju.

NegatÄ«vie ir tas, ka Å”ai funkcijai ir nepiecieÅ”ams vairāk atmiņas, lai izveidotu Å”o karti.

Otrs trÅ«kums ir lielas jaukÅ”anas izmaksas. Å is trÅ«kums nav Ä«paÅ”i acÄ«mredzams. Un mums tas arÄ« nebija Ä«paÅ”i acÄ«mredzami, tāpēc sākumā VictoriaMetrics krustojuma ievieÅ”ana notika ar kartes palÄ«dzÄ«bu. Bet tad profilÄ“Å”ana parādÄ«ja, ka galvenā procesora laiks tiek pavadÄ«ts, rakstot uz karti un pārbaudot, vai Å”ajā kartē ir kāda vērtÄ«ba.

Kāpēc Å”ajās vietās tiek tērēts CPU laiks? Tā kā Go Å”ajās rindās veic jaukÅ”anas darbÄ«bu. Tas nozÄ«mē, ka tas aprēķina atslēgas jaucējvērtÄ«bu, lai pēc tam piekļūtu tai noteiktā indeksā HashMap. JaukÅ”anas aprēķina darbÄ«ba tiek pabeigta desmitos nanosekundēs. VictoriaMetrics tas ir lēns.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Es nolēmu ieviest bitkopu, kas optimizēta Ä«paÅ”i Å”im gadÄ«jumam. Šādi tagad izskatās divu Ŕķēlumu krustpunkts. Å eit mēs izveidojam bitkopu. Mēs tam pievienojam elementus no pirmās Ŕķēles. Pēc tam mēs pārbaudām Å”o elementu klātbÅ«tni otrajā Ŕķēlē. Un pievienojiet tos rezultātam. Tas ir, tas gandrÄ«z neatŔķiras no iepriekŔējā piemēra. VienÄ«gais Å”eit ir tas, ka mēs aizstājām piekļuvi kartei ar pielāgotām funkcijām add Šø has.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

No pirmā acu uzmetiena Ŕķiet, ka Å”im vajadzētu darboties lēnāk, ja iepriekÅ” tur tika izmantota standarta karte, un tad tiek izsauktas vēl kādas funkcijas, bet profilÄ“Å”ana parāda, ka Ŕī lieta darbojas 10 reizes ātrāk nekā standarta karte VictoriaMetrics gadÄ«jumā.

Turklāt tas izmanto daudz mazāk atmiņas, salÄ«dzinot ar kartes ievieÅ”anu. Jo mēs Å”eit glabājam bitus, nevis astoņu baitu vērtÄ«bas.

Šīs ievieŔanas trūkums ir tāds, ka tas nav tik acīmredzams, nav triviāls.

Vēl viens trÅ«kums, ko daudzi var nepamanÄ«t, ir tas, ka Ŕī ievieÅ”ana dažos gadÄ«jumos var nedarboties labi. Tas ir, tas ir optimizēts konkrētam gadÄ«jumam, Å”im VictoriaMetrics laika rindu ID krustoÅ”anās gadÄ«jumam. Tas nenozÄ«mē, ka tas ir piemērots visiem gadÄ«jumiem. Ja tas tiek izmantots nepareizi, mēs neiegÅ«sim veiktspējas pieaugumu, bet gan kļūdu, kurā pietrÅ«ks atmiņa, un veiktspējas palēnināŔanos.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Apsvērsim Ŕīs struktÅ«ras ievieÅ”anu. Ja vēlaties meklēt, tas atrodas VictoriaMetrics avotos, mapē lib/uint64set. Tas ir optimizēts Ä«paÅ”i VictoriaMetrics korpusam, kur timeseries_id ir 64 bitu vērtÄ«ba, kur pirmie 32 biti pamatā ir nemainÄ«gi un mainās tikai pēdējie 32 biti.

Šī datu struktūra netiek saglabāta diskā, tā darbojas tikai atmiņā.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Å eit ir tā API. Tas nav Ä«paÅ”i sarežģīti. API ir Ä«paÅ”i pielāgota konkrētam VictoriaMetrics izmantoÅ”anas piemēram. Tas ir, Å”eit nav nevajadzÄ«gu funkciju. Å eit ir funkcijas, kuras Ä«paÅ”i izmanto VictoriaMetrics.

Ir funkcijas add, kas pievieno jaunas vērtÄ«bas. Ir funkcija has, kas pārbauda jaunas vērtÄ«bas. Un ir funkcija del, kas noņem vērtÄ«bas. Ir palÄ«gfunkcija len, kas atgriež komplekta izmēru. Funkcija clone klonē daudz. Un funkcija appendto pārvērÅ” Å”o kopu par Ŕķēli timeseries_ids.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Šādi izskatās Ŕīs datu struktūras ievieŔana. komplektā ir divi elementi:

  • ItemsCount ir palÄ«glauks, lai ātri atgrieztu kopas elementu skaitu. Varētu iztikt arÄ« bez Ŕī palÄ«glauka, taču tas Å”eit bija jāpievieno, jo VictoriaMetrics savos algoritmos bieži vaicā bitkopas garumu.

  • Otrais lauks ir buckets. Å Ä« ir struktÅ«ras daļa bucket32. Katra struktÅ«ra uzglabā hi lauks. Tie ir augŔējie 32 biti. Un divas Ŕķēles - b16his Šø buckets no bucket16 struktÅ«ras.

Å eit tiek glabāti 16 bitu struktÅ«ras otrās daļas 64 augŔējie biti. Un Å”eit bitkopas tiek saglabātas katra baita apakŔējiem 16 bitiem.

Bucket64 sastāv no masÄ«va uint64. Garumu aprēķina, izmantojot Ŕīs konstantes. Vienā bucket16 maksimāli var uzglabāt 2^16=65536 mazliet. Ja jÅ«s to dalāt ar 8, tas ir 8 kilobaiti. Ja jÅ«s vēlreiz dalāt ar 8, tas ir 1000 uint64 nozÄ«mē. Tas ir Bucket16 ā€“ Ŕī ir mÅ«su 8 kilobaitu struktÅ«ra.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

ApskatÄ«sim, kā tiek realizēta viena no Ŕīs struktÅ«ras metodēm jaunas vērtÄ«bas pievienoÅ”anai.

Viss sākas ar uint64 nozÄ«mes. Mēs aprēķinām augŔējos 32 bitus, mēs aprēķinām apakŔējos 32 bitus. Ejam cauri visam buckets. Mēs salÄ«dzinām labākos 32 bitus katrā segmentā ar pievienoto vērtÄ«bu. Un, ja tie sakrÄ«t, mēs izsaucam funkciju add struktÅ«rā b32 buckets. Un pievienojiet tur zemākos 32 bitus. Un ja tas atgrieztos true, tad tas nozÄ«mē, ka mēs tur pievienojām Ŕādu vērtÄ«bu un mums tādas vērtÄ«bas nebija. Ja tas atgriežas false, tad tāda nozÄ«me jau pastāvēja. Tad mēs palielinām elementu skaitu struktÅ«rā.

Ja neesam atraduÅ”i vajadzÄ«go bucket ar nepiecieÅ”amo hi-value, tad mēs izsaucam funkciju addAlloc, kas radÄ«s jaunu bucket, pievienojot to kausa struktÅ«rai.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Tā ir funkcijas Ä«stenoÅ”ana b32.add. Tas ir lÄ«dzÄ«gs iepriekŔējai ievieÅ”anai. Mēs aprēķinām visnozÄ«mÄ«gākos 16 bitus, vismazāk nozÄ«mÄ«gos 16 bitus.

Tad mēs ejam cauri visiem augŔējiem 16 bitiem. Mēs atrodam sērkociņus. Un, ja ir atbilstÄ«ba, mēs izsaucam pievienoÅ”anas metodi, ko mēs apsvērsim nākamajā lapā bucket16.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Un Å”eit ir zemākais lÄ«menis, kuru vajadzētu maksimāli optimizēt. Mēs aprēķinām par uint64 id vērtÄ«ba slice bitā un arÄ« bitmask. Å Ä« ir maska ā€‹ā€‹noteiktai 64 bitu vērtÄ«bai, ko var izmantot, lai pārbaudÄ«tu Ŕī bita klātbÅ«tni vai iestatÄ«tu to. Mēs pārbaudām, vai Å”is bits ir iestatÄ«ts, iestatām to un atgriežam klātbÅ«tni. Å Ä« ir mÅ«su ievieÅ”ana, kas ļāva mums paātrināt laika rindu krustojoÅ”o ID darbÄ«bu 10 reizes, salÄ«dzinot ar parastajām kartēm.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Papildus Å”ai optimizācijai VictoriaMetrics piedāvā daudzas citas optimizācijas. Lielākā daļa Å”o optimizāciju tika pievienotas iemesla dēļ, bet pēc koda profilÄ“Å”anas ražoÅ”anā.

Å is ir galvenais optimizācijas noteikums ā€” nepievienojiet optimizāciju, pieņemot, ka Å”eit bÅ«s saÅ”aurinājums, jo var izrādÄ«ties, ka tā nebÅ«s. Optimizācija parasti pasliktina koda kvalitāti. Tāpēc optimizēt ir vērts tikai pēc profilÄ“Å”anas un vēlams ražoÅ”anā, lai tie bÅ«tu reāli dati. Ja kādu interesē, varat apskatÄ«t VictoriaMetrics avota kodu un izpētÄ«t citas tur esoŔās optimizācijas.

Veiciet optimizāciju pakalpojumā VictoriaMetrics. Aleksandrs Vaļalkins

Man ir jautājums par bitset. Ä»oti lÄ«dzÄ«gs C++ vektora bool ievieÅ”anai, optimizēta bitkopa. Vai ievieÅ”anu pārņēmāt no turienes?

Nē, ne no turienes. IevieÅ”ot Å”o bitkopu, es vadÄ«jos pēc zināŔanām par Å”o ids laikrindu struktÅ«ru, kuras tiek izmantotas VictoriaMetrics. Un to struktÅ«ra ir tāda, ka augŔējie 32 biti bÅ«tÄ«bā ir nemainÄ«gi. ApakŔējie 32 biti var tikt mainÄ«ti. Jo zemāks uzgalis, jo biežāk tas var mainÄ«ties. Tāpēc Ŕī ievieÅ”ana ir Ä«paÅ”i optimizēta Å”ai datu struktÅ«rai. C++ ievieÅ”ana, cik man zināms, ir optimizēta vispārējam gadÄ«jumam. Ja optimizējat vispārējam gadÄ«jumam, tas nozÄ«mē, ka konkrētajam gadÄ«jumam tas nebÅ«s optimālākais.

Iesaku noskatÄ«ties arÄ« Alekseja Milovida reportāžu. Apmēram pirms mēneÅ”a viņŔ runāja par ClickHouse optimizāciju konkrētām specializācijām. ViņŔ tikai saka, ka vispārÄ«gā gadÄ«jumā C++ vai kāda cita implementācija ir pielāgota tā, lai tā vidēji labi darbotos slimnÄ«cā. Tas var darboties sliktāk nekā zināŔanām specifiska ievieÅ”ana, piemēram, mÅ«su, kur mēs zinām, ka galvenie 32 biti lielākoties ir nemainÄ«gi.

Man ir otrs jautājums. Kāda ir būtiska atŔķirība no InfluxDB?

Ir daudz bÅ«tisku atŔķirÄ«bu. Runājot par veiktspēju un atmiņas patēriņu, InfluxDB testos parāda 10 reizes lielāku atmiņas patēriņu augstas kardinalitātes laikrindām, ja jums to ir daudz, piemēram, miljoni. Piemēram, VictoriaMetrics patērē 1 GB uz miljonu aktÄ«vo rindu, bet InfluxDB patērē 10 GB. Un tā ir liela atŔķirÄ«ba.

Otra bÅ«tiskā atŔķirÄ«ba ir tā, ka InfluxDB ir dÄ«vainas vaicājumu valodas - Flux un InfluxQL. Tie nav Ä«paÅ”i ērti darbam ar laika rindām, salÄ«dzinot ar PromQL, ko atbalsta VictoriaMetrics. PromQL ir Prometheus vaicājumu valoda.

Un vēl viena atŔķirÄ«ba ir tā, ka InfluxDB ir nedaudz dÄ«vains datu modelis, kur katrā rindā var saglabāt vairākus laukus ar atŔķirÄ«gu tagu komplektu. Å Ä«s rindas tālāk ir sadalÄ«tas dažādās tabulās. Å Ä«s papildu komplikācijas sarežģī turpmāko darbu ar Å”o datubāzi. GrÅ«ti atbalstÄ«t un saprast.

VictoriaMetrics viss ir daudz vienkārŔāk. Tur katra laikrinda ir atslēgas vērtÄ«ba. VērtÄ«ba ir punktu kopa - (timestamp, value), un galvenais ir komplekts label=value. Nav atdalÄ«Å”anas starp laukiem un mērÄ«jumiem. Tas ļauj atlasÄ«t jebkurus datus un pēc tam apvienot, pievienot, atņemt, reizināt, dalÄ«t, atŔķirÄ«bā no InfluxDB, kur, cik man zināms, aprēķini starp dažādām rindām joprojām nav ieviesti. Pat ja tie ir ieviesti, tas ir grÅ«ti, jums ir jāraksta daudz koda.

Man ir precizējoÅ”s jautājums. Vai es pareizi sapratu, ka ir kaut kāda problēma, par kuru jÅ«s runājāt, ka Å”is apgrieztais indekss neiederas atmiņā, tāpēc tur ir nodalÄ«jums?

Pirmkārt, es parādÄ«ju naivu apgrieztā indeksa ievieÅ”anu standarta Go kartē. Å Ä« ievieÅ”ana nav piemērota datu bāzēm, jo ā€‹ā€‹Å”is apgrieztais indekss netiek saglabāts diskā, un datu bāze ir jāsaglabā diskā, lai Å”ie dati bÅ«tu pieejami pēc restartÄ“Å”anas. Å ajā ievieÅ”anā, restartējot lietojumprogrammu, jÅ«su apgrieztais indekss pazudÄ«s. Un jÅ«s zaudēsit piekļuvi visiem datiem, jo ā€‹ā€‹nevarēsit tos atrast.

Sveiki! Paldies par ziņojumu! Mani sauc Pāvels. Es esmu no Wildberries. Man jums ir daži jautājumi. Pirmais jautājums. Vai jÅ«s domājat, ka, ja jÅ«s, veidojot savas lietojumprogrammas arhitektÅ«ru, bÅ«tu izvēlējies citu principu un laika gaitā sadalÄ«jis datus, tad, iespējams, meklējot datus bÅ«tu varējis krustot, pamatojoties tikai uz to, ka vienā nodalÄ«jumā ir dati par vienu laika periodā, tas ir, vienā laika intervālā, un jums nebÅ«tu jāuztraucas par to, ka jÅ«su gabali ir izkaisÄ«ti atŔķirÄ«gi? Jautājums numur 2 - tā kā jÅ«s ievieÅ”at lÄ«dzÄ«gu algoritmu ar bitu kopu un visu pārējo, tad varbÅ«t mēģinājāt izmantot procesora instrukcijas? VarbÅ«t esat mēģinājuÅ”i Ŕādas optimizācijas?

Uz otro atbildÄ“Å”u uzreiz. Mēs vēl neesam tikuÅ”i lÄ«dz tam. Bet, ja vajadzēs, mēs tur tiksim. Un pirmais, kāds bija jautājums?

JÅ«s apspriedāt divus scenārijus. Un viņi teica, ka izvēlējās otro ar sarežģītāku ievieÅ”anu. Un viņi nevēlējās pirmo, kur dati ir sadalÄ«ti pēc laika.

Jā. Pirmajā gadÄ«jumā kopējais indeksa apjoms bÅ«tu lielāks, jo katrā nodalÄ«jumā mums bÅ«tu jāuzglabā dublēti dati par tām laikrindām, kas turpinās cauri visām Ŕīm sadaļām. Un, ja jÅ«su laikrindu maiņas ātrums ir mazs, t.i., pastāvÄ«gi tiek izmantotas vienas un tās paÅ”as rindas, tad pirmajā gadÄ«jumā mēs zaudētu daudz vairāk diska aizņemtās vietas, salÄ«dzinot ar otro gadÄ«jumu.

Un tā - jā, laika sadalÄ«Å”ana ir labs risinājums. Prometejs to izmanto. Bet Prometejam ir vēl viens trÅ«kums. Apvienojot Ŕīs datu daļas, tai ir jāsaglabā visu etiÄ·eÅ”u un laikrindu metainformācija. Tāpēc, ja tajā apvienotie datu gabali ir lieli, atmiņas patēriņŔ apvienoÅ”anas laikā ievērojami palielinās, atŔķirÄ«bā no VictoriaMetrics. Apvienojot, VictoriaMetrics vispār nepatērē atmiņu; tiek patērēti tikai daži kilobaiti neatkarÄ«gi no sapludināto datu lieluma.

Izmantotais algoritms izmanto atmiņu. Tas iezÄ«mē laikrindas tagus, kas satur vērtÄ«bas. Un Ŕādā veidā jÅ«s pārbaudāt klātbÅ«tni pārÄ« vienā datu masÄ«vā un citā. Un jÅ«s saprotat, vai krustojums ir noticis vai nē. Parasti datu bāzēs tiek ieviesti kursori un iteratori, kas saglabā to paÅ”reizējo saturu un pārlaiž sakārtotos datus Å”o darbÄ«bu vienkārŔās sarežģītÄ«bas dēļ.

Kāpēc mēs neizmantojam kursorus datu ŔķērsoÅ”anai?

Jā.

Mēs glabājam sakārtotās rindas LevelDB vai mergeset. Mēs varam pārvietot kursoru un atrast krustojumu. Kāpēc mēs to neizmantojam? Jo tas ir lēns. Jo kursori nozÄ«mē, ka katrai rindai ir jāizsauc funkcija. Funkcijas izsaukums ir 5 nanosekundes. Un, ja jums ir 100 000 000 lÄ«niju, tad izrādās, ka mēs pavadām pussekundi tikai funkcijas izsaukÅ”anai.

Ir tāda lieta, jā. Un mans pēdējais jautājums. Jautājums var izklausÄ«ties nedaudz dÄ«vaini. Kāpēc datu saņemÅ”anas brÄ«dÄ« nav iespējams nolasÄ«t visus nepiecieÅ”amos apkopojumus un saglabāt tos vajadzÄ«gajā formā? Kāpēc ietaupÄ«t milzÄ«gus apjomus dažās sistēmās, piemēram, VictoriaMetrics, ClickHouse utt., un pēc tam tērēt tām daudz laika?

Es sniegÅ”u piemēru, lai tas bÅ«tu skaidrāks. Teiksim, kā darbojas mazs rotaļlietas spidometrs? Tas reÄ£istrē jÅ«su nobraukto attālumu, visu laiku pievienojot to vienai vērtÄ«bai, bet otrajā - laikam. Un sadala. Un iegÅ«st vidējo ātrumu. JÅ«s varat darÄ«t apmēram to paÅ”u. Saskaitiet visus nepiecieÅ”amos faktus.

Labi, es saprotu jautājumu. JÅ«su piemēram ir sava vieta. Ja zināt, kādi agregāti jums nepiecieÅ”ami, Ŕī ir labākā ievieÅ”ana. Bet problēma ir tā, ka cilvēki saglabā Å”os rādÄ«tājus, dažus datus pakalpojumā ClickHouse, un viņi vēl nezina, kā tos apkopos un filtrēs nākotnē, tāpēc viņiem ir jāsaglabā visi neapstrādātie dati. Bet, ja zināt, ka kaut kas ir jāaprēķina vidēji, tad kāpēc gan to nerēķināt, nevis glabāt tur virkni neapstrādātu vērtÄ«bu? Bet tas ir tikai tad, ja jÅ«s precÄ«zi zināt, kas jums nepiecieÅ”ams.

Starp citu, datu bāzes laikrindu glabāŔanai atbalsta agregātu skaitÄ«Å”anu. Piemēram, Prometheus atbalsta ierakstÄ«Å”anas noteikumi. Tas ir, to var izdarÄ«t, ja zināt, kādas vienÄ«bas jums bÅ«s vajadzÄ«gas. VictoriaMetrics to vēl nav, bet parasti pirms tā ir Prometheus, kurā to var izdarÄ«t pārkodÄ“Å”anas noteikumos.

Piemēram, manā iepriekŔējā darbā man vajadzēja saskaitÄ«t notikumu skaitu bÄ«dāmajā logā pēdējās stundas laikā. Problēma ir tāda, ka man bija jāizveido pielāgota ievieÅ”ana Go, t.i., pakalpojums Ŕīs lietas skaitÄ«Å”anai. Å is pakalpojums galu galā nebija triviāls, jo to ir grÅ«ti aprēķināt. IevieÅ”ana var bÅ«t vienkārÅ”a, ja jums ir jāsaskaita daži apkopojumi noteiktos laika intervālos. Ja vēlaties skaitÄ«t notikumus bÄ«dāmā logā, tad tas nav tik vienkārÅ”i, kā Ŕķiet. Es domāju, ka tas vēl nav ieviests ClickHouse vai laikrindu datubāzēs, jo to ir grÅ«ti ieviest.

Un vēl viens jautājums. Mēs tikai runājām par vidējo rādÄ«tāju, un es atcerējos, ka kādreiz bija tāda lieta kā Graphite ar oglekļa aizmuguri. Un viņŔ prata retināt vecos datus, tas ir, atstāt vienu punktu minÅ«tē, vienu punktu stundā utt. Principā tas ir diezgan ērti, ja mums ir nepiecieÅ”ami neapstrādāti dati, nosacÄ«ti runājot, par mēnesi, un viss pārējais var tikt atŔķaidÄ«tam. Bet Prometheus un VictoriaMetrics neatbalsta Å”o funkcionalitāti. Vai ir plānots to atbalstÄ«t? Ja nē, kāpēc ne?

Paldies par jautājumu. MÅ«su lietotāji periodiski uzdod Å”o jautājumu. Viņi jautā, kad mēs pievienosim atbalstu samazinājumam. Å eit ir vairākas problēmas. Pirmkārt, katrs lietotājs to saprot downsampling kaut kas cits: kāds vēlas iegÅ«t jebkuru patvaļīgu punktu noteiktā intervālā, kāds vēlas maksimālās, minimālās, vidējās vērtÄ«bas. Ja daudzas sistēmas ieraksta datus jÅ«su datu bāzē, jÅ«s tos nevarat apvienot. Var gadÄ«ties, ka katrai sistēmai nepiecieÅ”ama atŔķirÄ«ga retināŔana. Un to ir grÅ«ti Ä«stenot.

Un otrā lieta ir tāda, ka VictoriaMetrics, tāpat kā ClickHouse, ir optimizēts darbam ar lieliem neapstrādātu datu apjomiem, tāpēc tas var izvilkt miljardu rindu mazāk nekā sekundē, ja jÅ«su sistēmā ir daudz kodolu. Laika rindu punktu skenÄ“Å”ana programmā VictoriaMetrics ā€“ 50 000 000 punkti sekundē uz vienu kodolu. Un Ŕī veiktspēja tiek pielāgota esoÅ”ajiem kodoliem. Tas ir, ja jums ir, piemēram, 20 kodoli, jÅ«s skenēsit miljardu punktu sekundē. Un Ŕī VictoriaMetrics un ClickHouse Ä«paŔība samazina vajadzÄ«bu pēc izlases samazināŔanas.

Vēl viena iezÄ«me ir tāda, ka VictoriaMetrics efektÄ«vi saspiež Å”os datus. SaspieÅ”ana vidēji ražoÅ”anā ir no 0,4 lÄ«dz 0,8 baitiem uz punktu. Katrs punkts ir laikspiedols + vērtÄ«ba. Un tas vidēji tiek saspiests mazāk nekā vienā baitā.

Sergejs. Man ir jautājums. Kāds ir minimālais ierakstīŔanas laika kvants?

Viena milisekunde. Nesen mums bija saruna ar citiem laikrindu datu bāzes izstrādātājiem. Viņu minimālais laika posms ir viena sekunde. Un, piemēram, grafītā tā ir arī viena sekunde. OpenTSDB tā ir arī viena sekunde. InfluxDB ir nanosekunžu precizitāte. VictoriaMetrics tā ir viena milisekunde, jo Prometejā tā ir viena milisekunde. Un VictoriaMetrics sākotnēji tika izstrādāts kā Prometheus attālā krātuve. Bet tagad tas var saglabāt datus no citām sistēmām.

Persona, ar kuru es runāju, saka, ka viņiem ir precizitāte no sekundes lÄ«dz sekundei ā€” viņiem ar to pietiek, jo tas ir atkarÄ«gs no datu veida, kas tiek glabāti laikrindu datu bāzē. Ja tie ir DevOps dati vai dati no infrastruktÅ«ras, kur tos savācat ik pēc 30 sekundēm minÅ«tē, tad pietiek ar sekundes precizitāti, neko mazāk nevajag. Un, ja jÅ«s apkopojat Å”os datus no augstas frekvences tirdzniecÄ«bas sistēmām, tad jums ir nepiecieÅ”ama nanosekundes precizitāte.

Milisekundes precizitāte programmā VictoriaMetrics ir piemērota arī DevOps gadījumam, un tā var būt piemērota lielākajai daļai gadījumu, ko minēju ziņojuma sākumā. Vienīgais, kam tas var nebūt piemērots, ir augstas frekvences tirdzniecības sistēmas.

Paldies! Un vēl jautājums. Kas ir PromQL saderība?

Pilna atpakaļejoÅ”a saderÄ«ba. VictoriaMetrics pilnÄ«bā atbalsta PromQL. Turklāt tas pievieno papildu uzlaboto funkcionalitāti PromQL, ko sauc MetricsQL. Vietnē YouTube tiek runāts par Å”o paplaÅ”ināto funkcionalitāti. Es runāju Monitoring Meetup pavasarÄ« Sanktpēterburgā.

Telegrammas kanāls VictoriaMetrics.

Aptaujā var piedalīties tikai reģistrēti lietotāji. Ielogoties, lūdzu.

Kas jums traucē pāriet uz VictoriaMetrics kā Prometheus ilgtermiņa krātuvi? (Raksti komentāros, pievienoÅ”u aptaujai))

  • 71,4%Es neizmantoju Prometheus5

  • 28,6%Nezināju par VictoriaMetrics2

Nobalsoja 7 lietotāji. 12 lietotāji atturējās.

Avots: www.habr.com

Pievieno komentāru