Kas yra Docker: trumpa ekskursija į istoriją ir pagrindines abstrakcijas

Prasidėjo rugpjūčio 10 d., Slurm Docker vaizdo kursas, kuriame mes jį visiškai analizuojame – nuo ​​pagrindinių abstrakcijų iki tinklo parametrų.

Šiame straipsnyje kalbėsime apie Docker istoriją ir pagrindines jos abstrakcijas: Image, Cli, Dockerfile. Paskaita skirta pradedantiesiems, todėl vargu ar bus įdomi patyrusiems vartotojams. Nebus kraujo, apendikso ar gilaus panardinimo. Patys pagrindai.

Kas yra Docker: trumpa ekskursija į istoriją ir pagrindines abstrakcijas

Kas yra Docker

Pažvelkime į Docker apibrėžimą iš Vikipedijos.

Docker yra programinė įranga, skirta automatizuoti programų diegimą ir valdymą konteinerinėse aplinkose.

Iš šio apibrėžimo nieko neaišku. Ypač neaišku, ką reiškia „aplinkoje, kuri palaiko konteinerizavimą“. Norėdami tai sužinoti, grįžkime laiku atgal. Pradėkime nuo eros, kurią tradiciškai vadinu „monolito era“.

Monolitinė era

Monolitinė era yra 2000-ųjų pradžia, kai visos programos buvo monolitinės, su daugybe priklausomybių. Vystymas užtruko ilgai. Tuo pačiu metu serverių nebuvo daug, visi žinojome juos pagal pavadinimą ir stebėjome. Yra toks juokingas palyginimas:

Naminiai gyvūnai yra naminiai gyvūnai. Monolitinėje eroje su savo serveriais elgėmės kaip su augintiniais, juos prižiūrėjome ir puoselėjome, nupūtėme dulkių dėmes. O geresniam išteklių valdymui panaudojome virtualizaciją: paėmėme serverį ir supjaustėme jį į kelias virtualias mašinas, taip užtikrindami aplinkos izoliaciją.

Hipervizoriumi pagrįstos virtualizacijos sistemos

Tikriausiai visi yra girdėję apie virtualizacijos sistemas: VMware, VirtualBox, Hyper-V, Qemu KVM ir tt Jos suteikia programų izoliaciją ir išteklių valdymą, tačiau turi ir trūkumų. Norėdami atlikti virtualizaciją, jums reikia hipervizoriaus. O hipervizorius yra papildomas išteklius. O pati virtuali mašina dažniausiai yra visas kolosas – sunkus vaizdas, kuriame yra operacinė sistema, Nginx, Apache ir galbūt MySQL. Vaizdas yra didelis, o virtualią mašiną nepatogu valdyti. Dėl to darbas su virtualiomis mašinomis gali būti lėtas. Šiai problemai išspręsti buvo sukurtos virtualizacijos sistemos branduolio lygiu.

Branduolio lygio virtualizacijos sistemos

Branduolio lygio virtualizaciją palaiko OpenVZ, Systemd-nspawn, LXC sistemos. Ryškus tokios virtualizacijos pavyzdys yra LXC („Linux Containers“).

LXC yra operacinės sistemos lygio virtualizacijos sistema, skirta paleisti kelis izoliuotus Linux operacinės sistemos egzempliorius viename mazge. LXC nenaudoja virtualių mašinų, bet kuria virtualią aplinką su savo proceso erdve ir tinklo stekeliu.

Iš esmės LXC kuria konteinerius. Kuo skiriasi virtualios mašinos ir konteineriai?

Kas yra Docker: trumpa ekskursija į istoriją ir pagrindines abstrakcijas

Konteineris netinka procesams izoliuoti: virtualizacijos sistemose branduolio lygiu randama pažeidžiamumų, leidžiančių joms pabėgti iš konteinerio į pagrindinį kompiuterį. Todėl, jei jums reikia ką nors izoliuoti, geriau naudoti virtualią mašiną.

Virtualizavimo ir konteinerizavimo skirtumus galima pamatyti diagramoje.
Yra aparatinės įrangos hipervizoriai, hipervizoriai OS viršuje ir konteineriai.

Kas yra Docker: trumpa ekskursija į istoriją ir pagrindines abstrakcijas

Aparatinės įrangos hipervizoriai yra puikūs, jei tikrai norite ką nors izoliuoti. Nes galima atskirti atminties puslapių ir procesorių lygiu.

Yra hipervizoriai kaip programa ir yra konteineriai, ir mes apie juos kalbėsime toliau. Konteinerių sistemos neturi hipervizoriaus, tačiau yra konteinerių variklis, kuris kuria ir tvarko konteinerius. Šis daiktas yra lengvesnis, todėl dirbant su šerdimi tenka mažiau išlaidų arba visai nėra.

Kas naudojamas konteinerizavimui branduolio lygiu

Pagrindinės technologijos, leidžiančios sukurti konteinerį, atskirtą nuo kitų procesų, yra vardų erdvės ir valdymo grupės.

Vardų erdvės: PID, Networking, Mount ir User. Yra ir daugiau, bet kad būtų lengviau suprasti, mes sutelksime dėmesį į juos.

PID vardų erdvė riboja procesus. Kai, pavyzdžiui, sukuriame PID vardų erdvę ir ten patalpiname procesą, jis tampa su PID 1. Paprastai sistemose PID 1 yra systemd arba init. Atitinkamai, kai įdedame procesą į naują vardų erdvę, jis taip pat gauna PID 1.

Tinklo vardų erdvė leidžia apriboti / izoliuoti tinklą ir įdėti savo sąsajas. Montavimas yra failų sistemos apribojimas. Vartotojas – vartotojų apribojimas.

Valdymo grupės: Atmintis, CPU, IOPS, Tinklas – iš viso apie 12 nustatymų. Kitu atveju jie taip pat vadinami C grupėmis („C grupėmis“).

Valdymo grupės valdo konteinerio išteklius. Per valdymo grupes galime pasakyti, kad konteineris neturėtų sunaudoti daugiau nei tam tikras išteklių kiekis.

Kad konteinerizavimas veiktų pilnai, naudojamos papildomos technologijos: Galimybės, Kopijavimas rašant ir kt.

Galimybės yra tada, kai mes nurodome procesui, ką jis gali ir ko negali. Branduolio lygmenyje tai tiesiog bitmaps su daugybe parametrų. Pavyzdžiui, root vartotojas turi visas teises ir gali daryti viską. Laiko serveris gali pakeisti sistemos laiką: jis turi Time Capsule galimybes, ir viskas. Naudodamiesi privilegijomis galite lanksčiai konfigūruoti procesų apribojimus ir taip apsisaugoti.

„Copy-on-Write“ sistema leidžia dirbti su „Docker“ vaizdais ir juos naudoti efektyviau.

Šiuo metu „Docker“ turi suderinamumo su Cgroups v2 problemų, todėl šiame straipsnyje daugiausia dėmesio skiriama Cgroups v1.

Bet grįžkime prie istorijos.

Kai virtualizacijos sistemos atsirado branduolio lygmenyje, jos buvo pradėtos aktyviai naudoti. Hipervizoriaus pridėtinės išlaidos išnyko, tačiau liko keletas problemų:

  • dideli vaizdai: jie įstumia operacinę sistemą, bibliotekas, krūvą skirtingos programinės įrangos į tą patį OpenVZ ir galiausiai vaizdas vis tiek pasirodo gana didelis;
  • Normalaus pakavimo ir pristatymo standarto nėra, todėl priklausomybių problema išlieka. Yra situacijų, kai dvi kodo dalys naudoja tą pačią biblioteką, bet turi skirtingas versijas. Tarp jų gali kilti konfliktas.

Norint išspręsti visas šias problemas, atėjo kita era.

Konteinerių era

Atėjus konteinerių erai, darbo su jais filosofija pasikeitė:

  • Vienas procesas – vienas konteineris.
  • Visas procesui reikalingas priklausomybes pristatome į jo konteinerį. Tam reikia išpjauti monolitus į mikroservisus.
  • Kuo mažesnis vaizdas, tuo geriau – mažiau galimų pažeidžiamumų, jis greičiau išriečia ir pan.
  • Atvejai tampa trumpalaikiai.

Prisimeni, ką sakiau apie naminius gyvūnus ir galvijus? Anksčiau egzemplioriai buvo kaip naminiai gyvūnai, o dabar jie tapo kaip galvijai. Anksčiau buvo monolitas – viena aplikacija. Dabar tai 100 mikro paslaugų, 100 konteinerių. Kai kuriuose konteineriuose gali būti 2–3 kopijos. Mums tampa mažiau svarbu kontroliuoti kiekvieną konteinerį. Mums svarbiau yra pačios paslaugos prieinamumas: ką daro šis konteinerių rinkinys. Tai keičia stebėjimo metodus.

2014–2015 metais klestėjo „Docker“ – technologija, apie kurią dabar kalbėsime.

„Docker“ pakeitė filosofiją ir standartizavo programų pakuotę. Naudodami „Docker“ galime supakuoti programą, išsiųsti ją į saugyklą, atsisiųsti iš ten ir įdiegti.

Viską, ko reikia, sudedame į Docker konteinerį, todėl priklausomybės problema išspręsta. „Docker“ garantuoja atkuriamumą. Manau, daug kas susidūrė su neatkuriamumu: tau viskas veikia, nustumi į gamybą, o ten nustoja veikti. Naudojant „Docker“, ši problema išnyksta. Jei jūsų „Docker“ konteineris paleidžiamas ir daro tai, ką turi padaryti, tada labai tikėtina, kad jis pradės gaminti ir darys tą patį.

Nukrypimas apie pridėtines išlaidas

Dėl pridėtinių išlaidų visada kyla ginčų. Kai kurie žmonės mano, kad „Docker“ nekelia papildomos apkrovos, nes naudoja „Linux“ branduolį ir visus jo procesus, reikalingus konteinerizavimui. Pavyzdžiui, „jei sakote, kad „Docker“ yra virš galvos, tada „Linux“ branduolys yra virš galvos.

Kita vertus, jei pasigilinsite, „Docker“ iš tikrųjų yra keletas dalykų, kuriuos galima sakyti, kad jie yra virš galvos.

Pirmoji yra PID vardų erdvė. Kai įdedame procesą į vardų erdvę, jam priskiriamas PID 1. Tuo pačiu metu šis procesas turi kitą PID, esantį pagrindinio kompiuterio vardų erdvėje, už konteinerio ribų. Pavyzdžiui, mes paleidome Nginx konteineryje, jis tapo PID 1 (pagrindinis procesas). O pagrindiniame kompiuteryje jis turi PID 12623. Ir sunku pasakyti, kiek tai yra pridėtinės išlaidos.

Antras dalykas yra C grupės. Paimkime Cgrupes pagal atmintį, tai yra galimybę apriboti konteinerio atmintį. Kai jis įjungtas, aktyvuojami skaitikliai ir atminties apskaita: branduolys turi suprasti, kiek puslapių šiam konteineriui skirta ir kiek dar laisvų. Galbūt tai yra pridėtinės išlaidos, bet aš nemačiau jokių tikslių tyrimų, kaip tai paveiktų našumą. Ir aš pats nepastebėjau, kad „Docker“ veikiančios programos našumas staiga smarkiai sumažėjo.

Ir dar viena pastaba apie pasirodymą. Kai kurie branduolio parametrai perduodami iš pagrindinio kompiuterio į konteinerį. Visų pirma, kai kurie tinklo parametrai. Todėl, jei norite, pavyzdžiui, „Docker“ paleisti ką nors didelio našumo, ką nors, kas aktyviai naudos tinklą, bent jau turite pakoreguoti šiuos parametrus. Pavyzdžiui, kai kurie nf_conntrack.

Apie Docker koncepciją

Docker susideda iš kelių komponentų:

  1. „Docker Daemon“ yra tas pats konteinerio variklis; paleidžia konteinerius.
  2. „Docker CII“ yra „Docker“ valdymo priemonė.
  3. Dockerfile – instrukcijos, kaip sukurti vaizdą.
  4. Vaizdas – vaizdas, iš kurio išvyniojamas konteineris.
  5. Konteineris.
  6. Docker registras yra vaizdų saugykla.

Schematiškai tai atrodo maždaug taip:

Kas yra Docker: trumpa ekskursija į istoriją ir pagrindines abstrakcijas

„Docker“ demonas veikia „Docker_host“ ir paleidžia konteinerius. Yra Klientas, kuris siunčia komandas: sukurkite vaizdą, atsisiųskite vaizdą, paleiskite konteinerį. „Docker“ demonas eina į registrą ir juos vykdo. „Docker“ klientas gali pasiekti tiek lokaliai (prie „Unix“ lizdo), tiek per TCP iš nuotolinio pagrindinio kompiuterio.

Peržiūrėkime kiekvieną komponentą.

Docker demonas - tai yra serverio dalis, ji veikia pagrindiniame kompiuteryje: atsisiunčia vaizdus ir paleidžia iš jų konteinerius, sukuria tinklą tarp konteinerių, renka žurnalus. Kai sakome „sukurti įvaizdį“, demonas taip pat daro tai.

Docker CLI — Docker kliento dalis, konsolės įrankis darbui su demonu. Pasikartosiu, jis gali veikti ne tik lokaliai, bet ir tinkle.

Pagrindinės komandos:

docker ps – rodyti konteinerius, kurie šiuo metu veikia Docker pagrindiniame kompiuteryje.
docker images – rodyti vaizdus, ​​atsisiųstus vietoje.
docker paieška <> – ieškokite vaizdo registre.
docker pull <> – atsisiųskite vaizdą iš registro į kompiuterį.
dokeris statyti < > - rinkti vaizdą.
docker run <> – paleiskite konteinerį.
docker rm <> – išimkite konteinerį.
docker logs <> - konteinerių rąstai
docker start/stop/restart <> – darbas su konteineriu

Jei įvaldote šias komandas ir esate įsitikinę, kad jas naudosite, manykite, kad esate 70% įvaldęs Docker vartotojo lygiu.

dockerfile - vaizdo kūrimo instrukcijos. Beveik kiekviena komandų komanda yra naujas sluoksnis. Pažiūrėkime į pavyzdį.

Kas yra Docker: trumpa ekskursija į istoriją ir pagrindines abstrakcijas

Taip atrodo Dockerfile: komandos kairėje, argumentai dešinėje. Kiekviena čia esanti komanda (ir paprastai parašyta „Dockerfile“) sukuria naują sluoksnį „Image“.

Net pažvelgus į kairę pusę galima apytiksliai suprasti, kas vyksta. Mes sakome: „sukurkite mums aplanką“ – tai vienas sluoksnis. „Padaryti aplanką veikiantį“ yra kitas sluoksnis ir pan. Sluoksnis tortas palengvina gyvenimą. Jei sukursiu kitą „Dockerfile“ ir ką nors pakeisiu paskutinėje eilutėje – paleidžiu ką nors kita nei „python“ „main.py“ arba įdiegiu priklausomybes iš kito failo – ankstesni sluoksniai bus pakartotinai naudojami kaip talpykla.

vaizdas - tai konteinerių pakuotė; konteineriai paleidžiami iš paveikslėlio. Jei pažvelgtume į Docker paketų tvarkyklės požiūriu (tarsi dirbtume su deb arba rpm paketais), vaizdas iš esmės yra rpm paketas. Naudodami „yum“ diegimą galime įdiegti programą, ją ištrinti, rasti saugykloje ir atsisiųsti. Čia maždaug tas pats: konteineriai paleidžiami iš vaizdo, jie saugomi Docker registre (panašiai kaip yum, saugykloje), o kiekvienas vaizdas turi SHA-256 maišą, pavadinimą ir žymą.

Vaizdas sukurtas pagal Dockerfile instrukcijas. Kiekviena „Dockerfile“ instrukcija sukuria naują sluoksnį. Sluoksniai gali būti naudojami pakartotinai.

Docker registras yra „Docker“ vaizdų saugykla. Panašiai kaip OS, Docker turi viešą standartinį registrą – dockerhub. Bet jūs galite sukurti savo saugyklą, savo Docker registrą.

Konteineris - kas paleidžiama iš vaizdo. Sukūrėme vaizdą pagal instrukcijas iš Dockerfile, tada paleidžiame jį iš šio vaizdo. Šis konteineris yra atskirtas nuo kitų talpyklų ir jame turi būti viskas, ko reikia, kad programa veiktų. Šiuo atveju vienas konteineris – vienas procesas. Taip atsitinka, kad turite atlikti du procesus, tačiau tai šiek tiek prieštarauja Docker ideologijai.

Reikalavimas „vienas konteineris, vienas procesas“ yra susijęs su PID vardų erdve. Kai vardų erdvėje prasideda procesas su PID 1, jei jis staiga miršta, miršta ir visas konteineris. Jei ten vyksta du procesai: vienas gyvas, o kitas miręs, konteineris vis tiek gyvuos. Bet tai yra geriausios praktikos klausimas, apie tai kalbėsime kitose medžiagose.

Norėdami išsamiau ištirti kurso ypatybes ir visą programą, spustelėkite nuorodą: “Docker vaizdo kursas".

Autorius: Marcel Ibraev, sertifikuotas Kubernetes administratorius, Southbridge praktikuojantis inžinierius, pranešėjas ir Slurm kursų kūrėjas.

Šaltinis: www.habr.com

Добавить комментарий