Patuloy na Mga Kasanayan sa Paghahatid sa Docker (pagsusuri at video)

Sisimulan namin ang aming blog sa mga publikasyon batay sa pinakabagong mga talumpati ng aming teknikal na direktor distol (Dmitry Stolyarov). Lahat ng mga ito ay naganap noong 2016 sa iba't ibang mga propesyonal na kaganapan at nakatuon sa paksa ng DevOps at Docker. Isang video mula sa Docker Moscow meeting sa Badoo office, mayroon na kami inilathala Online. Ang mga bago ay sasamahan ng mga artikulong naghahatid ng kakanyahan ng mga ulat. Kaya…

Mayo 31 sa kumperensya RootConf 2016, na ginanap bilang bahagi ng pagdiriwang na "Russian Internet Technologies" (RIT++ 2016), ang seksyong "Continuous Deployment and Deployment" ay binuksan sa ulat na "Pinakamahusay na Kasanayan ng Patuloy na Paghahatid sa Docker". Binuod at isinasaayos nito ang pinakamahuhusay na kagawian para sa pagbuo ng proseso ng Continuous Delivery (CD) gamit ang Docker at iba pang Open Source na mga produkto. Nakikipagtulungan kami sa mga solusyong ito sa produksyon, na nagbibigay-daan sa amin na umasa sa praktikal na karanasan.

Patuloy na Mga Kasanayan sa Paghahatid sa Docker (pagsusuri at video)

Kung may pagkakataon kang gumugol ng isang oras video ng ulat, inirerekomenda naming panoorin ito nang buo. Kung hindi, nasa ibaba ang pangunahing buod sa text form.

Tuloy-tuloy na Paghahatid sa Docker

Sa ilalim Patuloy na Paghahatid naiintindihan namin ang hanay ng mga kaganapan bilang isang resulta kung saan ang code ng aplikasyon mula sa repositoryo ng Git ay unang napupunta sa produksyon, at pagkatapos ay napupunta sa archive. Mukhang ganito: Git β†’ Build β†’ Test β†’ Release β†’ Operate.

Patuloy na Mga Kasanayan sa Paghahatid sa Docker (pagsusuri at video)
Karamihan sa ulat ay nakatuon sa yugto ng pagbuo (pagpupulong ng aplikasyon), at ang mga paksang inilabas at pinapatakbo ay binabanggit sa madaling sabi. Pag-uusapan natin ang tungkol sa mga problema at pattern na nagbibigay-daan sa iyong lutasin ang mga ito, at maaaring iba ang mga partikular na pagpapatupad ng mga pattern na ito.

Bakit kailangan dito ang Docker? It is not for nothing that we decided to talk about Continuous Delivery practices in the context of this Open Source tool. Bagama't ang buong ulat ay nakatuon sa paggamit nito, maraming dahilan ang inihayag kapag isinasaalang-alang ang pangunahing pattern ng paglulunsad ng code ng aplikasyon.

Pangunahing pattern ng rollout

Kaya, kapag inilunsad namin ang mga bagong bersyon ng application, tiyak na nahaharap kami problema sa downtime, nabuo sa panahon ng paglipat ng server ng produksyon. Ang trapiko mula sa lumang bersyon ng application patungo sa bago ay hindi maaaring lumipat kaagad: dapat muna nating tiyakin na ang bagong bersyon ay hindi lamang matagumpay na na-download, ngunit din "nagpainit" (ibig sabihin, ganap na handang maghatid ng mga kahilingan).

Patuloy na Mga Kasanayan sa Paghahatid sa Docker (pagsusuri at video)
Kaya, para sa ilang oras ang parehong mga bersyon ng application (luma at bago) ay gagana nang sabay-sabay. Na awtomatikong humahantong sa magkasalungat na pinagsasaluhang mapagkukunan: network, file system, IPC, atbp. Sa Docker, ang problemang ito ay madaling malutas sa pamamagitan ng pagpapatakbo ng iba't ibang bersyon ng application sa magkahiwalay na mga lalagyan, kung saan ginagarantiyahan ang paghihiwalay ng mapagkukunan sa loob ng parehong host (server/virtual machine). Siyempre, maaari kang makakuha ng ilang mga trick nang walang pagkakabukod, ngunit kung mayroong isang handa at maginhawang tool, pagkatapos ay mayroong kabaligtaran na dahilan - hindi upang pabayaan ito.

Nagbibigay ang containerization ng maraming iba pang benepisyo kapag na-deploy. Ang anumang aplikasyon ay nakasalalay sa tiyak na bersyon (o hanay ng bersyon) interpreter, pagkakaroon ng mga module/extension, atbp., pati na rin ang kanilang mga bersyon. At nalalapat ito hindi lamang sa agarang executable na kapaligiran, kundi pati na rin sa buong kapaligiran, kabilang ang software ng system at ang bersyon nito (hanggang sa ginamit na pamamahagi ng Linux). Dahil sa ang katunayan na ang mga lalagyan ay naglalaman ng hindi lamang application code, kundi pati na rin ang paunang naka-install na system at application software ng mga kinakailangang bersyon, maaari mong kalimutan ang tungkol sa mga problema sa mga dependency.

Pagbubuod pangunahing pattern ng rollout mga bagong bersyon na isinasaalang-alang ang mga sumusunod na salik:

  1. Sa una, ang lumang bersyon ng application ay tumatakbo sa unang lalagyan.
  2. Ang bagong bersyon ay inilulunsad at "pinainit" sa pangalawang lalagyan. Kapansin-pansin na ang bagong bersyon na ito mismo ay maaaring magdala hindi lamang ng na-update na code ng aplikasyon, kundi pati na rin ang alinman sa mga dependency nito, pati na rin ang mga bahagi ng system (halimbawa, isang bagong bersyon ng OpenSSL o ang buong pamamahagi).
  3. Kapag ganap nang handa ang bagong bersyon na maghatid ng mga kahilingan, lilipat ang trapiko mula sa unang lalagyan patungo sa pangalawa.
  4. Ang lumang bersyon ay maaari na ngayong ihinto.

Ang pamamaraang ito ng pag-deploy ng iba't ibang bersyon ng application sa magkahiwalay na mga lalagyan ay nagbibigay ng isa pang kaginhawahan - mabilis na rollback sa lumang bersyon (pagkatapos ng lahat, sapat na upang ilipat ang trapiko sa nais na lalagyan).

Patuloy na Mga Kasanayan sa Paghahatid sa Docker (pagsusuri at video)
Ang huling unang rekomendasyon ay parang isang bagay na kahit ang Kapitan ay hindi mahanapan ng kasalanan: "[kapag nag-oorganisa ng Tuloy-tuloy na Paghahatid sa Docker] Gamitin ang Docker [at unawain kung ano ang ibinibigay nito]" Tandaan, hindi ito isang pilak na bala na malulutas ang bawat problema, ngunit isang tool na nagbibigay ng isang kahanga-hangang pundasyon.

Reproducibility

Ang ibig sabihin ng "reproducibility" ay isang pangkalahatang hanay ng mga problemang nararanasan kapag nagpapatakbo ng mga application. Pinag-uusapan natin ang mga ganitong kaso:

  • Ang mga script na sinuri ng departamento ng kalidad para sa pagtatanghal ay dapat na tumpak na kopyahin sa produksyon.
  • Ang mga application ay nai-publish sa mga server na maaaring makatanggap ng mga pakete mula sa iba't ibang mga salamin ng repositoryo (sa paglipas ng panahon sila ay na-update, at kasama nila ang mga bersyon ng mga naka-install na application).
  • "Lahat ay gumagana para sa akin sa lokal!" (...at hindi pinapayagan ang mga developer sa produksyon.)
  • Kailangan mong suriin ang isang bagay sa lumang (naka-archive) na bersyon.
  • ...

Ang kanilang pangkalahatang kakanyahan ay nagmumula sa katotohanan na ang ganap na pagsunod sa mga kapaligiran na ginamit (pati na rin ang kawalan ng kadahilanan ng tao) ay kinakailangan. Paano natin masisiguro ang reproducibility? Gumawa ng mga larawan ng Docker batay sa code mula sa Git, at pagkatapos ay gamitin ang mga ito para sa anumang gawain: sa mga site ng pagsubok, sa produksyon, sa mga lokal na makina ng mga programmer... Kasabay nito, mahalagang bawasan ang mga aksyon na ginagawa pagkatapos pag-assemble ng imahe: mas simple ito, mas malamang na may mga error.

Ang imprastraktura ay code

Kung ang mga kinakailangan sa imprastraktura (availability ng software ng server, bersyon nito, atbp.) ay hindi pormal at "na-program," kung gayon ang paglulunsad ng anumang pag-update ng application ay maaaring magresulta sa mga mapaminsalang kahihinatnan. Halimbawa, sa pagtatanghal ay lumipat ka na sa PHP 7.0 at muling isinulat ang code nang naaayon - pagkatapos ay ang hitsura nito sa produksyon na may ilang lumang PHP (5.5) ay tiyak na magugulat sa isang tao. Maaaring hindi mo makalimutan ang tungkol sa isang malaking pagbabago sa bersyon ng interpreter, ngunit "ang diyablo ay nasa mga detalye": ang sorpresa ay maaaring nasa isang maliit na pag-update ng anumang dependency.

Ang isang diskarte upang malutas ang problemang ito ay kilala bilang IaC (Infrastructure as Code, β€œinfrastructure as code”) at nagsasangkot ng pag-iimbak ng mga kinakailangan sa imprastraktura kasama ang code ng aplikasyon. Gamit ito, ang mga developer at mga espesyalista sa DevOps ay maaaring gumana sa parehong Git application repository, ngunit sa iba't ibang bahagi nito. Mula sa code na ito, ang isang imahe ng Docker ay nilikha sa Git, kung saan ang application ay na-deploy na isinasaalang-alang ang lahat ng mga detalye ng imprastraktura. Sa madaling salita, ang mga script (mga panuntunan) para sa pag-assemble ng mga imahe ay dapat na nasa parehong repository na may source code at pinagsama-sama.

Patuloy na Mga Kasanayan sa Paghahatid sa Docker (pagsusuri at video)

Sa kaso ng isang multi-layer na arkitektura ng application - halimbawa, mayroong nginx, na nakatayo sa harap ng isang application na tumatakbo na sa loob ng isang Docker container - Ang mga imahe ng Docker ay dapat malikha mula sa code sa Git para sa bawat layer. Pagkatapos ang unang larawan ay maglalaman ng isang application na may isang interpreter at iba pang "malapit" na dependencies, at ang pangalawang larawan ay maglalaman ng upstream nginx.

Mga imahe ng Docker, komunikasyon sa Git

Hinahati namin ang lahat ng larawan ng Docker na nakolekta mula sa Git sa dalawang kategorya: pansamantala at release. Mga pansamantalang larawan na naka-tag sa pamamagitan ng pangalan ng sangay sa Git, ay maaaring ma-overwrite ng susunod na commit at ilalabas lamang para sa preview (hindi para sa produksyon). Ito ang kanilang pangunahing pagkakaiba sa mga release: hindi mo alam kung aling partikular na commit ang nasa kanila.

Makatuwirang mangolekta sa mga pansamantalang larawan: ang master branch (maaari mong awtomatikong i-roll out ito sa isang hiwalay na site upang patuloy na makita ang kasalukuyang bersyon ng master), mga sangay na may mga release, mga sangay ng mga partikular na inobasyon.

Patuloy na Mga Kasanayan sa Paghahatid sa Docker (pagsusuri at video)
Matapos ang preview ng mga pansamantalang larawan ay dumating sa pangangailangan para sa pagsasalin sa produksyon, ang mga developer ay naglagay ng isang tiyak na tag. Awtomatikong kinokolekta ng tag ilabas ang larawan (ang tag nito ay tumutugma sa tag mula sa Git) at inilunsad sa staging. Kung ito ay matagumpay na napatunayan ng departamento ng kalidad, ito ay mapupunta sa produksyon.

dapp

Ang lahat ng inilarawan (rollout, image assembly, kasunod na pagpapanatili) ay maaaring ipatupad nang nakapag-iisa gamit ang Bash script at iba pang "improvised" na tool. Ngunit kung gagawin mo ito, pagkatapos ay sa ilang mga punto ang pagpapatupad ay hahantong sa mahusay na pagiging kumplikado at mahinang pagkontrol. Sa pag-unawa dito, gumawa kami ng sarili naming espesyal na utility ng Workflow para sa pagbuo ng CI/CD - dapp.

Ang source code nito ay nakasulat sa Ruby, open source at nai-publish sa GitHub. Sa kasamaang palad, ang dokumentasyon ang kasalukuyang pinakamahina na punto ng tool, ngunit ginagawa namin ito. At kami ay magsusulat at mag-uusap tungkol sa dapp nang higit sa isang beses, dahil... Taos-puso kaming hindi makapaghintay na ibahagi ang mga kakayahan nito sa buong interesadong komunidad, ngunit pansamantala, ipadala ang iyong mga isyu at hilahin ang mga kahilingan at/o sundin ang pagbuo ng proyekto sa GitHub.

Na-update noong Agosto 13, 2019: kasalukuyang proyekto dapp pinalitan ng pangalan sa werf, ang code nito ay ganap na naisulat muli sa Go, at ang dokumentasyon nito ay lubos na napabuti.

Kubernetes

Ang isa pang handa na Open Source tool na nakatanggap na ng makabuluhang pagkilala sa propesyonal na kapaligiran ay Kubernetes,isang kumpol ng pamamahala ng Docker. Ang paksa ng paggamit nito sa pagpapatakbo ng mga proyektong binuo sa Docker ay lampas sa saklaw ng ulat, kaya ang pagtatanghal ay limitado sa isang pangkalahatang-ideya ng ilang mga kagiliw-giliw na tampok.

Para sa paglulunsad, nag-aalok ang Kubernetes ng:

  • Readiness probe β€” pagsuri sa kahandaan ng isang bagong bersyon ng application (upang ilipat ang trapiko dito);
  • rolling update - sunud-sunod na pag-update ng imahe sa isang kumpol ng mga container (shutdown, update, paghahanda para sa paglulunsad, paglipat ng trapiko);
  • kasabay na pag-update - pag-update ng isang imahe sa isang kumpol na may ibang diskarte: una sa kalahati ng mga lalagyan, pagkatapos ay sa iba pa;
  • mga paglabas ng canary - paglulunsad ng isang bagong imahe sa isang limitadong (maliit) na bilang ng mga lalagyan upang masubaybayan ang mga anomalya.

Dahil ang Patuloy na Paghahatid ay hindi lamang ang paglabas ng bagong bersyon, ang Kubernetes ay may ilang mga kakayahan para sa kasunod na pagpapanatili ng imprastraktura: built-in na pagsubaybay at pag-log para sa lahat ng mga lalagyan, awtomatikong pag-scale, atbp. Lahat ng ito ay gumagana na at naghihintay lamang ng wastong pagpapatupad sa iyong mga proseso.

Panghuling rekomendasyon

  1. Gamitin ang Docker.
  2. Lumikha ng mga larawan ng Docker ng mga application para sa lahat ng iyong mga pangangailangan.
  3. Sundin ang prinsipyong "Ang imprastraktura ay code."
  4. I-link ang Git sa Docker.
  5. I-regulate ang pagkakasunud-sunod ng paglulunsad.
  6. Gumamit ng isang handa na platform (Kubernetes o iba pa).

Mga video at slide

Video mula sa pagganap (mga isang oras) na-publish sa YouTube (ang ulat mismo ay nagsisimula sa ika-5 minuto - sundan ang link upang i-play mula sa sandaling ito).

Presentasyon ng ulat:

PS

Iba pang mga ulat sa paksa sa aming blog:

Pinagmulan: www.habr.com

Magdagdag ng komento