Obaj będą mogli wykonywać polecenia w kontenerze. Obaj mogli odłączyć pojemnik.
Jaka jest więc prawdziwa różnica między docker exec i docker attach?
Odpowiedzi:
Pojawił się komunikat PR, który dodał do dokumentu:
Uwaga: to polecenie (
attach
) nie służy do uruchamiania nowego procesu w kontenerze. Zobacz:docker exec
.
Odpowiedź na pytanie „ Docker. Jak uzyskać bash \ ssh wewnątrz uruchomionego kontenera ( run -d
)? ” Ilustruje różnicę:
(docker> = 1.3) Jeśli używamy
docker attach
, możemy użyć tylko jednej instancji powłoki .
Więc jeśli chcemy otworzyć nowy terminal z nową instancją powłoki kontenera, musimy po prostu uruchomićdocker exec
jeśli kontener docker został uruchomiony za pomocą
/bin/bash
polecenia, możesz uzyskać do niego dostęp za pomocą dołączania, jeśli nie, musisz wykonać polecenie, aby utworzyć instancję bash wewnątrz kontenera za pomocąexec
.
Jak wspomniano w tym numerze :
- Dołącz nie służy do uruchamiania dodatkowej rzeczy w kontenerze, służy do dołączania do uruchomionego procesu.
- „
docker exec
” jest przeznaczony specjalnie do uruchamiania nowych rzeczy w już uruchomionym kontenerze, czy to w powłoce, czy w jakimś innym procesie.
W tym samym numerze dodaje się:
Chociaż
attach
nie jest dobrze nazwany, szczególnie ze względu na polecenie LXClxc-attach
(które jest bardziej podobnedocker exec <container> /bin/sh
, ale specyficzne dla LXC), ma konkretny cel dosłownego dołączenia cię do procesu uruchomionego przez Docker.
W zależności od tego, jaki jest proces, zachowanie może się różnić , na przykład dołączenie do/bin/bash
da ci powłokę, ale podłączenie do redis-server będzie takie, jak po prostu zacząłeś redis bezpośrednio bez demonizacji.
Kiedy kontener jest uruchamiany przy użyciu / bin / bash, staje się kontenerami PID 1, a docker attach jest używany do uzyskania dostępu do PID 1 kontenera. Więc docker attach <container-id> przeniesie Cię do terminala bash, ponieważ jest to PID 1, jak wspomnieliśmy podczas uruchamiania kontenera. Wyjście z pojemnika zatrzyma pojemnik.
Natomiast w poleceniu docker exec możesz określić, do której powłoki chcesz wejść. Nie przeniesie Cię do PID 1 kontenera. Stworzy to nowy proces dla basha. docker exec -it <identyfikator-kontenera> bash . Wyjście z pojemnika nie zatrzyma pojemnika.
Możesz także użyć nsenter, aby wejść do kontenerów. nsenter -m -u -n -p -i -t <pid kontenera> Możesz znaleźć PID kontenera używając: docker inspect <id-kontenera> | grep PID
Uwaga: Jeśli uruchomiłeś swój kontener z flagą -d, wyjście z kontenera nie zatrzyma kontenera, niezależnie od tego, czy użyjesz attach, czy exec, aby dostać się do środka.
Jak stwierdził Michael Sun w swojej odpowiedzi
docker exec
wykonuje nowe polecenie / tworzy nowy proces w środowisku kontenera, podczas gdydocker attach
po prostu łączy standardowe wejście / wyjście / błąd głównego procesu (z PID 1) wewnątrz kontenera do odpowiedniego standardowego wejścia / wyjścia / błędu bieżącego terminala (terminal używasz do uruchomienia polecenia).
Moja odpowiedź skupi się bardziej na umożliwieniu ci zweryfikowania powyższego stwierdzenia i lepszego zrozumienia go.
Otwórz okno terminala i uruchom polecenie docker run -itd --name busybox busybox /bin/sh
. Polecenie ściągnie obraz, busybox
jeśli jeszcze go nie ma. Następnie utworzy kontener o nazwie busybox
przy użyciu tego obrazu.
Możesz sprawdzić stan swojego kontenera, uruchamiając polecenie docker ps -a | grep busybox
.
Jeśli uruchomisz docker top busybox
, powinieneś zobaczyć takie wyjście.
UID PID PPID C STIME TTY TIME CMD
root 7469 7451 0 11:40 pts/0 00:00:00 /bin/sh
Oczywiście, PID
, PPID
oraz inne wartości będą różne w Twoim przypadku. Można korzystać z innych narzędzi i programów narzędziowych oraz jak pstree
, top
, htop
aby wyświetlić listę PID
i PPID
.
PID
I PPID
oznacza identyfikator procesu i proces nadrzędny ID. Proces rozpoczął się, gdy utworzyliśmy i uruchomiliśmy nasz kontener poleceniem /bin/sh
. Teraz uruchom polecenie docker attach busybox
. Spowoduje to dołączenie standardowego strumienia wejścia / wyjścia / błędu kontenera do terminala.
Po dołączeniu kontenera utwórz sesję powłoki, uruchamiając polecenie sh
. CTRL-p CTRL-q
Sekwencja prasy . Spowoduje to odłączenie terminala od kontenera i utrzyma kontener w ruchu. Jeśli teraz uruchomisz docker top busybox
, na liście powinny pojawić się dwa procesy.
UID PID PPID C STIME TTY TIME CMD
root 7469 7451 0 11:40 pts/0 00:00:00 /bin/sh
root 7737 7469 0 11:43 pts/0 00:00:00 sh
Ale PPID
z tych dwóch procesów będzie inny. W rzeczywistości PPID
drugi proces będzie taki sam, jak PID
pierwszy. Pierwszy proces działa jako proces nadrzędny dla właśnie utworzonej sesji powłoki.
A teraz biegnij docker exec -it busybox sh
. Po wejściu do kontenera sprawdź listę uruchomionych procesów kontenera busybox
w innym oknie terminala, uruchamiając polecenie docker top busybox
. Powinieneś zobaczyć coś takiego
UID PID PPID C STIME TTY TIME CMD
root 7469 7451 0 11:40 pts/0 00:00:00 /bin/sh
root 7737 7469 0 11:43 pts/0 00:00:00 sh
root 7880 7451 0 11:45 pts/1 00:00:00 sh
PPID
Pierwszego i trzeciego procesu będzie to samo, co potwierdza, że docker exec
tworzy nowy proces w środowisku kontenera podczas gdy docker attach
tylko połączy standardowego wejścia / wyjścia / błąd głównego procesu wewnątrz pojemnika na odpowiednie standardowe wejście / wyjście / błąd prądu terminal.
Docker wykonuje nowe polecenie / tworzy nowy proces w środowisku kontenera, podczas gdy docker attach po prostu łączy standardowe wejście / wyjście / błąd głównego procesu (z PID 1) wewnątrz kontenera do odpowiedniego standardowego wejścia / wyjścia / błędu prądu terminal (terminal, którego używasz do uruchomienia polecenia).
Kontener to izolowane środowisko, w którym działają pewne procesy. W szczególności kontener ma własną przestrzeń systemu plików i przestrzeń PID, które są odizolowane od hosta i innych kontenerów. Gdy kontener zostanie uruchomiony przy użyciu polecenia „docker run –it…”, główny proces będzie miał pseudo-tty i STDIN pozostające otwarte. Po podłączeniu w trybie tty można odłączyć się od kontenera (i pozostawić go uruchomionego) za pomocą konfigurowalnej sekwencji klawiszy. Domyślna sekwencja to CTRL-p CTRL-q. Sekwencję klawiszy można skonfigurować za pomocą opcji --detach-keys lub pliku konfiguracyjnego. Możesz ponownie dołączyć do odłączonego kontenera za pomocą Docker Attach.
Docker exec właśnie uruchamia nowy proces w środowisku kontenera, czyli należy do przestrzeni PID kontenera.
Na przykład, jeśli uruchomisz kontener za pomocą „docker run –dit XXX / bin / bash”, możesz dołączyć do kontenera (głównego procesu) za pomocą dwóch różnych terminali. Kiedy wprowadzasz dane w jednym terminalu, możesz zobaczyć, że pojawia się w drugim terminalu, ponieważ oba terminale są podłączone do tego samego terminala. Uważaj, ponieważ jesteś teraz w głównym procesie kontenera, jeśli wpiszesz „exit”, wyjdziesz z kontenera ( więc uważaj, używając klawiszy odłączania do odłączenia ), a zobaczysz, że oba terminale zostały opuszczone. Ale jeśli uruchomisz „docker exec –it XXX / bin / bash” w dwóch terminalach, uruchomiłeś dwa nowe procesy wewnątrz kontenera i nie są one powiązane ze sobą ani z procesem głównym i możesz bezpiecznie z nich wyjść .
nsenter
. Czy możesz rozwinąć? Wyjaśnienie opcji byłoby w porządku. Dlaczego nie wprowadzić wszystkich przestrzeni nazw? Dlaczego właśnie te?