Späte Antwort, könnte aber jemandem helfen
docker run/exec -i
verbindet die Standardeingabe des Befehls im Container mit der Standardeingabe des docker run/exec
selbst.
So
-
docker run -i alpine cat
gibt Ihnen eine leere Zeile, die auf Eingabe wartet. Geben Sie "hello" ein und Sie erhalten ein Echo "hello". Der Container wird erst beendet, wenn Sie STRG + D senden, da der Hauptprozess cat
wartet auf Eingaben aus dem unendlichen Stream, der der Terminaleingang des docker run
.
- Auf der anderen Seite
echo "hello" | docker run -i alpine cat
wird "hallo" drucken und sofort beenden, weil cat
stellt fest, dass der Eingabestream beendet wurde und sich selbst beendet.
Wenn du es versuchst docker ps
nachdem Sie einen der oben genannten Schritte beendet haben, werden Sie keine laufenden Container finden. In beiden Fällen, cat
selbst beendet wurde, hat Docker den Container beendet.
Jetzt für "-t" teilt dies dem Hauptprozess im Docker mit, dass seine Eingabe ein Terminalgerät ist.
So
-
docker run -t alpine cat
gibt Ihnen eine leere Zeile, aber wenn Sie versuchen, "hello" einzugeben, erhalten Sie kein Echo. Dies liegt daran, dass während cat
an einen Terminaleingang angeschlossen ist, ist dieser Eingang nicht mit Ihrem Eingang verbunden. Das von Ihnen eingegebene "hallo" hat die Eingabe von nicht erreicht cat
. cat
wartet auf Eingaben, die nie ankommen.
-
echo "hello" | docker run -t alpine cat
gibt Ihnen auch eine leere Zeile und verlässt den Container nicht mit STRG-D, aber Sie erhalten kein Echo "hallo", weil Sie nicht bestanden haben -i
Wenn Sie STRG + C senden, erhalten Sie Ihre Shell zurück, aber wenn Sie es versuchen docker ps
jetzt sehen Sie die cat
container läuft noch. Dies liegt daran, dass cat
wartet immer noch auf einen Eingabestream, der nie geschlossen wurde. Ich habe keine nützliche Verwendung für die gefunden -t
allein, ohne mit kombiniert zu werden -i
.
Jetzt, für -it
zusammen. Dies teilt cat mit, dass sein Eingang ein Terminal ist, und verbindet dieses Terminal gleichzeitig mit dem Eingang von docker run
welches ist ein Terminal. docker run/exec
wird sicherstellen, dass seine eigene Eingabe tatsächlich ein tty ist, bevor es an übergeben wird cat
. Deshalb erhalten Sie eine input device is not a TTY
wenn du es versuchst echo "hello" | docker run -it alpine cat
weil in diesem Fall die Eingabe von docker run
selbst ist die Pipe vom vorherigen Echo und nicht das Terminal, wo docker run
wird ausgeführt
Schließlich, warum solltest du bestehen müssen -t
wenn -i
wird den Trick machen, Ihre Eingabe mit zu verbinden cat
's Eingabe? Dies liegt daran, dass Befehle die Eingabe anders behandeln, wenn es sich um ein Terminal handelt. Dies lässt sich auch am besten anhand eines Beispiels veranschaulichen
-
docker run -e MYSQL_ROOT_PASSWORD=123 -i mariadb mysql -uroot -p
wird Ihnen eine Passwortabfrage geben. Wenn Sie das Passwort eingeben, werden die Zeichen sichtbar gedruckt.
-
docker run -i alpine sh
wird Ihnen eine leere Zeile geben. Wenn Sie einen Befehl wie eingeben ls
sie erhalten eine Ausgabe, aber keine Eingabeaufforderung oder farbige Ausgabe.
In den letzten beiden Fällen erhalten Sie dieses Verhalten, weil mysql
sowie shell
behandelten die Eingabe nicht als tty und verwendeten daher kein tty-spezifisches Verhalten wie Maskieren der Eingabe oder Einfärben der Ausgabe.