Jaki jest urok rozdzielenia środowiska wykonawczego kontenera na osobne komponenty narzędzi? W szczególności narzędzia te można zacząć łączyć, aby wzajemnie się chroniły.
Wiele osób przyciąga pomysł budowania w nich kontenerowych obrazów OCI
Dlatego ludzie ciągle próbują uruchomić Buildah w kontenerze. Krótko mówiąc, stworzyliśmy
regulacja
Obrazy te są zbudowane z plików Dockerfiles, które można znaleźć w repozytorium Buildah w folderze
Tutaj przyjrzymy się
# stable/Dockerfile
#
# Build a Buildah container image from the latest
# stable version of Buildah on the Fedoras Updates System.
# https://bodhi.fedoraproject.org/updates/?search=buildah
# This image can be used to create a secured container
# that runs safely with privileges within the container.
#
FROM fedora:latest
# Don't include container-selinux and remove
# directories used by dnf that are just taking
# up space.
RUN yum -y install buildah fuse-overlayfs --exclude container-selinux; rm -rf /var/cache /var/log/dnf* /var/log/yum.*
# Adjust storage.conf to enable Fuse storage.
RUN sed -i -e 's|^#mount_program|mount_program|g' -e '/additionalimage.*/a "/var/lib/shared",' /etc/containers/storage.conf
Zamiast OverlayFS, zaimplementowanego na poziomie jądra Linuksa hosta, używamy programu znajdującego się wewnątrz kontenera
podman run --device /dev/fuse quay.io/buildahctr ...
RUN mkdir -p /var/lib/shared/overlay-images /var/lib/shared/overlay-layers; touch /var/lib/shared/overlay-images/images.lock; touch /var/lib/shared/overlay-layers/layers.lock
Następnie tworzymy katalog na dodatkową pamięć.
# Set up environment variables to note that this is
# not starting with user namespace and default to
# isolate the filesystem with chroot.
ENV _BUILDAH_STARTED_IN_USERNS="" BUILDAH_ISOLATION=chroot
Na koniec, używając zmiennej środowiskowej BUILDAH_ISOLATION, nakazujemy kontenerowi Buildah, aby domyślnie działał z izolacją chroot. Dodatkowa izolacja nie jest tutaj wymagana, ponieważ pracujemy już w kontenerze. Aby Buildah mógł tworzyć własne kontenery oddzielone przestrzenią nazw, wymagane jest uprawnienie SYS_ADMIN, co wymagałoby złagodzenia reguł SELinux i SECCOMP kontenera, co jest sprzeczne z naszą preferencją budowania z bezpiecznego kontenera.
Uruchamianie Buildaha w kontenerze
Omówiony powyżej diagram obrazu kontenera Buildah pozwala elastycznie różnicować sposoby uruchamiania takich kontenerów.
Szybkość kontra bezpieczeństwo
Bezpieczeństwo komputera jest zawsze kompromisem pomiędzy szybkością procesu a poziomem ochrony, jaki jest wokół niego owinięty. To stwierdzenie odnosi się również do montażu kontenerów, dlatego poniżej rozważymy opcje takiego kompromisu.
Omówiony powyżej obraz kontenera będzie przechowywany w /var/lib/containers. Dlatego musimy zamontować zawartość w tym folderze, a sposób, w jaki to zrobimy, będzie miał ogromny wpływ na szybkość tworzenia obrazów kontenerów.
Rozważmy trzy opcje.
Opcja 1. Jeśli wymagane jest maksymalne bezpieczeństwo, dla każdego kontenera możesz utworzyć własny folder dla kontenerów/obrazu i podłączyć go do kontenera poprzez montowanie woluminów. Poza tym umieść katalog kontekstowy w samym kontenerze, w folderze /build:
# mkdir /var/lib/containers1
# podman run -v ./build:/build:z -v /var/lib/containers1:/var/lib/containers:Z quay.io/buildah/stable
buildah -t image1 bud /build
# podman run -v /var/lib/containers1:/var/lib/containers:Z quay.io/buildah/stable buildah push image1 registry.company.com/myuser
# rm -rf /var/lib/containers1
Bezpieczeństwa. Buildah działający w takim kontenerze charakteryzuje się maksymalnym bezpieczeństwem: nie ma żadnych uprawnień roota do korzystania z możliwości, a obowiązują go wszystkie ograniczenia SECOMP i SELinux.Taki kontener można nawet uruchomić z izolacją przestrzeni nazw użytkownika, dodając opcję typu —uidmap 0: 100000 10000:XNUMX XNUMX.
Wydajność. Ale wydajność tutaj jest minimalna, ponieważ wszelkie obrazy z rejestrów kontenerów są za każdym razem kopiowane do hosta, a buforowanie w ogóle nie działa. Po zakończeniu swojej pracy kontener Buildah musi wysłać obraz do rejestru i zniszczyć zawartość na hoście. Następnym razem, gdy obraz kontenera zostanie zbudowany, trzeba będzie go ponownie pobrać z rejestru, ponieważ do tego czasu na hoście nie będzie już nic.
Opcja 2. Jeśli potrzebujesz wydajności na poziomie platformy Docker, możesz zamontować kontener/magazyn hosta bezpośrednio w kontenerze.
# podman run -v ./build:/build:z -v /var/lib/containers:/var/lib/containers --security-opt label:disabled quay.io/buildah/stable buildah -t image2 bud /build
# podman run -v /var/lib/containers:/var/lib/containers --security-opt label:disabled quay.io/buildah/stable buildah push image2 registry.company.com/myuser
Bezpieczeństwa. Jest to najmniej bezpieczny sposób budowania kontenerów, ponieważ pozwala kontenerowi modyfikować pamięć na hoście i może potencjalnie dostarczyć Podmanowi lub CRI-O złośliwy obraz. Ponadto będziesz musiał wyłączyć separację SELinux, aby procesy w kontenerze Buildah mogły wchodzić w interakcję z pamięcią masową na hoście. Należy pamiętać, że ta opcja jest nadal lepsza niż gniazdo Docker, ponieważ kontener jest zablokowany przez pozostałe funkcje zabezpieczeń i nie można po prostu uruchomić kontenera na hoście.
Wydajność. Tutaj jest maksymalna, ponieważ buforowanie jest w pełni wykorzystane. Jeśli Podman lub CRI-O pobrał już wymagany obraz na hosta, to proces Buildah wewnątrz kontenera nie będzie musiał pobierać go ponownie, a kolejne kompilacje oparte na tym obrazie również będą mogły pobrać to, czego potrzebują z pamięci podręcznej .
Opcja 3. Istotą tej metody jest połączenie kilku obrazów w jeden projekt ze wspólnym folderem na obrazy kontenerowe.
# mkdir /var/lib/project3
# podman run --security-opt label_level=s0:C100, C200 -v ./build:/build:z
-v /var/lib/project3:/var/lib/containers:Z quay.io/buildah/stable buildah -t image3 bud /build
# podman run --security-opt label_level=s0:C100, C200
-v /var/lib/project3:/var/lib/containers quay.io/buildah/stable buildah push image3 registry.company.com/myuser
W tym przykładzie nie usuwamy folderu projektu (/var/lib/project3) pomiędzy uruchomieniami, więc wszystkie kolejne kompilacje w ramach projektu korzystają z buforowania.
Bezpieczeństwa. Coś pomiędzy opcjami 1 i 2. Z jednej strony kontenery nie mają dostępu do treści na hoście i w związku z tym nie mogą wrzucić czegoś złego do magazynu obrazów Podman/CRI-O. Z drugiej strony kontener ze względu na swoją konstrukcję może kolidować z montażem innych kontenerów.
Wydajność. Tutaj jest gorzej niż w przypadku korzystania ze współdzielonej pamięci podręcznej na poziomie hosta, ponieważ nie można używać obrazów, które zostały już pobrane za pomocą Podmana/CRI-O. Jednak gdy Buildah pobierze obraz, będzie można go wykorzystać w kolejnych kompilacjach projektu.
Dodatkowe miejsce do przechowywania
У
Jeśli przewiniesz w górę i spojrzysz na plik Dockerfile, którego używamy do zbudowania obrazu quay.io/buildah/stable, znajdziesz tam takie linie:
# Adjust storage.conf to enable Fuse storage.
RUN sed -i -e 's|^#mount_program|mount_program|g' -e '/additionalimage.*/a "/var/lib/shared",' /etc/containers/storage.conf
RUN mkdir -p /var/lib/shared/overlay-images /var/lib/shared/overlay-layers; touch /var/lib/shared/overlay-images/images.lock; touch /var/lib/shared/overlay-layers/layers.lock
W pierwszej linii modyfikujemy plik /etc/containers/storage.conf wewnątrz obrazu kontenera, informując sterownik pamięci masowej, aby używał „additionalimagestores” w folderze /var/lib/shared. W następnej linii tworzymy folder współdzielony i dodajemy kilka plików blokujących, aby nie było nadużyć w kontenerach/magazynach. Zasadniczo tworzymy po prostu pusty sklep z obrazami kontenerów.
Jeśli zamontujesz kontenery/magazyn na poziomie wyższym niż ten folder, Buildah będzie mógł wykorzystać obrazy.
Wróćmy teraz do omówionej powyżej Opcji 2, kiedy kontener Buildah może czytać i zapisywać do kontenerów/magazynu na hostach i zgodnie z tym ma maksymalną wydajność dzięki buforowaniu obrazów na poziomie Podman/CRI-O, ale zapewnia minimum bezpieczeństwa ponieważ może zapisywać bezpośrednio do pamięci. Dodajmy teraz tutaj dodatkową pamięć i wykorzystajmy to, co najlepsze z obu światów.
# mkdir /var/lib/containers4
# podman run -v ./build:/build:z -v /var/lib/containers/storage:/var/lib/shared:ro -v /var/lib/containers4:/var/lib/containers:Z quay.io/buildah/stable
buildah -t image4 bud /build
# podman run -v /var/lib/containers/storage:/var/lib/shared:ro
-v >/var/lib/containers4:/var/lib/containers:Z quay.io/buildah/stable buildah push image4 registry.company.com/myuser
# rm -rf /var/lib/continers4
Należy zauważyć, że plik /var/lib/containers/storage hosta jest podłączony do pliku /var/lib/shared wewnątrz kontenera w trybie tylko do odczytu. Dlatego też, pracując w kontenerze, Buildah może używać dowolnych obrazów, które zostały wcześniej pobrane przy użyciu Podmana/CRI-O (witaj, prędkość), ale może zapisywać tylko do własnej pamięci (witaj, bezpieczeństwo). Należy również pamiętać, że odbywa się to bez wyłączania separacji SELinux dla kontenera.
Ważne niuanse
W żadnym wypadku nie należy usuwać żadnych obrazów z repozytorium bazowego. W przeciwnym razie kontener Buildah może ulec awarii.
A to nie wszystkie zalety
Możliwości dodatkowego przechowywania nie ograniczają się do powyższego scenariusza. Na przykład możesz umieścić wszystkie obrazy kontenerów we współdzielonym magazynie sieciowym i zapewnić dostęp do nich wszystkim kontenerom Buildah. Załóżmy, że mamy setki obrazów, których nasz system CI/CD regularnie używa do tworzenia obrazów kontenerów. Koncentrujemy wszystkie te obrazy na jednym hoście pamięci masowej, a następnie korzystając z preferowanych narzędzi sieciowej pamięci masowej (NFS, Gluster, Ceph, ISCSI, S3...) otwieramy ogólny dostęp do tej pamięci dla wszystkich węzłów Buildah lub Kubernetes.
Teraz wystarczy zamontować tę pamięć sieciową w kontenerze Buildah w katalogu /var/lib/shared i gotowe – kontenery Buildah nie muszą już pobierać obrazów metodą pull. W ten sposób odrzucamy fazę przedpopulacyjną i jesteśmy od razu gotowi do wystawienia kontenerów.
Można to oczywiście wykorzystać w działającym systemie Kubernetes lub infrastrukturze kontenerów do uruchamiania i uruchamiania kontenerów w dowolnym miejscu bez konieczności pobierania obrazów za pomocą funkcji „pull”. Co więcej, rejestr kontenerów, otrzymując żądanie push o przesłanie do niego zaktualizowanego obrazu, może automatycznie wysłać ten obraz do udostępnionego magazynu sieciowego, gdzie natychmiast staje się on dostępny dla wszystkich węzłów.
Obrazy kontenerów mogą czasami osiągać rozmiar wielu gigabajtów. Funkcjonalność dodatkowej pamięci pozwala uniknąć klonowania takich obrazów pomiędzy węzłami i sprawia, że uruchamianie kontenerów jest niemal natychmiastowe.
Ponadto obecnie pracujemy nad nową funkcją zwaną nakładkami na wolumeny, dzięki której budowanie kontenerów będzie jeszcze szybsze.
wniosek
Uruchamianie Buildaha wewnątrz kontenera w Kubernetes/CRI-O, Podman, a nawet Docker jest wykonalne, proste i znacznie bezpieczniejsze niż używanie docker.socket. Znacząco zwiększyliśmy elastyczność pracy z obrazami, dzięki czemu można je uruchamiać na różne sposoby, aby zoptymalizować równowagę między bezpieczeństwem a wydajnością.
Funkcjonalność dodatkowej pamięci pozwala przyspieszyć lub nawet całkowicie wyeliminować pobieranie obrazów do węzłów.
Źródło: www.habr.com