Töötab süsteemselt konteineris

Oleme systemd konteinerites kasutamise teemat jälginud juba pikemat aega. 2014. aastal kirjutas meie turvainsener Daniel Walsh artikli Süsteem töötab Dockeri konteineris, ja paar aastat hiljem - teine, mida kutsuti Süsteem töötab mitteprivilegeeritud konteineris, milles ta väitis, et olukord pole palju paremaks läinud. Eelkõige kirjutas ta, et "kahjuks isegi kaks aastat hiljem, kui googeldada "Docker system", on esimene asi, mis ilmub tema sama vana artikkel. Seega on aeg midagi muuta." Lisaks oleme juba rääkinud konflikt Dockeri ja süsteemsete arendajate vahel.

Töötab süsteemselt konteineris

Selles artiklis näitame, mis on aja jooksul muutunud ja kuidas Podman saab meid selles küsimuses aidata.

Süsteemi konteineris käitamiseks on palju põhjuseid, näiteks:

  1. Multiserver konteinerid – Paljud inimesed tahavad oma multiteenusrakendused virtuaalmasinatest välja tõmmata ja konteinerites käitada. Muidugi oleks parem jagada sellised rakendused mikroteenusteks, kuid kõik ei tea, kuidas seda veel teha või lihtsalt pole aega. Seetõttu on selliste rakenduste käivitamine teenustena, mille systemd üksusefailidest käivitas, täiesti loogiline.
  2. Süsteemiüksuse failid – Enamik konteinerites töötavaid rakendusi on üles ehitatud koodist, mis varem töötas virtuaalsetes või füüsilistes masinates. Nendel rakendustel on nende rakenduste jaoks kirjutatud ühikfail ja see mõistab, kuidas neid tuleks käivitada. Seega on ikkagi parem alustada teenuseid toetatud meetoditega, selle asemel, et häkkida oma algteenust.
  3. Systemd on protsessijuht. See haldab teenuseid (lülitub välja, taaskäivitab teenuseid või tapab zombiprotsesse) paremini kui ükski teine ​​tööriist.

Sellegipoolest on palju põhjusi, miks süsteemi konteinerites mitte käivitada. Peamine on see, et systemd/journald kontrollib konteinerite ja selliste tööriistade väljundit Kubernetes või avatud vahetus eeldavad, et konteinerid kirjutavad logi otse stdout ja stderr. Seega, kui kavatsete konteinereid hallata ülalmainitud orkestreerimistööriistade abil, peaksite tõsiselt kaaluma systemd-põhiste konteinerite kasutamist. Lisaks on Dockeri ja Moby arendajad sageli olnud tugevalt vastu systemd'i kasutamisele konteinerites.

Podmani tulek

Meil on hea meel teatada, et olukord on lõpuks edasi liikunud. Red Hati konteinerite käitamise eest vastutav meeskond otsustas areneda oma konteineri mootor. Ta sai nime podman ja pakub sama käsurea liidest (CLI) nagu Docker. Ja peaaegu kõiki Dockeri käske saab Podmanis kasutada samamoodi. Tihti viime läbi seminare, mida nüüd nimetatakse nn Dockeri vahetamine Podmani vastu, ja kõige esimene slaid nõuab kirjutamist: alias docker=podman.

Paljud inimesed teevad seda.

Minu Podman ja mina ei ole kuidagi süsteemipõhiste konteinerite vastu. Lõppude lõpuks on Systemd kõige sagedamini kasutatav Linuxi initi alamsüsteem ja kui ta ei lase sellel konteinerites korralikult töötada, siis eiratakse seda, kuidas tuhanded inimesed on konteinerite käitamisega harjunud.

Podman teab, mida teha, et süsteem konteineris korralikult töötaks. See vajab selliseid asju nagu tmpfs-i paigaldamine /run ja /tmp. Talle meeldib, kui "konteinerite" keskkond on lubatud ja ta ootab oma cgroupi kataloogi osale ja kausta /var/log/journald kirjutamisõigusi.

Kui käivitate konteineri, milles esimene käsk on init või systemd, konfigureerib Podman automaatselt tmpfs ja Cgroups, et tagada systemd probleemideta käivitumine. Selle automaatse käivitamise režiimi blokeerimiseks kasutage suvandit --systemd=false. Pange tähele, et Podman kasutab systemd-režiimi ainult siis, kui ta näeb, et see peab käivitama käsu systemd või init.

Siin on väljavõte juhendist:

mees podman jooksma
...

–systemd=true|false

Konteineri käitamine süsteemses režiimis. Vaikimisi lubatud.

Kui käivitate konteineris käsu systemd või init, konfigureerib Podman tmpfs-i ühenduspunktid järgmistes kataloogides:

/run, /run/lock, /tmp, /sys/fs/cgroup/systemd, /var/lib/journal

Samuti on vaikimisi seiskamissignaal SIGRTMIN+3.

Kõik see võimaldab süsteemil töötada suletud konteineris ilma muudatusteta.

MÄRKUS. Systemd üritab kirjutada failisüsteemi cgroup. Kuid SELinux takistab konteineritel seda vaikimisi tegemast. Kirjutamise lubamiseks lubage tõeväärtusparameeter container_manage_cgroup:

setsebool -P konteineri_haldus_cgroup true

Nüüd vaadake, kuidas Dockerfile välja näeb, et käitada Systemd konteineris Podmani abil:

# cat Dockerfile

FROM fedora

RUN dnf -y install httpd; dnf clean all; systemctl enable httpd

EXPOSE 80

CMD [ "/sbin/init" ]

See on kõik.

Nüüd paneme konteineri kokku:

# podman build -t systemd .

Me käsime SELinuxil lubada systemdil muuta Cgroupsi konfiguratsiooni:

# setsebool -P container_manage_cgroup true

Muide, paljud inimesed unustavad selle sammu. Õnneks tuleb seda teha vaid üks kord ja säte salvestatakse peale süsteemi taaskäivitamist.

Nüüd käivitame konteineri:

# podman run -ti -p 80:80 systemd

systemd 239 running in system mode. (+PAM +AUDIT +SELINUX +IMA -APPARMOR +SMACK +SYSVINIT +UTMP +LIBCRYPTSETUP +GCRYPT +GNUTLS +ACL +XZ +LZ4 +SECCOMP +BLKID +ELFUTILS +KMOD +IDN2 -IDN +PCRE2 default-hierarchy=hybrid)

Detected virtualization container-other.

Detected architecture x86-64.

Welcome to Fedora 29 (Container Image)!

Set hostname to <1b51b684bc99>.

Failed to install release agent, ignoring: Read-only file system

File /usr/lib/systemd/system/systemd-journald.service:26 configures an IP firewall (IPAddressDeny=any), but the local system does not support BPF/cgroup based firewalling.

Proceeding WITHOUT firewalling in effect! (This warning is only shown for the first loaded unit using IP firewalling.)

[  OK ] Listening on initctl Compatibility Named Pipe.

[  OK ] Listening on Journal Socket (/dev/log).

[  OK ] Started Forward Password Requests to Wall Directory Watch.

[  OK ] Started Dispatch Password Requests to Console Directory Watch.

[  OK ] Reached target Slices.

…

[  OK ] Started The Apache HTTP Server.

See on kõik, teenus on valmis ja töötab:

$ curl localhost

<html  xml_lang="en" lang="en">

…

</html>

MÄRKUS. Ärge proovige seda Dockeris! Seal tuleb ikka parmupilliga tantsida, et selliseid konteinereid deemoni kaudu käivitada. (Selle kõige sujuvamaks toimimiseks Dockeris on vaja lisavälju ja -pakette või tuleb seda käitada privilegeeritud konteineris. Üksikasju vt siit.)

Veel paar lahedat asja Podmani ja systemdi kohta

Podman töötab süsteemiüksuse failides paremini kui Docker

Kui konteinerid tuleb süsteemi algkäivitamisel käivitada, saate lihtsalt sisestada süsteemiüksuse faili vastavad Podmani käsud, mis käivitavad teenuse ja jälgivad seda. Podman kasutab standardset fork-exec mudelit. Teisisõnu, konteinerprotsessid on Podmani protsessi lapsed, nii et systemd saab neid hõlpsalt jälgida.

Docker kasutab klient-serveri mudelit ja Dockeri CLI-käske saab paigutada ka otse üksusefaili. Kuid kui Dockeri klient loob ühenduse Dockeri deemoniga, muutub see (klient) lihtsalt üheks protsessiks, mis haldab stdini ja stdouti. Süsteemil pole omakorda aimu Dockeri kliendi ja Dockeri deemoni kontrolli all töötava konteineri vahelisest ühendusest ning seetõttu ei saa systemd selle mudeli raames teenust põhimõtteliselt jälgida.

Süsteemi aktiveerimine pistikupesa kaudu

Podman käsitleb pesa kaudu aktiveerimist õigesti. Kuna Podman kasutab mudelit fork-exec, saab see pesa edastada oma alamkonteineri protsessidele. Docker ei saa seda teha, kuna kasutab klient-serveri mudelit.

Varlinki teenus, mida Podman kasutab kaugklientidega konteineritesse suhtlemiseks, aktiveeritakse tegelikult pistikupesa kaudu. Cockpit-podmani pakett, mis on kirjutatud Node.js-is ja osa kokpitiprojektist, võimaldab inimestel veebiliidese kaudu Podmani konteineritega suhelda. Cockpit-podmani käivitav veebideemon saadab teated varlinki pesasse, mida systemd kuulab. Seejärel aktiveerib Systemd Podmani programmi, et saada sõnumeid ja alustada konteinerite haldamist. Systemd aktiveerimine pesa kaudu välistab kaug-API juurutamisel vajaduse pidevalt töötava deemoni järele.

Lisaks töötame välja teist Podmani klienti nimega podman-remote, mis rakendab sama Podmani CLI-d, kuid kutsub konteinerite käitamiseks välja varlinki. Podman-remote saab töötada SSH-seansside peal, võimaldades teil turvaliselt suhelda erinevate masinate konteineritega. Aja jooksul kavatseme lubada podman-remote'i toetada MacOS-i ja Windowsi koos Linuxiga, et nende platvormide arendajad saaksid käitada Linuxi virtuaalmasinat, milles töötab Podman varlink, ja saada täielikku kogemust, et konteinerid töötavad kohalikus masinas.

SD_NOTIFY

Systemd võimaldab abiteenuste käivitamist edasi lükata seni, kuni käivitub nende jaoks vajalik konteinerteenus. Podman saab SD_NOTIFY-pesa edastada konteinerteenusele, nii et teenus teavitab süsteemi, et see on töövalmis. Ja jällegi, klient-serveri mudelit kasutav Docker ei saa seda teha.

Plaanides

Plaanime lisada käsu podman generate systemd CONTAINERID, mis genereerib systemd üksuse faili konkreetse määratud konteineri haldamiseks. See peaks töötama mitteprivilegeeritud konteinerite puhul nii juur- kui ka juureta režiimis. Oleme isegi näinud taotlust OCI-ga ühilduva systemd-nspawn käitusaja loomiseks.

Järeldus

Systemd konteineris töötamine on arusaadav vajadus. Ja tänu Podmanile on meil lõpuks konteineri käitusaeg, mis ei ole vastuolus systemd-iga, kuid muudab selle kasutamise lihtsaks.

Allikas: www.habr.com

Lisa kommentaar