Šta je Docker: kratak izlet u istoriju i osnovne apstrakcije

Počelo 10. avgusta u Slurmu Docker video kurs, u kojem ga u potpunosti analiziramo - od osnovnih apstrakcija do mrežnih parametara.

U ovom članku ćemo govoriti o istoriji Docker-a i njegovim glavnim apstrakcijama: Image, Cli, Dockerfile. Predavanje je namenjeno početnicima, pa je malo verovatno da će biti interesantno iskusnim korisnicima. Neće biti krvi, slijepog crijeva ili dubokog uranjanja. Same osnove.

Šta je Docker: kratak izlet u istoriju i osnovne apstrakcije

Šta je Docker

Pogledajmo definiciju Dockera sa Wikipedije.

Docker je softver za automatizaciju implementacije i upravljanja aplikacijama u kontejnerskim okruženjima.

Iz ove definicije ništa nije jasno. Posebno je nejasno šta znači "u okruženjima koja podržavaju kontejnerizaciju". Da saznamo, vratimo se u prošlost. Počnimo s erom koju konvencionalno nazivam "monolitnom erom".

Monolitno doba

Monolitna era je početkom 2000-ih, kada su sve aplikacije bile monolitne, sa gomilom zavisnosti. Razvoj je trajao dugo. Istovremeno, nije bilo mnogo servera, svi smo ih poznavali po imenu i pratili ih. Postoji tako smiješno poređenje:

Kućni ljubimci su domaće životinje. U monolitnoj eri, tretirali smo naše servere kao kućne ljubimce, njegovane i njegovane, otpuhujući trunke prašine. A za bolje upravljanje resursima koristili smo virtuelizaciju: uzeli smo server i izrezali ga na nekoliko virtuelnih mašina, čime smo obezbedili izolaciju okruženja.

Virtualizacijski sistemi bazirani na hipervizoru

Svi su vjerovatno čuli za sisteme virtuelizacije: VMware, VirtualBox, Hyper-V, Qemu KVM, itd. Oni pružaju izolaciju aplikacija i upravljanje resursima, ali imaju i nedostatke. Za virtuelizaciju vam je potreban hipervizor. A hipervizor je glavni resurs. A sama virtuelna mašina je obično čitav kolos - teška slika koja sadrži operativni sistem, Nginx, Apache i možda MySQL. Slika je velika i virtuelna mašina je nezgodna za rad. Kao rezultat toga, rad sa virtuelnim mašinama može biti spor. Da bi se riješio ovaj problem, kreirani su sistemi virtuelizacije na nivou kernela.

Sistemi virtuelizacije na nivou kernela

Virtuelizaciju na nivou kernela podržavaju OpenVZ, Systemd-nspawn, LXC sistemi. Upečatljiv primjer takve virtualizacije je LXC (Linux Containers).

LXC je sistem virtuelizacije na nivou operativnog sistema za pokretanje više izolovanih instanci Linux operativnog sistema na jednom čvoru. LXC ne koristi virtuelne mašine, već stvara virtuelno okruženje sa sopstvenim procesnim prostorom i mrežnim stekom.

U suštini LXC stvara kontejnere. Koja je razlika između virtuelnih mašina i kontejnera?

Šta je Docker: kratak izlet u istoriju i osnovne apstrakcije

Kontejner nije pogodan za izolaciju procesa: ranjivosti se nalaze u virtuelizacijskim sistemima na nivou kernela koje im omogućavaju da pobjegnu iz kontejnera na host. Stoga, ako trebate nešto izolirati, bolje je koristiti virtuelnu mašinu.

Razlike između virtualizacije i kontejnerizacije mogu se vidjeti na dijagramu.
Postoje hardverski hipervizori, hipervizori na vrhu OS-a i kontejneri.

Šta je Docker: kratak izlet u istoriju i osnovne apstrakcije

Hardverski hipervizori su cool ako stvarno želite nešto izolirati. Zato što je moguće izolovati na nivou memorijskih stranica i procesora.

Postoje hipervizori kao program, a postoje i kontejneri i o njima ćemo dalje. Sistemi za kontejnerizaciju nemaju hipervizor, ali postoji Container Engine koji kreira kontejnere i upravlja njima. Ova stvar je lakša, tako da zbog rada sa jezgrom ima manje troškova ili ih uopšte nema.

Šta se koristi za kontejnerizaciju na nivou kernela

Glavne tehnologije koje vam omogućavaju da kreirate kontejner izolovan od drugih procesa su prostori imena i kontrolne grupe.

Prostori imena: PID, Networking, Mount i User. Ima ih još, ali radi lakšeg razumijevanja fokusirat ćemo se na ove.

PID Imenski prostor ograničava procese. Kada, na primjer, kreiramo PID Namespace i tamo smjestimo proces, on postaje sa PID-om 1. Obično je u sistemima PID 1 systemd ili init. U skladu s tim, kada proces postavimo u novi prostor imena, on također prima PID 1.

Mrežni nazivni prostor vam omogućava da ograničite/izolirate mrežu i postavite vlastita sučelja unutra. Montiranje je ograničenje sistema datoteka. Korisnik—ograničenje za korisnike.

Kontrolne grupe: Memorija, CPU, IOPS, Mreža - oko 12 postavki ukupno. Inače se nazivaju i Cgrupe (“C-grupe”).

Kontrolne grupe upravljaju resursima za kontejner. Preko kontrolnih grupa možemo reći da kontejner ne bi trebao trošiti više od određene količine resursa.

Da bi kontejnerizacija funkcionirala u potpunosti, koriste se dodatne tehnologije: Mogućnosti, Copy-on-write i druge.

Sposobnosti su kada kažemo procesu šta može, a šta ne može. Na nivou kernela, ovo su jednostavno bitmape sa mnogo parametara. Na primjer, root korisnik ima pune privilegije i može sve. Vremenski server može promijeniti sistemsko vrijeme: ima mogućnosti na Time Capsule, i to je to. Koristeći privilegije, možete fleksibilno konfigurirati ograničenja za procese i tako se zaštititi.

Sistem Copy-on-write nam omogućava da radimo sa Docker slikama i da ih efikasnije koristimo.

Docker trenutno ima problema s kompatibilnošću sa Cgroups v2, tako da se ovaj članak posebno fokusira na Cgroups v1.

Ali vratimo se istoriji.

Kada su se virtualizacijski sistemi pojavili na nivou kernela, počeli su se aktivno koristiti. Nestali su problemi na hipervizoru, ali su ostali problemi:

  • velike slike: guraju operativni sistem, biblioteke, gomilu različitog softvera u isti OpenVZ, a na kraju slika i dalje ispada prilično velika;
  • Ne postoji normalan standard za pakovanje i isporuku, tako da ostaje problem zavisnosti. Postoje situacije kada dva dijela koda koriste istu biblioteku, ali s različitim verzijama. Može doći do sukoba među njima.

Za rješavanje svih ovih problema došlo je sljedeće doba.

Kontejnerska era

Kada je nastupila era kontejnera, promijenila se filozofija rada s njima:

  • Jedan proces - jedan kontejner.
  • Isporučujemo sve zavisnosti koje su potrebne procesu u njegov kontejner. Ovo zahtijeva rezanje monolita u mikroservise.
  • Što je slika manja, to je bolje – manje je mogućih ranjivosti, brže se razvija i tako dalje.
  • Slučajevi postaju efemerni.

Sjećate se šta sam rekao o kućnim ljubimcima u odnosu na stoku? Ranije su slučajevi bili poput domaćih životinja, a sada su postali kao stoka. Ranije je postojao monolit - jedna aplikacija. Sada je to 100 mikroservisa, 100 kontejnera. Neki kontejneri mogu imati 2-3 replike. Postaje nam manje važno da kontrolišemo svaki kontejner. Ono što nam je važnije je dostupnost same usluge: šta radi ovaj set kontejnera. Ovo mijenja pristupe praćenju.

U 2014-2015, Docker je procvjetao - tehnologija o kojoj ćemo sada govoriti.

Docker je promijenio filozofiju i standardizirao pakovanje aplikacija. Koristeći Docker, možemo spakovati aplikaciju, poslati je u spremište, preuzeti je odatle i implementirati.

Stavljamo sve što nam treba u Docker kontejner, tako da je problem zavisnosti riješen. Docker garantuje ponovljivost. Mislim da su se mnogi ljudi susreli sa neponovljivošću: sve ti radi, gurneš to u proizvodnju i tamo prestane da radi. Sa Dockerom ovaj problem nestaje. Ako se vaš Docker kontejner pokrene i radi ono što treba, onda će s velikim stepenom vjerovatnoće pokrenuti proizvodnju i učiniti isto tamo.

Digresija o režiji

Uvek postoje sporovi oko režijskih troškova. Neki ljudi vjeruju da Docker ne nosi dodatno opterećenje, jer koristi Linux kernel i sve njegove procese potrebne za kontejnerizaciju. Na primjer, "ako kažete da je Docker prekomjeran, onda je Linux kernel prekomjeran."

S druge strane, ako zađete dublje, u Dockeru zaista postoji nekoliko stvari za koje se, uz natezanje, može reći da su iznad glave.

Prvi je PID imenski prostor. Kada postavimo proces u imenski prostor, on dobija PID 1. U isto vrijeme, ovaj proces ima drugi PID, koji se nalazi na host imenskom prostoru, izvan kontejnera. Na primjer, pokrenuli smo Nginx u kontejneru, postao je PID 1 (master proces). A na hostu ima PID 12623. I teško je reći koliki je to dodatni trošak.

Druga stvar su Cgroups. Uzmimo Cgroups po memoriji, odnosno po mogućnosti ograničavanja memorije kontejnera. Kada je omogućeno, aktiviraju se brojači i obračun memorije: kernel treba da shvati koliko je stranica dodijeljeno i koliko je još slobodnih za ovaj kontejner. Ovo je možda pretjerano, ali nisam vidio nikakve precizne studije o tome kako to utiče na performanse. I lično nisam primijetio da je aplikacija koja radi u Dockeru iznenada doživjela oštar gubitak u performansama.

I još jedna napomena o performansama. Neki parametri kernela se prosleđuju sa hosta na kontejner. Konkretno, neki mrežni parametri. Stoga, ako želite pokrenuti nešto visokih performansi u Dockeru, na primjer, nešto što će aktivno koristiti mrežu, onda barem trebate prilagoditi ove parametre. Neki nf_conntrack, na primjer.

O konceptu Docker

Docker se sastoji od nekoliko komponenti:

  1. Docker Daemon je isti Container Engine; lansira kontejnere.
  2. Docker CII je uslužni program za upravljanje Dockerom.
  3. Dockerfile - upute o tome kako napraviti sliku.
  4. Slika — slika iz koje se izvlači kontejner.
  5. Kontejner.
  6. Docker registar je spremište slika.

Šematski to izgleda otprilike ovako:

Šta je Docker: kratak izlet u istoriju i osnovne apstrakcije

Docker daemon radi na Docker_host i pokreće kontejnere. Postoji klijent koji šalje komande: napravite sliku, preuzmite sliku, pokrenite kontejner. Docker daemon ide u registar i izvršava ih. Docker klijent može pristupiti i lokalno (u Unix socket) i preko TCP-a sa udaljenog hosta.

Idemo kroz svaku komponentu.

Docker daemon - ovo je serverski dio, radi na host stroju: preuzima slike i pokreće kontejnere iz njih, stvara mrežu između kontejnera, prikuplja zapise. Kada kažemo „napravi sliku“, demon to takođe radi.

Docker CLI — Docker klijentski dio, konzolni uslužni program za rad sa demonom. Ponavljam, može raditi ne samo lokalno, već i preko mreže.

Osnovne naredbe:

docker ps - prikaži kontejnere koji se trenutno izvode na Docker hostu.
docker slike - prikazuju slike preuzete lokalno.
docker search <> - traži sliku u registru.
docker pull <> - preuzimanje slike iz registra na mašinu.
docker build < > - prikupi sliku.
docker run <> - pokretanje kontejnera.
docker rm <> - uklonite kontejner.
docker logs <> - dnevnici kontejnera
docker start/stop/restart <> - rad sa kontejnerom

Ako savladate ove komande i sigurni ste u njihovu upotrebu, smatrajte da ste 70% iskusni u Dockeru na korisničkom nivou.

dockerfile - upute za kreiranje slike. Gotovo svaka naredba instrukcija je novi sloj. Pogledajmo primjer.

Šta je Docker: kratak izlet u istoriju i osnovne apstrakcije

Ovako izgleda Dockerfile: komande na lijevoj strani, argumenti na desnoj strani. Svaka naredba koja je ovdje (i općenito napisana u Dockerfile-u) stvara novi sloj u Image.

Čak i ako pogledate lijevu stranu, možete otprilike razumjeti šta se dešava. Kažemo: „kreirajte fasciklu za nas“ - ovo je jedan sloj. „Neka fascikla radi“ je još jedan sloj i tako dalje. Layer cake olakšava život. Ako kreiram još jedan Dockerfile i promijenim nešto u posljednjem redu – pokrenem nešto drugo osim “python” “main.py” ili instaliram zavisnosti iz druge datoteke – tada će se prethodni slojevi ponovo koristiti kao keš memorija.

slika - ovo je pakiranje kontejnera, kontejneri se pokreću sa slike. Ako posmatramo Docker sa stanovišta menadžera paketa (kao da radimo sa deb ili rpm paketima), onda je slika u suštini rpm paket. Kroz yum install možemo instalirati aplikaciju, obrisati je, pronaći je u spremištu i preuzeti. Ovdje je otprilike isto: kontejneri se pokreću sa slike, pohranjuju se u Docker registar (slično kao yum, u spremištu), a svaka slika ima SHA-256 hash, ime i oznaku.

Slika je napravljena prema uputama iz Dockerfile-a. Svaka instrukcija iz Dockerfile-a stvara novi sloj. Slojevi se mogu ponovo koristiti.

Docker registar je Docker spremište slika. Slično OS-u, Docker ima javni standardni registar - dockerhub. Ali možete napraviti svoje vlastito spremište, svoj vlastiti Docker registar.

kontejner - šta se pokreće sa slike. Napravili smo sliku prema uputama iz Dockerfile-a, a zatim je pokrećemo sa ove slike. Ovaj kontejner je izoliran od drugih kontejnera i mora sadržavati sve što je potrebno da bi aplikacija funkcionirala. U ovom slučaju, jedan kontejner - jedan proces. Dešava se da morate obaviti dva procesa, ali to je donekle suprotno Docker ideologiji.

Zahtjev "jedan kontejner, jedan proces" povezan je s prostorom imena PID. Kada proces sa PID-om 1 započne u Namespaceu, ako iznenada umre, umire i cijeli kontejner. Ako tamo rade dva procesa: jedan je živ, a drugi mrtav, kontejner će i dalje nastaviti živjeti. Ali ovo je pitanje najboljih praksi, o njima ćemo govoriti u drugim materijalima.

Da biste detaljnije proučili karakteristike i kompletan program kursa, slijedite link: “Docker video kurs".

Autor: Marcel Ibraev, certificirani Kubernetes administrator, praktičan inženjer u Southbridgeu, govornik i programer Slurm kurseva.

izvor: www.habr.com

Dodajte komentar