Tai straipsnis iš Python pasaulio, tačiau jis vis dar taikomas visai programavimo sričiai, nors multithreading leidžia greičiau apdoroti užklausas, tačiau yra ir lubos, žalios (mikro gijos) gijos yra sprendimas.
Kelių gijų programinės įrangos kūrimas išsprendžia daugybę problemų, ypač į tinklą orientuotoms programoms, kurioms reikalingas didelis našumas, kad greitai reaguotų į vartotojus. Deja, norint išspręsti didelio masto klausimus, nepakanka kelių gijųLygiagrečiaiseksualinės problemos.
Norint išspręsti šias problemas, reikia keisti programavimo modelius, naudoti asinchroninius įvykius ir atgalinio skambinimo mechanizmus. "Druva" sukūrėme python biblioteką "Dhaga", skirtą didelio masto problemoms spręstiLygiagrečiai, o programavimo modelis nereikalauja didelių pakeitimų.
Programinės įrangos kūrėjai gyvena vienameLygiagrečiaipasaulis. Gijos šiandien yra aukščiausios klasės piliečiai, ypač kūrimo metu, ypač kai jūsų programa atlieka intensyvias tinklo operacijas, pvz., "inSync" sistema (tinklo saugos sinchronizavimo produktas), pvz., "Druva". Multithreading padeda programavimo kodo srautas tinklo operacijoms paprastas ir tvarkingas. Kai mūsų programą reikia patobulinti ar patobulinti, ją galima patobulintiElastingumas, galime padidinti gijų skaičių.
Bet kai kalbama apie tūkstančius svarstykliųLygiagrečiaiprašymų, temų nepakanka.
Mes nustatėme, kad daugiasriegis turi šiuos trūkumus: 1. "inSync" sistemos klientas turi sukurti atsarginę kopiją daug failų serveryje per tinklo RPC skambučius. Tipiškas būdas kūrėjams pagreitinti dalykus yra naudoti gijas. Tačiau kelių gijų atnešamas našumas padidina atminties ir procesoriaus kainą; Kūrėjai turi išlaikyti pusiausvyrą tarp greičio ir gijų skaičiaus.
2. Mūsų serveriai turi tvarkyti tarp inSync sistemos ir tūkstančių klientųLygiagrečiaiRyšiai ir pranešimai. Norėdami efektyviai tvarkyti ryšius, užklausoms tvarkyti naudojame gijas. Tačiau didėjantis "inSync" sistemos klientų skaičius taip pat reiškia, kad turime ir toliau didinti gijų skaičių, o tai sunaudoja daug serverio atminties ir procesoriaus.
3. Mūsų žiniatinklio serveris turi apdoroti tūkstančius lygiagrečių HTTP užklausų. Didžioji dalis darbo atliekama tinklo lizduose, kurie priima ir siunčia duomenis ir perduoda juos į "inSync" sistemos galinę dalį. Dėl to dauguma gijų laukia tinklo operacijų. Sukelia C10K problemą, kai yra tūkstančiai sinchroninių užklausų žiniatinklio serveriui, kiekvienos užklausos gijos generavimas yra gana nekeičiamas (mastelis).
Asinchroninių karkasų apribojimai Daugelis asinchroninių sistemų, įskaitant "Twisted", "Tornado Tornado" ir "asyncore", gali padėti kūrėjams atsisakyti populiarių gijų naudojimo būdų. Šios sistemos remiasi neblokuojančiais lizdais ir atgalinio skambinimo mechanizmais (panašiais į Node.js). Jei naudosime šias sistemas tokias, kokios yra, pagrindinės mūsų "Druva" kodo dalys turės būti pertvarkytos. Tai nėra tai, ką mes norime daryti. Kodo pertvarkymas padidina kūrimo ir testavimo ciklus, todėl negalime atitikti masto reikalavimų. Atsižvelgiant į tai, kad kelios gaminio dalys turi būti masyvios, kiekvienas iš mūsų turės jas pertvarkyti – taigi reikia stengtis padvigubinti arba patrigubinti.
Kad nekeistume tiek daug kodo, turėjome atsisakyti tiesioginės esamos sistemos naudojimo. Laimei, radome naudingų įrankių.
Kadangi norime kontroliuoti kodo vykdymą tinklo I/O, mums reikia būdo, kaip padalyti giją į mikrogijas. Mes randameŽalumynai。 Jame pateikiamas nenumanomas mikrogijų planavimas, vadinamas korutinos rutina. Kitaip tariant. Tai naudinga, kai norite valdyti vykdomą kodą. Galite kurti mikrogijas pasirinktiniams tvarkaraščiams, nes galite kontroliuoti, kada žalumynai duoda pauzes. Tai puikiai tinka mums, nes leidžia visiškai kontroliuoti kodo planavimą.
"Tornado" yra paprasta, neblokuojanti žiniatinklio serverio sistema, parašyta Python kalba, skirta apdoroti tūkstančius asinchroninių užklausų. Mes naudojame pagrindinį jo komponentą IOLoop IOStream. IOLoop yra neblokuojanti lizdo I/O įvykių kilpa; Jis naudoja epoll (Linux) arba eiles (BSD ir Mac OS X), kitu atveju pasirinkite (Windows), jei jie yra. "IOStream" siūlo neblokuojančius lizdus, tokius kaip patogi pakuotė skaitymui ir rašymui. Mes deleguojame visas lizdo operacijas Tornado ir tada naudojame atgalinius skambučius, kad suaktyvintume kodo operacijas (banq pastaba: labai panašus į Node.js mechanizmą).
Tai gera pradžia, bet mums reikia daugiau. Jei mes naudojame aukščiau modulį tiesiai į mūsų kodą, daug mūsų RPC kodas turės keistis, planuojant RPC per greenlets, užtikrinant, kad greenlets neblokuoti (jei greenlets gauti užsikimšęs, jis užkimš visą siūlą ir visus kitus), tvarkyti atgalinio skambučio funkcijas iš tornado.
Mums reikia abstrakcijos, kad galėtume valdyti ir išdėstyti žalumynus, kad neužkimštume jų išoriniais skambučiais, ir ši abstrakcija gali būti masiškai keičiama už gijų ribų. Ši abstrakcija yra Dhaga, kuri leidžia programos kodo srautą užprogramuoti kaip tradicinę sinchroninę seką, tačiau vykdymas yra asinchroninis.
Dhaga (iš hindi kalbos, o tai reiškia siūlą) yra lengvo siūlo, kurį abstrahuojame, vykdymo sistema. Dhaga klasė yra kilusi iš žalumynų ir naudoja rietuvės perjungimą, kad vykdytų kelis kodo srautus vienoje operacinės sistemos gijoje. Vienos operacinės sistemos gijos vykdo kelias dhagas, naudodamos bendradarbiavimo planavimą. Kai dhaga laukia (daugiausia laukia, kol sugrįš RPC iškvietimas), ji perduoda valdymą pirminiam lygiui (t. y. jį sukūrusios OS lygio gijos vykdymo kontekstui). Tada tėvų lygis suplanuoja kitą dhaga, kad būtų pasirengęs bėgti. RPC skambutis bus perduotas tornado žiniatinklio serveriui, kad jis asinchroniškai parašytų lizdą, o tada užregistruotų atgalinį skambutį, kai jis grįš, o kai šis RPC grįš, laukianti dhaga bus įtraukta į vykdomąją eilę ir tada paimta pirminės gijos. (Banq pastaba: panašus į node.js principą)
Didelės delsos operacijoms galime naudoti "Dhaga" vietoj gijų, o vienoje gijoje naudojame 512 dhagas, kai gijų skaičius viršija pagrįstą pralaidumo ribą.
|