Wie kann ich ein vollständiges Betriebssystem in einem Docker-Container ausführen, ohne einen Befehl anzugeben?

25

Ich verfolge die CoreOS Docker-Dokumentation und erwähne das Starten von Containern mit Befehlen wie:

docker run someImageName /bin/somebinary

Wo someImageNameist ein Bild? Wenn / bin / somebinary beendet wird, wird das Image nicht mehr ausgeführt.

Ich möchte einfach ein Image ausführen, ohne die auszuführenden Binärdateien anzugeben. Stattdessen möchte ich einfach die Dienste (z. B. systemd / sysvinit) ausführen, die normalerweise im Images-Betriebssystem ausgeführt werden .

Dies scheint die häufigste Aufgabe zu sein, die jemand jemals mit Docker ausführen möchte, aber der Versuch, ein Image ohne einen Befehl auszuführen, gibt Folgendes zurück:

2014/02/05 14:49:19 Error: create: No command specified

Wie kann ich einen Docker-Container starten und ein vollständiges Betriebssystem ausführen, anstatt einen Befehl anzugeben ?

Mikemaccana
quelle
Dies ist ein Duplikat dieser Frage stackoverflow.com/questions/19332662/…
Fred the Magic Wonder Dog
@FredtheMagicWonderDog Nicht ganz, obwohl die Antwort dieselbe ist.
Mikemaccana

Antworten:

24

Wie hier dokumentiert, führen Sie /sbin/initden Befehl einfach wie jedes andere Unix aus, das vom Einzelbenutzermodus in den Mehrbenutzermodus bootet.

https://stackoverflow.com/questions/19332662/start-full-container-in-docker

Container können ausgereifte Betriebssysteme sein, müssen es aber nicht sein (und VMs sind auch nicht komplizierter zu konfigurieren und zu verwalten).

Ich würde sagen, der Sinn von Docker ist es, Anwendungscontainer einfach zu gestalten, sodass Sie nur eine App konfigurieren müssen, nicht das gesamte Betriebssystem.

Fred der Zauberwunderhund
quelle
Vielen Dank. Nachdem ich das Image mit / sbin / init gestartet hatte, lief ich docker ps -notrunc, um die Container-ID zu erhalten, und dann sudo /usr/sbin/lxc-attach -n containerIDin das laufende Image. Wie im anderen Poster erwähnt, brauche ich eigentlich keine zweite Init, also werde ich als nächstes die Container mit nur einem Befehl prüfen ...
mikemaccana
Zu sagen, dass Sie auf einer VM kein vollständiges Betriebssystem ausführen müssen, ist wie zu sagen, dass Sie auf einer physischen Maschine kein vollständiges Betriebssystem ausführen müssen Programm, das ohne die Stdlib läuft und so init, aber es ist
Lie Ryan
11

Docker ist ein System zur Verwaltung und Bereitstellung von Anwendungscontainern , nicht von Betriebssystemcontainern . Es scheint, als würden Sie einen Docker-Container mit dem Booten eines Betriebssystems in Konflikt bringen.

Bei Ihren Docker-Containern sollte es sich um Einzweckanwendungen mit sehr engem Anwendungsbereich handeln, die mit einem einzigen Befehl gestartet werden können. Wenn Sie nach etwas Komplexerem suchen, ist Docker nicht die Lösung, die Sie suchen. In diesem Fall schauen Sie sich KVM, ESXi, OpenVZ, LXD usw. an.

Wenn Sie nur suchen, wie Sie einen Standard CMDund ENTRYPOINTIhre Container festlegen können , können Sie dies während der Erstellung mithilfe einer Docker-Datei tun.

EEAA
quelle
5
Mir ist bewusst, was Docker ist. Ich werde darauf hinweisen, dass Anwendungscontainer auf Betriebssystemen wie Fedora oder Ubuntu basieren. Persistente Anwendungen unter Unix - auch nur für Benutzer Unixe wie Docker-Container - werden entweder aus Initskripten oder System-Unit-Dateien gestartet. Wenn meine App zum Beispiel abstürzt, möchte ich, dass sie automatisch mit einem Schwellenwert neu gestartet wird, den systemd bereitstellt.
Mikemaccana
5
Sie versuchen zu viel in Ihre Container zu stopfen - sie sind kein Betriebssystem. Die Prozessüberwachung sollte außerhalb jedes Behälters erfolgen.
EEAA
1
Also, wenn ein Prozess stirbt ... starten Sie einfach den gesamten Container neu? Ich denke, das ist nicht so teuer, also könnte das in Ordnung sein. Es fühlt sich irgendwie komisch an - mein Container hat ein / sbin / init, aber es wird nie benutzt ...
Mikemaccana
1
Ja, das ist die Idee. Ihr Container hat ein /sbin/init, muss es aber nicht haben . Sie haben wahrscheinlich einen Standard-Ubuntu-Container oder ähnliches verwendet. In diesen Behältern befinden sich viele Teile, die entfernt werden können, wenn Sie dies wünschen.
EEAA
1
@ValkoSipuli Diese Meinung können Sie gerne vertreten. Ich behaupte immer noch, dass das Ausführen von mehr als einem Prozess in einem Container einen Großteil des Grundes für die erstmalige Verwendung von Containern zunichte macht. Gibt es einen Ort zum Ausführen eines Betriebssystems in einem Container? Wahrscheinlich. Das ist jedoch eine Ausnahme und sollte nicht ohne viel Nachdenken über Vor- und Nachteile geschehen.
EEAA
5

Um ein vollständiges Betriebssystem in einem Container auszuführen, erstellen Sie die folgende Docker-Datei:

FROM fedora:25

CMD /sbin/init

Erstellen und starten Sie den Container und geben Sie eine Shell ein, um die darin ausgeführten Dienste zu untersuchen:

docker build -t os .
docker run -d --privileged --name os os
docker exec -it os bash

Komplette Systemdienstleistungen im Container. Schön.

Markus Hallmann
quelle
0
docker pull ubuntu

Führen Sie einfach so oft wie nötig das gleiche Image aus. Es werden neue Container erstellt, die dann gestartet und gestoppt werden können, wobei jeweils eine eigene Konfiguration gespeichert wird. Geben Sie zu Ihrer Bequemlichkeit jedem Ihrer Container einen Namen mit "--name".

Fi:

docker run --name MyContainer1 <ubuntu image>
docker run --name MyContainer2 <ubuntu image>
docker run --name MyContainer3 <ubuntu image>

Das ist es.

$ docker ps
CONTAINER ID        IMAGE            CREATED          STATUS               NAMES
a7e789711e62        67759a80360c   12 hours ago     Up 2 minutes         MyContainer1
87ae9c5c3f84        67759a80360c   12 hours ago     Up About a minute    MyContainer2
c1524520d864        67759a80360c   12 hours ago     Up About a minute    MyContainer3

Danach haben Sie Ihre Container für immer erstellt und können sie wie VMs starten und stoppen.

docker start MyContainer1

Um in den Container zu steigen und das zu tun, was Sie tun möchten:

docker exec -it MyContainer1 bash
DimiDak
quelle