Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Sa kanyang ulat, sasabihin sa iyo ni Andrey Borodin kung paano nila isinasaalang-alang ang karanasan ng pag-scale ng PgBouncer kapag nagdidisenyo ng pooler ng koneksyon Odisea, habang inilunsad nila ito sa produksyon. Bilang karagdagan, tatalakayin namin kung anong mga function ng puller ang gusto naming makita sa mga bagong bersyon: mahalaga para sa amin hindi lamang upang matugunan ang aming mga pangangailangan, ngunit upang bumuo ng komunidad ng gumagamit Odyssey.

Video:

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Kamusta kayong lahat! Ang pangalan ko ay Andrew.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Sa Yandex, bumuo ako ng mga open source database. At ngayon mayroon kaming isang paksa tungkol sa mga koneksyon sa pooler na koneksyon.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Kung alam mo kung paano tumawag sa koneksyon pooler sa Russian, pagkatapos ay sabihin sa akin. Gusto ko talagang makahanap ng isang mahusay na terminong teknikal na dapat itatag sa teknikal na panitikan.

Ang paksa ay medyo kumplikado, dahil sa maraming mga database ang koneksyon pooler ay built-in at hindi mo na kailangang malaman ang tungkol dito. Siyempre, mayroong ilang mga setting sa lahat ng dako, ngunit sa Postgres hindi ito gumagana sa ganoong paraan. At kahanay (sa HighLoad++ 2019) mayroong isang ulat ni Nikolai Samokhvalov tungkol sa pag-set up ng mga query sa Postgres. At sa pagkakaintindi ko, nagpunta rito ang mga tao na perpektong na-configure ang kanilang mga query, at ito ang mga taong nahaharap sa mas bihirang mga problema sa system na may kaugnayan sa network at paggamit ng mapagkukunan. At sa ilang mga lugar maaari itong maging mahirap sa kahulugan na ang mga problema ay hindi halata.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ang Yandex ay may mga Postgres. Maraming serbisyo ng Yandex ang nakatira sa Yandex.Cloud. At mayroon kaming ilang petabytes ng data na bumubuo ng hindi bababa sa isang milyong kahilingan kada segundo sa Postgres.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

At nagbibigay kami ng isang medyo karaniwang kumpol para sa lahat ng mga serbisyo - ito ang pangunahing pangunahing node ng node, ang karaniwang dalawang replika (kasabay at asynchronous), backup, scaling ng mga kahilingan sa pagbabasa sa replica.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ang bawat cluster node ay Postgres, kung saan, bilang karagdagan sa mga Postgres at monitoring system, naka-install din ang isang connection pooler. Ginagamit ang connection pooler para sa fencing at para sa pangunahing layunin nito.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ano ang pangunahing layunin ng connection pooler?

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ang mga postgres ay gumagamit ng isang modelo ng proseso kapag nagtatrabaho sa isang database. Nangangahulugan ito na ang isang koneksyon ay isang proseso, isang Postgres backend. At sa backend na ito mayroong maraming iba't ibang mga cache, na medyo mahal upang gumawa ng iba para sa iba't ibang mga koneksyon.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Bilang karagdagan, ang Postgres code ay may array na tinatawag na procArray. Naglalaman ito ng pangunahing data tungkol sa mga koneksyon sa network. At halos lahat ng procArray processing algorithm ay may linear complexity; pinapatakbo nila ang buong hanay ng mga koneksyon sa network. Ito ay isang medyo mabilis na ikot, ngunit sa mas maraming mga papasok na koneksyon sa network ay nagiging mas mahal ang mga bagay. At kapag medyo mas mahal ang mga bagay, maaari kang magbayad ng napakataas na presyo para sa maraming koneksyon sa network.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Mayroong 3 posibleng diskarte:

  • Sa gilid ng aplikasyon.
  • Sa gilid ng database.
  • At sa pagitan, iyon ay, lahat ng uri ng kumbinasyon.

Sa kasamaang palad, ang built-in na pooler ay kasalukuyang nasa ilalim ng pag-unlad. Madalas itong ginagawa ng aming mga kaibigan sa PostgreSQL Professional. Kung kailan ito lilitaw ay mahirap hulaan. At sa katunayan, mayroon tayong dalawang solusyon na mapagpipilian ng arkitekto. Ang mga ito ay application-side pool at proxy pool.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ang application-side pool ay ang pinakamadaling paraan. At halos lahat ng mga driver ng kliyente ay nagbibigay sa iyo ng isang paraan: ipakita ang milyun-milyong iyong mga koneksyon sa code bilang ilang dosenang mga koneksyon sa database.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ang problemang lumitaw ay na sa isang tiyak na punto na gusto mong sukatin ang backend, gusto mong i-deploy ito sa maraming virtual machine.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Pagkatapos ay napagtanto mo na mayroon ka pang ilang mga availability zone, ilang mga data center. At ang client side pooling approach ay humahantong sa malalaking numero. Ang mga malalaki ay halos 10 na koneksyon. Ito ang gilid na maaaring gumana nang normal.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Kung pag-uusapan natin ang tungkol sa mga proxy pooler, kung gayon mayroong dalawang pooler na maaaring gumawa ng maraming bagay. Hindi lang sila poolers. Mga pooler sila + mas cool na functionality. Ito Pgpool ΠΈ Malutong-Proxy.

Ngunit, sa kasamaang-palad, hindi lahat ay nangangailangan ng karagdagang pag-andar na ito. At humahantong ito sa katotohanan na sinusuportahan lamang ng mga pooler ang session pooling, ibig sabihin, isang papasok na kliyente, isang papalabas na kliyente sa database.

Hindi ito masyadong angkop para sa aming mga layunin, kaya gumagamit kami ng PgBouncer, na nagpapatupad ng pagsasama-sama ng transaksyon, ibig sabihin, ang mga koneksyon sa server ay itinutugma sa mga koneksyon ng kliyente para lamang sa tagal ng transaksyon.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

At sa workload natin, totoo ito. Ngunit may ilang mga problema.Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Magsisimula ang mga problema kapag gusto mong mag-diagnose ng session, dahil lokal ang lahat ng iyong mga papasok na koneksyon. Ang bawat isa ay dumating na may isang loopback at kahit papaano ay nagiging mahirap na masubaybayan ang session.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Siyempre maaari mong gamitin ang application_name_add_host. Ito ay isang paraan sa panig ng Bouncer upang magdagdag ng IP address sa application_name. Ngunit ang application_name ay itinakda ng karagdagang koneksyon.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Sa graph na ito, kung saan ang dilaw na linya ay mga tunay na kahilingan, at kung saan ang asul na linya ay mga kahilingan na lumilipad sa database. At ang pagkakaiba na ito ay tiyak ang pag-install ng application_name, na kailangan lamang para sa pagsubaybay, ngunit hindi ito libre.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Bilang karagdagan, sa Bouncer hindi mo maaaring limitahan ang isang pool, ibig sabihin, ang bilang ng mga koneksyon sa database bawat partikular na user, bawat partikular na database.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ano ang humahantong dito? Mayroon kang naka-load na serbisyo na nakasulat sa C++ at sa isang lugar na malapit sa isang maliit na serbisyo sa isang node na hindi gumagawa ng anumang kahila-hilakbot sa database, ngunit ang driver nito ay nababaliw. Nagbubukas ito ng 20 koneksyon at lahat ng iba pa ay maghihintay. Kahit na ang iyong code ay normal.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Siyempre, nagsulat kami ng maliit na patch para sa Bouncer na nagdagdag ng setting na ito, ibig sabihin, nililimitahan ang mga kliyente sa pool.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Posibleng gawin ito sa panig ng Postgres, ibig sabihin, limitahan ang mga tungkulin sa database sa pamamagitan ng bilang ng mga koneksyon.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ngunit pagkatapos ay nawalan ka ng kakayahang maunawaan kung bakit wala kang mga koneksyon sa server. Ang PgBouncer ay hindi nagtatapon ng error sa koneksyon, palagi itong nagbabalik ng parehong impormasyon. At hindi mo maintindihan: baka nagbago ang iyong password, baka nawala lang ang database, baka may mali. Ngunit walang diagnosis. Kung hindi maitatag ang isang sesyon, hindi mo malalaman kung bakit hindi ito maitatag.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Sa isang tiyak na punto, titingnan mo ang mga graph ng application at makikita na hindi gumagana ang application.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Tumingin sa itaas at makita na ang Bouncer ay single-threaded. Ito ay isang pagbabago sa buhay ng serbisyo. Napagtanto mo na naghahanda ka sa pag-scale ng database sa loob ng isang taon at kalahati, at kailangan mong sukatin ang pooler.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Nakarating kami sa konklusyon na kailangan namin ng higit pang mga PgBouncer.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

https://lwn.net/Articles/542629/

Medyo na-patch na ang bouncer.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

At ginawa nila ito upang ang ilang mga Bouncer ay mapataas sa pamamagitan ng muling paggamit ng TCP port. At awtomatikong inililipat ng operating system ang mga papasok na koneksyon sa TCP sa pagitan nila gamit ang round-robin.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ito ay transparent sa mga kliyente, ibig sabihin, mukhang mayroon kang isang Bouncer, ngunit mayroon kang fragmentation ng mga idle na koneksyon sa pagitan ng mga tumatakbong Bouncer.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

At sa isang tiyak na sandali maaari mong mapansin na ang 3 Bouncer na ito ay kumakain ng 100% sa kanilang core ng bawat isa. Kailangan mo ng ilang Bouncer. Bakit?

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Dahil mayroon kang TLS. Mayroon kang naka-encrypt na koneksyon. At kung i-benchmark mo ang mga Postgres na may at walang TLS, makikita mo na ang bilang ng mga naitatag na koneksyon ay bumaba ng halos dalawang order ng magnitude na may naka-enable na pag-encrypt, dahil ang TLS handshake ay gumagamit ng mga mapagkukunan ng CPU.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

At sa itaas ay makakakita ka ng ilang mga cryptographic na pag-andar na isinasagawa kapag mayroong isang alon ng mga papasok na koneksyon. Dahil ang aming primary ay maaaring lumipat sa pagitan ng mga availability zone, ang isang wave ng mga papasok na koneksyon ay isang medyo karaniwang sitwasyon. Ibig sabihin, sa ilang kadahilanan ay hindi available ang lumang primary, ang buong load ay ipinadala sa isa pang data center. Sabay-sabay silang lalapit para kumustahin ang TLS.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

At ang malaking bilang ng TLS handshake ay maaaring hindi na kumusta kay Bouncer, ngunit mapipiga ang kanyang lalamunan. Dahil sa timeout, ang wave ng mga papasok na koneksyon ay maaaring maging undamped. Kung susubukan mong muli sa base nang walang exponential backoff, hindi sila babalik nang paulit-ulit sa isang magkakaugnay na alon.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Narito ang isang halimbawa ng 16 PgBouncers na naglo-load ng 16 na core sa 100%.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Dumating kami sa cascade PgBouncer. Ito ang pinakamahusay na configuration na maaaring makamit sa aming load sa Bouncer. Ang aming mga panlabas na Bouncer ay ginagamit para sa TCP handshake, at ang mga panloob na Bouncer ay ginagamit para sa tunay na pagsasama-sama, upang hindi masyadong mapira-piraso ang mga panlabas na koneksyon.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Sa pagsasaayos na ito, posible ang isang maayos na pag-restart. Maaari mong i-restart ang lahat ng 18 Bouncers na ito nang paisa-isa. Ngunit ang pagpapanatili ng gayong pagsasaayos ay medyo mahirap. Ang mga Sysadmin, DevOps, at mga taong aktwal na responsable para sa server na ito ay hindi magiging masaya sa kaayusan na ito.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Mukhang ang lahat ng aming mga pagpapabuti ay maaaring i-promote sa open source, ngunit ang Bouncer ay hindi masyadong suportado. Halimbawa, ang kakayahang magpatakbo ng ilang PgBouncer sa isang port ay ginawa noong isang buwan. Nagkaroon ng pull request sa feature na ito ilang taon na ang nakalipas.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

https://www.postgresql.org/docs/current/libpq-cancel.html

https://github.com/pgbouncer/pgbouncer/pull/79

O isa pang halimbawa. Sa Postgres, maaari mong kanselahin ang isang kahilingan na isinasagawa sa pamamagitan ng pagpapadala ng sikreto sa ibang koneksyon nang walang hindi kinakailangang pagpapatunay. Ngunit ang ilang mga kliyente ay nagpapadala lamang ng isang pag-reset ng TCP, ibig sabihin, sinisira nila ang koneksyon sa network. Ano ang gagawin ni Bouncer? Wala siyang gagawin. Patuloy nitong isasagawa ang kahilingan. Kung nakatanggap ka ng isang malaking bilang ng mga koneksyon na lumikha ng isang database na may maliliit na kahilingan, pagkatapos ay hindi sapat ang pagdiskonekta ng koneksyon mula sa Bouncer; kailangan mo ring kumpletuhin ang mga kahilingang iyon na tumatakbo sa database.

Ito ay na-patched at ang problemang ito ay hindi pa naisasama sa upstream ng Bouncer.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

At kaya kami ay dumating sa konklusyon na kailangan namin ang aming sariling koneksyon pooler, na kung saan ay binuo, patched, kung saan ang mga problema ay maaaring mabilis na naitama at kung saan, siyempre, ay dapat na multi-threaded.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Itinakda namin ang multithreading bilang pangunahing gawain. Kailangan nating mahawakan nang maayos ang alon ng mga papasok na koneksyon sa TLS.

Upang gawin ito, kailangan naming bumuo ng isang hiwalay na library na tinatawag na Machinarium, na idinisenyo upang ilarawan ang mga estado ng makina ng isang koneksyon sa network bilang sequential code. Kung titingnan mo ang source code ng libpq, makakakita ka ng ilang medyo kumplikadong mga tawag na maaaring magbalik sa iyo ng isang resulta at magsasabing, β€œTawagan mo ako mamaya. Sa ngayon mayroon akong IO sa ngayon, ngunit kapag nawala ang IO magkakaroon ako ng load sa processor." At ito ay isang multi-level scheme. Ang komunikasyon sa network ay karaniwang inilalarawan ng isang makina ng estado. Maraming panuntunan tulad ng "Kung nakatanggap ako dati ng packet header na may sukat na N, ngayon ay naghihintay ako ng N byte," "Kung nagpadala ako ng SYNC packet, ngayon ay naghihintay ako ng isang packet na may metadata ng resulta." Ang resulta ay medyo mahirap, counterintuitive na code, na parang ang maze ay na-convert sa line scan. Ginawa namin ito upang sa halip na isang makina ng estado, inilalarawan ng programmer ang pangunahing landas ng pakikipag-ugnayan sa anyo ng ordinaryong imperative code. Kaya lang sa imperative code na ito kailangan mong magpasok ng mga lugar kung saan kailangang maputol ang execution sequence sa pamamagitan ng paghihintay ng data mula sa network, pagpasa sa execution context sa isa pang coroutine (green thread). Ang diskarte na ito ay katulad ng katotohanan na isinulat namin ang pinaka-inaasahang landas sa maze nang sunud-sunod, at pagkatapos ay magdagdag ng mga sanga dito.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Bilang resulta, mayroon kaming isang thread na tinatanggap ng TCP at ipinapasa ng round-robin ang koneksyon ng TPC sa maraming manggagawa.

Sa kasong ito, ang bawat koneksyon ng kliyente ay palaging tumatakbo sa isang processor. At ito ay nagpapahintulot sa iyo na gawin itong cache-friendly.

At bilang karagdagan, bahagyang pinahusay namin ang koleksyon ng maliliit na packet sa isang malaking packet upang maibsan ang system TCP stack.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Bilang karagdagan, pinahusay namin ang transactional pooling sa kahulugan na ang Odyssey, kapag na-configure, ay maaaring magpadala ng CANCEL at ROLLBACK kung sakaling magkaroon ng pagkabigo sa koneksyon sa network, ibig sabihin, kung walang naghihintay ng kahilingan, sasabihin ni Odyssey sa database na huwag subukang tuparin ang kahilingan na maaaring mag-aksaya ng mahalagang mga mapagkukunan.

At hangga't maaari, pinapanatili namin ang mga koneksyon sa parehong kliyente. Iniiwasan nitong muling i-install ang application_name_add_host. Kung posible ito, hindi na namin kailangang i-reset ang mga parameter na kinakailangan para sa mga diagnostic.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Nagtatrabaho kami para sa interes ng Yandex.Cloud. At kung gumagamit ka ng pinamamahalaang PostgreSQL at may naka-install na connection pooler, maaari kang lumikha ng lohikal na pagtitiklop palabas, ibig sabihin, iwanan kami, kung gusto mo, gamit ang lohikal na pagtitiklop. Hindi ilalabas ng bouncer ang lohikal na daloy ng pagtitiklop sa labas.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ito ay isang halimbawa ng pag-set up ng lohikal na pagtitiklop.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Bilang karagdagan, mayroon kaming suporta para sa pisikal na pagtitiklop sa labas. Sa Cloud, siyempre, imposible ito, dahil ang kumpol ay magbibigay sa iyo ng masyadong maraming impormasyon tungkol sa sarili nito. Ngunit sa iyong mga pag-install, kung kailangan mo ng pisikal na pagtitiklop sa pamamagitan ng pooler ng koneksyon sa Odyssey, posible ito.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ang Odyssey ay may ganap na katugmang pagsubaybay sa PgBouncer. Mayroon kaming parehong console na nagpapatakbo ng halos lahat ng parehong mga utos. Kung may kulang, magpadala ng pull request, o kahit isang isyu sa GitHub, at kukumpletuhin namin ang mga kinakailangang command. Ngunit mayroon na kaming pangunahing pag-andar ng PgBouncer console.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

At, siyempre, mayroon kaming error sa pagpapasa. Ibabalik namin ang error na iniulat ng database. Makakatanggap ka ng impormasyon tungkol sa kung bakit hindi ka kasama sa database, at hindi lang dahil hindi ka kasama dito.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Naka-disable ang feature na ito kung sakaling kailanganin mo ng 100% compatibility sa PgBouncer. Maaari tayong kumilos tulad ng Bouncer, para lang maging ligtas.

Development

Ilang salita tungkol sa source code ng Odyssey.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

https://github.com/yandex/odyssey/pull/66

Halimbawa, may mga "Pause / Resume" na mga utos. Karaniwang ginagamit ang mga ito upang i-update ang database. Kung kailangan mong i-update ang Postgres, maaari mo itong i-pause sa pooler ng koneksyon, gawin ang pg_upgrade, pagkatapos ay ipagpatuloy. At mula sa panig ng kliyente, ito ay magmumukhang parang bumagal ang database. Ang functionality na ito ay dinala sa amin ng mga tao mula sa komunidad. Siya ay hindi pa nagyelo, ngunit sa lalong madaling panahon ang lahat ay magiging. (Naka-freeze na)

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

https://github.com/yandex/odyssey/pull/73 - nagyelo na

Bilang karagdagan, ang isa sa mga bagong feature sa PgBouncer ay suporta para sa SCRAM Authentication, na dinala rin sa amin ng isang taong hindi nagtatrabaho sa Yandex.Cloud. Parehong kumplikadong pag-andar at mahalaga.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Samakatuwid, nais kong sabihin sa iyo kung saan ginawa ang Odyssey, kung sakaling gusto mo ring magsulat ng kaunting code ngayon.

Mayroon kang Odyssey source base, na umaasa sa dalawang pangunahing library. Ang Kiwi library ay isang pagpapatupad ng Postgres message protocol. Ibig sabihin, ang katutubong proto 3 ng Postgres ay mga karaniwang mensahe na maaaring ipagpalit ng mga front-end at back-end. Ang mga ito ay ipinatupad sa Kiwi library.

Ang library ng Machinarium ay isang library ng pagpapatupad ng thread. Ang isang maliit na fragment ng Machinarium na ito ay nakasulat sa assembly language. Ngunit huwag maalarma, mayroon lamang 15 na linya.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Arkitektura ng Odyssey. Mayroong pangunahing makina kung saan tumatakbo ang mga coroutine. Ang makinang ito ay nagpapatupad ng pagtanggap ng mga papasok na koneksyon sa TCP at pamamahagi ng mga ito sa mga manggagawa.

Ang isang handler para sa ilang mga kliyente ay maaaring magtrabaho sa loob ng isang manggagawa. Pinapatakbo din ng pangunahing thread ang console at ang pagpoproseso ng mga gawain ng crone upang tanggalin ang mga koneksyon na hindi na kailangan sa pool.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Sinusubukan ang Odyssey gamit ang karaniwang Postgres test suite. Nagpapatakbo lang kami ng install-check sa pamamagitan ng Bouncer at sa pamamagitan ng Odyssey, nakakakuha kami ng null div. Mayroong ilang mga pagsubok na nauugnay sa pag-format ng petsa na hindi eksaktong pumasa sa Bouncer at sa Odyssey.

Bilang karagdagan, maraming mga driver na may sariling pagsubok. At ginagamit namin ang kanilang mga pagsubok upang subukan ang Odyssey.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Bilang karagdagan, dahil sa aming configuration ng cascade, kailangan naming subukan ang iba't ibang mga bundle: Postgres + Odyssey, PgBouncer + Odyssey, Odyssey + Odyssey upang matiyak na kung napunta ang Odyssey sa alinman sa mga bahagi sa cascade, gagana pa rin ito gaya ng inaasahan natin.

Rake

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ginagamit namin ang Odyssey sa produksyon. At hindi magiging patas kung sasabihin kong gumagana lang ang lahat. Hindi, iyon ay, oo, ngunit hindi palaging. Halimbawa, sa produksyon ay gumana lang ang lahat, pagkatapos ay dumating ang aming mga kaibigan mula sa PostgreSQL Professional at sinabi na mayroon kaming memory leak. Sila talaga, tinama namin sila. Ngunit ito ay simple.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Pagkatapos ay natuklasan namin na ang connection pooler ay may mga papasok na TLS na koneksyon at papalabas na TLS na koneksyon. At ang mga koneksyon ay nangangailangan ng mga sertipiko ng kliyente at mga sertipiko ng server.

Ang mga sertipiko ng server ng Bouncer at Odyssey ay muling binabasa ng kanilang pcache, ngunit ang mga sertipiko ng kliyente ay hindi kailangang basahin muli mula sa pcache, dahil ang aming nasusukat na Odyssey sa huli ay tumatakbo sa pagganap ng system ng pagbabasa ng certificate na ito. Ito ay nagulat sa amin, dahil hindi siya nagtagal upang labanan. Sa una ito ay linearly scale, ngunit pagkatapos ng 20 papasok na sabay-sabay na koneksyon ang problemang ito ay nagpakita mismo.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ang Pluggable Authentication Method ay ang kakayahang mag-authenticate gamit ang built-in na Lunux tool. Sa PgBouncer ito ay ipinatupad sa paraang may hiwalay na thread na maghihintay ng tugon mula sa PAM at mayroong pangunahing PgBouncer thread na nagseserbisyo sa kasalukuyang koneksyon at maaaring humiling sa kanila na manirahan sa PAM thread.

Hindi namin ito ipinatupad sa isang simpleng dahilan. Marami tayong thread. Bakit kailangan natin ang mga ito?

Ito ay maaaring lumikha ng mga problema sa huli kung mayroon kang PAM authentication at non-PAM authentication, kung gayon ang isang malaking wave ng PAM authentication ay maaaring makabuluhang maantala ang non-PAM authentication. Ito ay isa sa mga bagay na hindi namin naayos. Ngunit kung nais mong ayusin ito, magagawa mo ito.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ang isa pang rake ay mayroon kaming isang thread na tumatanggap ng lahat ng mga papasok na koneksyon. At pagkatapos ay inilipat sila sa worker pool, kung saan magaganap ang TLS handshake.

Bottom line, kung mayroon kang magkakaugnay na alon ng 20 mga koneksyon sa network, lahat sila ay tatanggapin. At sa panig ng kliyente, magsisimula ang libpq sa pag-uulat ng mga timeout. Bilang default, ito ay tila 000 segundo.

Kung lahat sila ay hindi makapasok sa database nang sabay-sabay, kung gayon hindi sila makakapasok sa database, dahil ang lahat ng ito ay maaaring saklawin ng hindi exponential retry.

Nakarating kami sa konklusyon na kinopya namin ang scheme mula sa PgBouncer dito na may katotohanan na na-throttling namin ang bilang ng mga koneksyon sa TCP na tinatanggap namin.

Kung nakita namin na tumatanggap kami ng mga koneksyon, ngunit sa huli ay wala silang oras para makipagkamay, inilalagay namin sila sa isang pila upang hindi sila mag-aksaya ng mga mapagkukunan ng CPU. Ito ay humahantong sa katotohanan na ang sabay-sabay na pagkakamay ay maaaring hindi maisagawa para sa lahat ng mga koneksyon na dumating. Pero at least may papasok sa database kahit medyo mabigat ang load.

Roadmap

Ano ang gusto mong makita sa hinaharap sa Odyssey? Ano ang handa nating paunlarin ang ating sarili at ano ang inaasahan natin sa komunidad?

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Mula noong Agosto 2019.

Ito ang hitsura ng roadmap ng Odyssey noong Agosto:

  • Gusto namin ng SCRAM at PAM authentication.
  • Nais naming ipasa ang mga kahilingan sa pagbabasa sa standby.
  • Gusto ko ng online restart.
  • At ang kakayahang mag-pause sa server.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Nakumpleto na ang kalahati ng roadmap na ito, at hindi sa amin. At ito ay mabuti. Kaya't pag-usapan natin kung ano ang natitira at magdagdag pa.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Tungkol sa ipasa ang read-only na mga query sa standby? Mayroon kaming mga replika na magpapainit lang ng hangin nang hindi nagsasagawa ng mga kahilingan. Kailangan natin silang magbigay ng failover at switchover. Sa kaso ng mga problema sa isa sa mga sentro ng data, nais kong sakupin sila ng ilang kapaki-pakinabang na gawain. Dahil hindi namin mai-configure ang parehong mga sentral na processor, magkaiba ang parehong memorya, dahil kung hindi ay hindi gagana ang pagtitiklop.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Sa prinsipyo, sa Postgres, simula sa 10, posibleng tukuyin ang session_attrs kapag kumokonekta. Maaari mong ilista ang lahat ng mga host ng database sa koneksyon at sabihin kung bakit ka pupunta sa database: magsulat o magbasa lamang. At ang driver mismo ang pipili ng unang host sa listahan na pinakagusto niya, na tumutupad sa mga kinakailangan ng session_attrs.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ngunit ang problema sa diskarteng ito ay hindi nito kinokontrol ang lag ng pagtitiklop. Maaaring mayroon kang ilang kopya na nahuli sa hindi katanggap-tanggap na tagal ng oras para sa iyong serbisyo. Upang paganahin ang buong tampok na pagpapatupad ng mga read query sa isang replica, mahalagang kailangan naming suportahan ang kakayahan ng Odyssey na hindi tumakbo kapag hindi ito mabasa.

Ang Odyssey ay dapat pumunta sa database paminsan-minsan at hilingin ang distansya ng pagtitiklop mula sa pangunahing. At kung naabot nito ang halaga ng limitasyon, huwag payagan ang mga bagong kahilingan sa database, sabihin sa kliyente na kailangan nitong muling simulan ang mga koneksyon at, posibleng, pumili ng isa pang host para magsagawa ng mga kahilingan. Ito ay magbibigay-daan sa database na mabilis na maibalik ang replication lag at bumalik muli upang tumugon sa isang kahilingan.

Mahirap magbigay ng time frame para sa pagpapatupad, dahil open source ito. Pero, sana, hindi 2,5 years gaya ng mga kasamahan ko sa PgBouncer. Ito ang feature na gusto kong makita sa Odyssey.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Sa komunidad, nagtanong ang mga tao tungkol sa suporta para sa inihandang pahayag. Ngayon ay maaari kang lumikha ng isang inihandang pahayag sa dalawang paraan. Una, maaari mong isagawa ang SQL command, ibig sabihin ay "handa". Upang maunawaan ang SQL command na ito, kailangan nating matutunang maunawaan ang SQL sa bahagi ng Bouncer. Ito ay magiging labis, dahil ito ay labis, dahil kailangan natin ang buong parser. Hindi namin ma-parse ang bawat SQL command.

Ngunit mayroong isang inihandang pahayag sa antas ng protocol ng mensahe sa proto3. At ito ang lugar kung kailan ang impormasyon na nililikha ng isang inihandang pahayag ay nasa isang structured form. At maaari naming suportahan ang pag-unawa na sa ilang koneksyon sa server hiniling ng kliyente na lumikha ng mga inihandang pahayag. At kahit na sarado ang transaksyon, kailangan pa rin nating panatilihin ang pagkakakonekta sa pagitan ng server at ng kliyente.

Ngunit narito ang isang pagkakaiba-iba sa diyalogo, dahil may nagsasabi na kailangan mong maunawaan kung anong uri ng mga inihandang pahayag ang nilikha ng kliyente at ibinahagi ang koneksyon sa server sa pagitan ng lahat ng mga kliyente na lumikha ng koneksyon sa server na ito, ibig sabihin, na lumikha ng gayong handa na pahayag.

Sinabi ni Andres Freund na kung ang isang kliyente ay dumating sa iyo na nakagawa na ng ganoong inihandang pahayag sa isa pang koneksyon sa server, pagkatapos ay gawin ito para sa kanya. Ngunit tila medyo mali na magsagawa ng mga query sa database sa halip na sa kliyente, ngunit mula sa punto ng view ng developer na nagsusulat ng protocol para sa pakikipag-ugnayan sa database, magiging maginhawa kung bibigyan lamang siya ng koneksyon sa network kung saan may ganyang inihandang query.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

At isa pang tampok na kailangan nating ipatupad. Mayroon na kaming pagsubaybay na katugma sa PgBouncer. Maaari naming ibalik ang average na oras ng pagpapatupad ng query. Ngunit ang average na oras ay ang average na temperatura sa ospital: ang ilan ay malamig, ang ilan ay mainit-init - sa karaniwan, lahat ay malusog. Hindi yan totoo.

Kailangan nating ipatupad ang suporta para sa mga percentile na magsasaad na may mga mabagal na query na nag-aaksaya ng mga mapagkukunan at ginagawang mas katanggap-tanggap ang pagsubaybay.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Ang pinakamahalagang bagay ay gusto ko ang bersyon 1.0 (Ang bersyon 1.1 ay inilabas na). Ang katotohanan ay ang Odyssey ay nasa bersyon 1.0rc na ngayon, i.e. release candidate. At ang lahat ng mga problema na nakalista ko ay naayos na may eksaktong parehong bersyon, maliban sa pagtagas ng memorya.

Ano ang ibig sabihin ng bersyon 1.0 para sa atin? Inilunsad namin ang Odyssey sa aming mga base. Ito ay tumatakbo na sa aming mga database, ngunit kapag ito ay umabot sa punto ng 1 mga kahilingan sa bawat segundo, pagkatapos ay maaari nating sabihin na ito ang bersyon ng paglabas at ito ay isang bersyon na matatawag na 000.

Ilang tao sa komunidad ang nagtanong na ang bersyon 1.0 ay magsama ng pause at SCRAM. Ngunit mangangahulugan ito na kakailanganin nating ilunsad ang susunod na bersyon sa produksyon, dahil wala pang napatay na SCRAM o pause. Ngunit, malamang, ang isyung ito ay malulutas nang mabilis.

Odyssey roadmap: ano pa ang gusto natin mula sa isang connection pooler. Andrey Borodin (2019)

Hinihintay ko ang pull request mo. Gusto ko ring marinig kung anong mga problema mo sa Bouncer. Pag-usapan natin sila. Siguro maaari naming ipatupad ang ilang mga function na kailangan mo.

Ito ang katapusan ng aking bahagi, nais kong makinig sa iyo. Salamat!

mga katanungan

Kung itatakda ko ang sarili kong application_name, maipapasa ba ito nang tama, kasama ang pagsasama-sama ng transaksyon sa Odyssey?

Odyssey o Bouncer?

Sa Odyssey. Sa Bouncer ito itinapon.

Gagawa tayo ng set.

At kung ang aking tunay na koneksyon ay tumalon sa iba pang mga koneksyon, ito ba ay maililipat?

Gagawa kami ng set ng lahat ng parameter na nakalista sa listahan. Hindi ko masabi kung ang application_name ay nasa listahang ito. Parang nakita ko siya doon. Itatakda namin ang lahat ng parehong mga parameter. Sa isang kahilingan, gagawin ng set ang lahat ng na-install ng kliyente sa panahon ng startup.

Salamat, Andrey, para sa ulat! Magandang ulat! Natutuwa ako na ang Odyssey ay umuunlad nang mas mabilis at mas mabilis bawat minuto. Gusto kong magpatuloy sa ganito. Hiniling na namin sa iyo na magkaroon ng maraming data-source na koneksyon upang ang Odyssey ay makakonekta sa iba't ibang mga database nang sabay-sabay, ibig sabihin, isang master slave, at pagkatapos ay awtomatikong kumonekta sa isang bagong master pagkatapos ng failover.

Oo, parang natatandaan ko ang usapan na ito. Ngayon ay may ilang mga imbakan. Ngunit walang paglipat sa pagitan nila. Sa aming panig, dapat naming i-poll ang server na ito ay buhay pa at maunawaan na ang isang failover ay naganap, na tatawag sa pg_recovery. Mayroon akong karaniwang paraan ng pag-unawa na hindi kami nakarating sa master. At dapat ba nating maunawaan kahit papaano mula sa mga pagkakamali o ano? Ibig sabihin, interesante ang ideya, pinag-uusapan. Sumulat ng higit pang mga komento. Kung mayroon kang mga manggagawa na nakakaalam ng C, kung gayon iyon ay mahusay.

Interesado rin sa amin ang isyu ng pag-scale sa mga replika, dahil gusto naming gawing simple hangga't maaari para sa mga developer ng application ang pag-aampon ng mga replicated na cluster. Ngunit dito gusto ko ng higit pang mga komento, ibig sabihin, eksakto kung paano ito gagawin, kung paano ito gagawin nang maayos.

Ang tanong ay tungkol din sa mga replika. Ito ay lumiliko na mayroon kang isang master at ilang mga replika. At malinaw na mas madalas silang pumunta sa replika kaysa sa master para sa mga koneksyon, dahil maaaring may mga pagkakaiba sila. Sinabi mo na ang pagkakaiba sa data ay maaaring maging tulad na hindi ito masisiyahan sa iyong negosyo at hindi ka pupunta doon hanggang sa ito ay ginagaya. Kasabay nito, kung hindi ka pumunta doon nang mahabang panahon, at pagkatapos ay nagsimulang pumunta, kung gayon ang data na kinakailangan ay hindi agad magagamit. Iyon ay, kung patuloy kaming pumunta sa master, pagkatapos ay ang cache doon ay warmed up, ngunit sa replica ang cache ay lags ng kaunti.

Oo totoo. Ang pcache ay hindi magkakaroon ng mga bloke ng data na gusto mo, ang tunay na cache ay hindi magkakaroon ng impormasyon tungkol sa mga talahanayan na gusto mo, ang mga plano ay hindi magkakaroon ng mga na-parse na query, walang anuman.

At kapag mayroon kang isang uri ng kumpol, at nagdagdag ka ng isang bagong kopya doon, pagkatapos habang nagsisimula ito, lahat ay masama sa loob nito, ibig sabihin, pinapataas nito ang cache nito.

Nakuha ko ang ideya. Ang tamang diskarte ay ang magpatakbo muna ng maliit na porsyento ng mga query sa replica, na magpapainit sa cache. Sa halos pagsasalita, mayroon tayong kundisyon na dapat tayong mahuli sa master nang hindi hihigit sa 10 segundo. At ang kundisyong ito ay hindi kasama sa isang alon, ngunit maayos para sa ilang mga kliyente.

Oo, dagdagan ang timbang.

Ito ay isang magandang ideya. Ngunit kailangan muna nating ipatupad ang pagsasara na ito. Una kailangan nating i-off, at pagkatapos ay pag-isipan natin kung paano i-on. Ito ay isang mahusay na tampok upang paganahin nang maayos.

Ang Nginx ay may ganitong opsyon slowly start sa isang kumpol para sa server. At unti-unti niyang dinadagdagan ang kargada.

Oo, magandang ideya, susubukan namin ito kapag nakuha namin ito.

Pinagmulan: www.habr.com

Magdagdag ng komento