Ngarkoni optimizimin në një projekt Highload me ElasticSearch

Hej Habr! Unë quhem Maxim Vasiliev, punoj si analist dhe menaxher projekti në FINCH. Sot do të doja t'ju tregoja se si, duke përdorur ElasticSearch, ne mundëm të përpunonim 15 milion kërkesa në 6 minuta dhe të optimizonim ngarkesat ditore në faqen e një prej klientëve tanë. Fatkeqësisht, do të duhet të bëjmë pa emra, pasi kemi një NDA, shpresojmë që përmbajtja e artikullit të mos vuajë nga kjo. Shkojme.

Si funksionon projekti

Në backend-in tonë, ne krijojmë shërbime që sigurojnë performancën e faqeve të internetit të klientëve tanë dhe aplikacionit celular. Struktura e përgjithshme mund të shihet në diagram:

Ngarkoni optimizimin në një projekt Highload me ElasticSearch

Në procesin e punës, ne përpunojmë një numër të madh transaksionesh: blerje, pagesa, operacione me bilancet e përdoruesve, për të cilat ruajmë shumë regjistra, si dhe importojmë dhe eksportojmë këto të dhëna në sisteme të jashtme.

Ekzistojnë gjithashtu procese të kundërta kur marrim të dhëna nga klienti dhe i transferojmë ato te përdoruesi. Për më tepër, ka ende procese për të punuar me pagesat dhe programet e bonusit.

Sfondi i shkurtër

Fillimisht, ne përdorëm PostgreSQL si dyqanin e vetëm të të dhënave. Përparësitë e tij standarde për një DBMS: prania e transaksioneve, një gjuhë e zhvilluar e kampionimit të të dhënave, një gamë e gjerë mjetesh për integrim; kombinuar me performancën e mirë plotësoi nevojat tona për një kohë mjaft të gjatë.

Ne ruajtëm absolutisht të gjitha të dhënat në Postgres: nga transaksionet tek lajmet. Por numri i përdoruesve u rrit dhe bashkë me të edhe numri i kërkesave.

Për t'u kuptuar, numri vjetor i seancave në 2017 vetëm në faqen e desktopit është 131 milion. Në 2018 - 125 milion. 2019 përsëri 130 milion. Shtoni 100-200 milion të tjera nga versioni celular i faqes dhe aplikacioni celular, dhe ju do të marrë një numër të madh kërkesash.

Me rritjen e projektit, Postgres pushoi së përballuari ngarkesën, nuk kishim kohë - u shfaqën një numër i madh pyetjesh të ndryshme, për të cilat nuk mund të krijonim një numër të mjaftueshëm indeksesh.

Kuptuam se kishte nevojë për dyqane të tjera të dhënash që do të siguronin nevojat tona dhe do të largonin ngarkesën nga PostgreSQL. Elasticsearch dhe MongoDB u konsideruan si opsione të mundshme. Ky i fundit humbi në pikat e mëposhtme:

  1. Shpejtësia e ngadaltë e indeksimit ndërsa sasia e të dhënave në indekse rritet. Me Elastic, shpejtësia nuk varet nga sasia e të dhënave.
  2. Nuk ka kërkim të plotë të tekstit

Kështu që ne zgjodhëm Elastic për veten tonë dhe u përgatitëm për tranzicionin.

Kalimi në Elastic

1. Filluam kalimin nga shërbimi i kërkimit të pikës së shitjes. Klienti ynë ka gjithsej rreth 70 pika shitjeje, dhe kjo kërkon disa lloje kërkimesh në faqe dhe në aplikacion:

  • Kërkimi i tekstit sipas emrit të qytetit
  • Gjeokërkimi brenda një rrezeje të caktuar nga një pikë. Për shembull, nëse përdoruesi dëshiron të shohë se cilat pika shitje janë më afër shtëpisë së tij.
  • Kërko sipas një katrori të caktuar - përdoruesi vizaton një katror në hartë dhe të gjitha pikat në këtë rreze i tregohen atij.
  • Kërkoni sipas filtrave shtesë. Pikat e shitjes ndryshojnë nga njëra-tjetra në asortiment

Nëse flasim për organizimin, atëherë në Postgres kemi një burim të dhënash si për hartën ashtu edhe për lajmet, dhe në Elastic Snapshots janë marrë nga të dhënat origjinale. Fakti është se fillimisht Postgres nuk mund ta përballonte kërkimin me të gjitha kriteret. Jo vetëm që kishte shumë indekse, ato gjithashtu mund të mbivendosen, kështu që planifikuesi Postgres humbi dhe nuk e kuptoi se cilin indeks të përdorte.

2. Në radhë ishte rubrika e lajmeve. Publikimet shfaqen në faqe çdo ditë në mënyrë që përdoruesi të mos humbasë në rrjedhën e informacionit, të dhënat duhet të renditen përpara se të lëshohen. Kjo është ajo për të cilën kërkohet kërkimi: ju mund të kërkoni faqen sipas përputhjes së tekstit, dhe në të njëjtën kohë të lidhni filtra shtesë, pasi ato bëhen edhe përmes Elastic.

3. Më pas zhvendosëm përpunimin e transaksionit. Përdoruesit mund të blejnë një produkt të caktuar në faqe dhe të marrin pjesë në një tërheqje çmimesh. Pas blerjeve të tilla, ne përpunojmë një sasi të madhe të dhënash, veçanërisht gjatë fundjavave dhe festave. Për krahasim, nëse në ditët e zakonshme numri i blerjeve është diku midis 1,5-2 milionë, atëherë gjatë pushimeve shifra mund të arrijë në 53 milionë.

Në të njëjtën kohë, të dhënat duhet të përpunohen në kohën më të shkurtër të mundshme - përdoruesit nuk u pëlqen të presin rezultatin për disa ditë. Nuk ka asnjë mënyrë për të arritur afate të tilla përmes Postgres - ne shpesh merrnim bravë, dhe ndërsa po përpunonim të gjitha kërkesat, përdoruesit nuk mund të kontrollonin nëse morën çmime apo jo. Kjo nuk është shumë e këndshme për biznesin, kështu që ne e zhvendosëm përpunimin në Elasticsearch.

periodicitet

Tani përditësimet janë konfiguruar bazuar në ngjarje, sipas kushteve të mëposhtme:

  1. Pikat e shitjes. Sapo marrim të dhëna nga një burim i jashtëm, fillojmë menjëherë përditësimin.
  2. Lajme. Sapo ndonjë lajm redaktohet në faqe, ai dërgohet automatikisht në Elastic.

Këtu përsëri vlen të përmenden avantazhet e Elastic. Në Postgres, kur dërgoni një kërkesë, duhet të prisni derisa të përpunojë me ndershmëri të gjitha të dhënat. Ju mund të dërgoni 10 regjistrime në Elastic dhe të filloni të punoni menjëherë, pa pritur që regjistrimet të shpërndahen në të gjitha Shards. Sigurisht, disa Shard ose Replica mund të mos i shohin të dhënat menjëherë, por gjithçka do të jetë e disponueshme shumë shpejt.

Metodat e integrimit

Ka 2 mënyra për t'u integruar me Elastic:

  1. Përmes një klienti vendas mbi TCP. Drejtuesi vendas po shuhet gradualisht: nuk mbështetet më, ka një sintaksë shumë të papërshtatshme. Prandaj, ne praktikisht nuk e përdorim atë dhe përpiqemi ta braktisim plotësisht.
  2. Përmes një ndërfaqeje HTTP që mund të përdorë kërkesat JSON dhe sintaksën Lucene. I fundit është një motor teksti që përdor Elastic. Në këtë version, ne kemi mundësinë për të grumbulluar përmes kërkesave JSON mbi HTTP. Ky është opsioni që ne po përpiqemi të përdorim.

Falë ndërfaqes HTTP, ne mund të përdorim biblioteka që ofrojnë një zbatim asinkron të klientit HTTP. Ne mund të përfitojmë nga Batch dhe API-ja asinkrone, e cila rezulton në performancë të lartë, e cila ndihmoi shumë në ditët e promovimit të madh (më shumë për këtë më poshtë)

Disa numra për krahasim:

  • Ruajtja e përdoruesve të bounty Postgres në 20 tema pa grupim: 460713 regjistrime në 42 sekonda
  • Klient elastik + reaktiv për 10 fije + grumbull për 1000 elementë: 596749 regjistrime në 11 sekonda
  • Klient elastik + reaktiv për 10 fije + grumbull për 1000 elementë: 23801684 hyrje në 4 minuta

Tani ne kemi shkruar një menaxher të kërkesave HTTP që ndërton JSON si Batch/jo Batch dhe e dërgon atë nëpërmjet çdo klienti HTTP, pavarësisht nga biblioteka. Ju gjithashtu mund të zgjidhni të dërgoni kërkesat në mënyrë sinkrone ose asinkrone.

Në disa integrime, ne ende përdorim klientin zyrtar të transportit, por kjo është vetëm një çështje e rifaktorimit të radhës. Në këtë rast, një klient i personalizuar i ndërtuar mbi bazën e Spring WebClient përdoret për përpunim.

Ngarkoni optimizimin në një projekt Highload me ElasticSearch

promovim i madh

Një herë në vit, projekti pret një promovim të madh për përdoruesit - ky është i njëjti Highload, pasi në këtë kohë ne punojmë me dhjetëra miliona përdorues në të njëjtën kohë.

Zakonisht kulmet e ngarkesave ndodhin gjatë pushimeve, por ky promovim është në një nivel krejtësisht tjetër. Një vit më parë, në ditën e promovimit, kemi shitur 27 njësi mallrash. Të dhënat u përpunuan për më shumë se gjysmë ore, gjë që shkaktoi bezdi për përdoruesit. Përdoruesit morën çmime për pjesëmarrje, por u bë e qartë se procesi duhej të përshpejtohej.

Në fillim të vitit 2019, vendosëm që na duhej ElasticSearch. Për një vit të tërë organizuam përpunimin e të dhënave të marra në Elastic dhe nxjerrjen e tyre në api të aplikacionit celular dhe uebsajtit. Si rezultat, vitin e ardhshëm gjatë fushatës, ne përpunuam 15 hyrje në 131 minuta.

Meqenëse kemi shumë njerëz që duan të blejnë mallra dhe të marrin pjesë në tërheqjen e çmimeve në promovime, kjo është një masë e përkohshme. Tani po dërgojmë informacione të përditësuara në Elastic, por në të ardhmen planifikojmë të transferojmë informacionin e arkivuar për muajt e fundit në Postgres si një ruajtje të përhershme. Për të mos bllokuar indeksin Elastic, i cili gjithashtu ka kufizimet e tij.

Përfundim/Përfundime

Për momentin, ne i kemi transferuar të gjitha shërbimet që kemi dashur tek Elastic dhe kemi ndalur për momentin. Tani po ndërtojmë një indeks në Elastic në krye të ruajtjes kryesore të vazhdueshme në Postgres, i cili merr përsipër ngarkesën e përdoruesit.

Në të ardhmen, ne planifikojmë të transferojmë shërbime nëse kuptojmë që kërkesa e të dhënave bëhet shumë e larmishme dhe kërkohet për një numër të pakufizuar kolonash. Kjo nuk është më një detyrë për Postgres.

Nëse kemi nevojë për kërkim të tekstit të plotë në funksionalitet ose nëse kemi shumë kritere të ndryshme kërkimi, atëherë ne tashmë e dimë se kjo duhet të përkthehet në Elastic.

⌘⌘⌘

Faleminderit per leximin. Nëse kompania juaj përdor gjithashtu ElasticSearch dhe ka rastet e veta të zbatimit, atëherë na tregoni. Do të jetë interesante të dini se si janë të tjerët 🙂

Burimi: www.habr.com

Shto një koment