Docker Grundlagen

Was ist Docker?

Mit Docker können wir unsere Anwendung und die dazugehörende Plattform ( Betriebsystem, Laufzeitumgebung, Libraries … ) in ein Image packen und diese von jedem Gerät laufen lassen. Hauptsache auf unserem Gerät läuft Docker. Docker kann das Image lesen und erstellt für uns einen Container, welcher auf allen Geräten, sowohl auf einem Computer, Laptop oder Cloud läuft.

Docker installieren

Docker unter Mac & Windows installieren Damit Docker auf Mac und Windows läuft, benötigen wir ein zusätzliches Programm: boot2docker. Wenn wir boot2docker runtergeladen und installiert haben, müssen wir nur noch boot2docker starten. Im Terminal eingeben boot2docker init boot2docker up Wenn wir im Terminal: "docker ps" ausführen und es kommt keine Fehlermeldung wie: "no such file or directory. Are you trying to connect to a TLS-enabled daemon without TLS?" . Ist alles in Ordnung. Ich bekomme eine Fehlermeldung, was soll ich tun? Du musst in deinem Terminal Fenster, boot2docker initialisieren: Führe diesen Befehl aus: boot2docker up und versuch es nochmal mit docker ps Wenn du magst kannst du $(boot2docker shellinit) in deine .bash_profile hinzufügen. Danach sollte boot2docker in jedem neuen Terminal Fenster automatisch gestartet werden.

Docker unter Linux installieren

Docker läuft auf Linux nativ. Einfach Distribution auswählen und der Anweisung folgen: Docker installation

Docker Image

Bei einem Image handelt es sich um eine Art Template. Dieses Template könnte ein Betriebsystem ( z.B Ubuntu ) sein, welcher wiederum eine NGINX, PHP oder Node.js Installation beinhaltet. Auch die Anwendung selber kann in einem Image stecken. Unser Image können wir ganz leicht mit anderen Entwicklern teilen. Das Image kann überall mit Docker verwendet werden.Docker bittet ein eigenes Repository für Images an.

Wir können auch unser Terminal verwenden, um nach Images zu suchen: docker search nginx

Image laden

Wenn wir docker pull nginx ausführen können wir ein Image unserem Docker hinzufügen. Mit docker images können wir alle Images auflisten.

Docker Container

Ein Container ist ein Image, welcher gerade ausgeführt wird. Wenn ich ein Image mit docker run nginx ausführe, spricht man von einem Container. Es ist vergleichbar mit einem Prozess. Wir können mit docker ps alle Container auflisten (ähnlich wie bei Linux ps).

Container steuern

Mit docker stop ContainerID können wir ein Container stoppen. Wenn wir noch zusätzlich ein docker rm ContainerID ausführen entfernen wir unseren Container. Wenn wir ein Container starten wollen müssen wir zuerst die ID des Containers herausfinden. Da docker ps nur laufende Container anzeigt müssen wir noch eine kleinigkeit hinzufügen: docker ps -a. Damit sehen wir alle beendeten Container. Mit docker start containerID starten wir unseren Container erneuet. Andernfalls mit docker run nginx.

Container vs Images

Was ist der unterschied zwischen Image und Container?

Ein Image ist ein Bauplan für Docker. Ein Image besitzt nur "read-only" rechte und kann nur gelesen werden. Ein Container ist eine Instanz von einem Image und kann zur Laufzeit verändert werden.

Image erzeugen

Es gibt zwei Möglichkeiten ein Image zu erzeugen oder zu erweitern. Einmal mit Dockerfile oder mit "Commits", wobei das letzte etwas mehr bedarf als ein commit aber später mehr dazu. Ich fange mit dem Dockerfile an.

Dockerfile

Wir erstellen ein "Dockerfile" in unserem Projekt Ordner. mkdir my-project && touch Dockerfile Ein Dockerfile beinhaltet alle Befehle für die Erstellung eines Images. Hier mal eine Liste der Dockerfile Befehle (Auswahl!)

FROM

Das From beinhaltet ein Image, welches wir verwenden wollen. Wir können als Basis ein Betriebssystem verwenden. z.B FROM ubuntu:latest. Vorausgesetzt wir haben das Image davor gepullt!

RUN

Das Run enthält ein Linux-Befehle für die Shell. z.B "RUN mkdir /www && touch index.html"

ADD

Mit add können wir unsere Dateien in den Container laden oder überschreiben. Nützlich wenn wir irgendwelche Config Dateien überschreiben müssen. z.B ADD ./unser-config/nginx.conf /etc/nginx/nginx.conf.

EXPOSE

Mit Expose können wir unser Container einen bestimmten Port binden. z.B EXPOSE 80

Hier mal Dockerfile Beispiel:

# wir verwenden nginx als Basis Image
# nginx wiederum verwendet das debian Betriebssystem!
FROM nginx:latest 

# wir aktualisieren unsere Paketliste 
RUN apt-get -y update

# wir installieren php5-fpm
RUN apt-get -y install php5-fpm # php installieren

# wir überschreiben die config files
ADD ./php-config/www.conf /etc/php5/fpm/pool.d/www.conf
ADD ./nginx-config/default.conf /etc/nginx/conf.d/default.conf
ADD ./nginx-config/nginx.conf /etc/nginx/nginx.conf

# wir erzeugen einen www Ordner
RUN mkdir /www

# wir kopieren unsere index.php in den www Ordner 
ADD /www/index.php /www

# php5fpm starten
RUN service php5-fpm start

# nginx webserver neustarten
RUN service nginx restart

# Unser Container auf Port 80 binden
EXPOSE 80

Wenn wir unser Dockerfile haben können wir jetzt daraus ein Image machen, indem wir folgenden docker Befehl verwenden:

docker build [path/to/dockerfile] docker build -t mein-image-name

Mit -t können wir unseren Image ein tag-name zuweisen.

Image als Container starten:

docker run -d mein-image-name

Das "-d" sorgt dafür, dass der Container im Hintergrund läuft.

Wenn wir im Browser http://127.0.0.1 aufrufen sollte unsere "mein-image-name" laufen. Wenn du meine Beispiel Datei verwendest, sollest du "echo phpinfo()" sehen.

Wer boot2docker verwendet bei dem wird http://127.0.0.1 nicht funktionieren. Du sollest erstmal im Terminal "boot2docker ip" aufrufen und die angezeigte IP verwenden. Bei mir ist es die: 192.168.59.103

Alternative zu Dockerfile

Wir können Images und Container auch ohne Dockerfile erstellen, indem wir den docker commit Befehl verwenden. Im nächstem Abschnitt zeige ich wie man ein Node.js Image erstellt. Dabei verwende ich kein Dockerfile, sondern docker commit.

Ubuntu aus dem Repository laden

Als erstes öffnen wir unser Terminal. Unser erster Schritt mit Docker ist das pullen eines Betriebssystem. Ich persönlich mag ubuntu, kann aber eine andere Distribution sein.

Wir holen uns das ubuntu Image: docker pull ubuntu. Danach starten wir Ubuntu Container: docker run -t -i ubuntu. Das "-i" und "-t" erlaubt uns die Konsole von ubuntu zu steuern. Bei manchen Images wäre ein zusätzliches "/bin/bash" erforderlich! docker run -t -i nginx /bin/bash. Danach sollten wir uns im Ubuntu befinden.

Ubuntu Container starten

Zuerst müssen wir unsere Paketliste erneuern. Sonst können wir vorerst keine Pakete installieren. apt-get update. Nachdem update können wir "nodejs" und "npm" Pakete runterladen.

apt-get install -y nodejs apt-get install -y npm

Wenn wir npm -v und nodejs -v ausführen sollten wir jeweilige Versionsnummern sehen. Danach erstellen wir ein /www Ordner und diesem eine index.js Datei.

mkdir -p www && touch www/index.js

Jetzt wollen wir unsere index.js Datei beschreiben. Entweder machen wir es im Container oder wir machen es auf unserem System und überschreiben die index.js mit "docker cp". Wenn wir es auf unserem Server machen wollen sollten wir davor ein Editor installieren:

apt-get install -y nano

Danach können wir mit nano unsere index.js bearbeiten:

nano /www/index.js

oder wir haben auf unserem System eine index.js welche wir auf unser Container laden wollen. Das werde ich an dieser Stelle überspringen. Ich komme in kürze darauf zurück! Am Ende sollte unsere index.js so aussehen:

var http = require('http');

http.createServer(function (req, res) {

  res.writeHead(200, {'Content-Type': 'text/plain'});
  res.end('Hello from Docker!');

}).listen(8888);

Docker commit

Wir haben "nodejs" und "npm" auf unserem Container installiert. Dazu noch eine index.js welche unsere Anwendung repräsentieren soll. Jetzt wollen wir aus unserem Container ein Image machen. Dafür verlassen wir unser ubuntu: Mit dem exit Befehl. Mit exit schließen wir den Container. Wenn wir docker ps ausführen, sollte kein Container laufen. Allerdings brauchen wir für den nächsten schritt die ubuntu Container ID. Diese können wir mit docker ps -a herausbekommen. Wir führen docker ps -a aus und merken uns die Container ID (copy)

Mit docker commit können wir aus unserem Container ein Image machen.

docker commit -m "add node and npm" containerID image-name

Wenn du ubuntu Image überschreiben möchtest:

docker commit -m "add node and npm" a0f87d36b1b6 ubuntu:latest

Wenn du ein neues Image anlegen möchtest:

docker commit -m "add node and npm" a0f87d36b1b6 my-nodejs:0.1

Jetzt sollten wir ein "my-nodejs" Image haben. Diesen können wir im Hintergrund starten:

docker run -d -p 8000:8888 my-nodejs:0.1 nodejs /www/index.js

Wenn wir http://127.0.0.1:8000 bzw. http://192.168.59.103:8000 im Browser aufrufen sollten wir unsere Anwednung sehen. Zu index.js, wir können mit docker cp my-nodejs:0.1:/www/index.js /unsere/node-app/index.js die index.js durch unsere lokale ersetzen. Statt mit nano zu editieren.

Zurück