wake-up-neo.com

So stellen Sie die NFS-Freigabe/das Volume mithilfe von Docker Compose V3 direkt in einen Container ein

Ich habe eine compose-Datei mit v3, bei der 3 Dienste das gleiche Volume gemeinsam nutzen/verwenden. Während des Swarm-Modus müssen zusätzliche Container und Volumes erstellt werden, um unsere Dienste im gesamten Cluster zu verwalten. 

Ich plane die Verwendung eines NFS-Servers, damit eine einzelne NFS-Freigabe direkt auf allen Hosts im Cluster bereitgestellt wird. 

Ich habe unten zwei Möglichkeiten gefunden, aber es müssen zusätzliche Schritte auf dem Docker-Host ausgeführt werden.

Gibt es eine Standardmethode, mit der ich NFS-Freigaben mit Docker Compose v3 direkt verwenden/bereitstellen kann, indem ich nur wenige/keine Schritte auf dem Docker-Host durchführe.

10
vivekyad4v

Nachdem Sie festgestellt haben, dass dies massiv undokumentiert ist, können Sie ein NFS-Volume mithilfe von Stack- und Docker-Composition mounten.

Das Wichtigste ist, dass Sie version: "3.2" oder höher verwenden müssen. Wenn Sie dies nicht tun, werden Sie seltsame und nicht offensichtliche Fehler haben.

Das zweite Problem ist, dass Volumes nicht automatisch aktualisiert werden, wenn sich ihre Definition ändert. Dies kann dazu führen, dass Sie ein Kaninchenloch der Meinung sind, dass Ihre Änderungen nicht korrekt sind, wenn sie nicht angewendet wurden. Stellen Sie sicher, dass docker rm VOLUMENAME überall vorhanden ist, da das Volume vorhanden ist und nicht validiert wird.

Das dritte Problem ist eher ein NFS-Problem - Der NFS-Ordner wird nicht erstellt auf dem Server, wenn er nicht existiert. Genau so funktioniert NFS. Sie müssen sicherstellen, dass es existiert, bevor Sie etwas tun.

(Entfernen Sie "soft" und "nolock" nur, wenn Sie sicher sind, dass Sie wissen, was Sie tun. Andernfalls kann das Andockfenster nicht einfrieren, wenn der NFS-Server nicht mehr funktioniert.)

Hier ist ein vollständiges Beispiel:

[[email protected] docker-mirror]# cat nfs-compose.yml
version: "3.2"

services:
  rsyslog:
    image: jumanjiman/rsyslog
    ports:
      - "514:514"
      - "514:514/udp"
    volumes:
      - type: volume
        source: example
        target: /nfs
        volume:
          nocopy: true
volumes:
  example:
    driver_opts:
      type: "nfs"
      o: "addr=10.40.0.199,nolock,soft,rw"
      device: ":/docker/example"



[[email protected] docker-mirror]# docker stack deploy --with-registry-auth -c nfs-compose.yml rsyslog
Creating network rsyslog_default
Creating service rsyslog_rsyslog
[[email protected] docker-mirror]# docker stack ps rsyslog
ID                  NAME                IMAGE                       NODE                DESIRED STATE       CURRENT STATE                     ERROR               PORTS
tb1dod43fe4c        rsyslog_rsyslog.1   jumanjiman/rsyslog:latest   swarm-4             Running             Starting less than a second ago
[[email protected] docker-mirror]#

Nun zu Swarm-4:

[email protected]:~# docker ps
CONTAINER ID        IMAGE                       COMMAND                  CREATED             STATUS              PORTS               NAMES
d883e0f14d3f        jumanjiman/rsyslog:latest   "rsyslogd -n -f /e..."   6 seconds ago       Up 5 seconds        514/tcp, 514/udp    rsyslog_rsyslog.1.tb1dod43fe4cy3j5vzsy7pgv5
[email protected]:~# docker exec -it d883e0f14d3f df -h /nfs
Filesystem                Size      Used Available Use% Mounted on
:/docker/example          7.2T      5.5T      1.7T  77% /nfs
[email protected]:~#

Dieses Volume wird auf jedem Schwarmknoten erstellt ( aber nicht zerstört ), auf dem der Stack ausgeführt wird.

[email protected]:~# docker volume inspect rsyslog_example
[
    {
        "CreatedAt": "2017-09-29T13:53:59+10:00",
        "Driver": "local",
        "Labels": {
            "com.docker.stack.namespace": "rsyslog"
        },
        "Mountpoint": "/var/lib/docker/volumes/rsyslog_example/_data",
        "Name": "rsyslog_example",
        "Options": {
            "device": ":/docker/example",
            "o": "addr=10.40.0.199,nolock,soft,rw",
            "type": "nfs"
        },
        "Scope": "local"
    }
]
[email protected]:~#
25
xrobau

Ja, Sie können direkt auf ein NFS aus der Erstellungsdatei verweisen: 

volumes:
   db-data:
      driver: local
      driver_opts:
        type: nfs
        o: addr=$SOMEIP,rw
        device: ":$PathOnServer"

Auf analoge Weise können Sie auf jedem Host ein nfs-Volume erstellen.

docker volume create --driver local --opt type=nfs --opt o=addr=$SomeIP,rw --opt device=:$DevicePath --name nfs-docker
5
herm

Abhängig davon, wie ich das Volume verwenden muss, habe ich die folgenden 3 Optionen.

Zunächst können Sie das benannte Volume direkt erstellen und als externes Volume in compose oder als benanntes Volume in einem Befehl docker run Oder docker service create Verwenden.

  # create a reusable volume
  $ docker volume create --driver local \
      --opt type=nfs \
      --opt o=nfsvers=4,addr=nfs.example.com,rw \
      --opt device=:/path/to/dir \
      foo

Als nächstes gibt es die Syntax --mount, Die mit docker run Und docker service create Funktioniert. Dies ist eine ziemlich lange Option. Wenn Sie eine durch Kommas getrennte Option in eine andere durch Kommas getrennte Option einbetten, müssen Sie dem ausgeführten Befehl einige Anführungszeichen (mit Escape-Zeichen, damit die Shell sie nicht entfernt) übergeben. Ich verwende dies in der Regel für einen einmaligen Container, der auf NFS zugreifen muss (z. B. einen Utility-Container zum Einrichten von NFS-Verzeichnissen):

  # or from the docker run command
  $ docker run -it --rm \
    --mount type=volume,dst=/container/path,volume-driver=local,volume-opt=type=nfs,\"volume-opt=o=nfsvers=4,addr=nfs.example.com\",volume-opt=device=:/Host/path \
    foo

  # or to create a service
  $ docker service create \
    --mount type=volume,dst=/container/path,volume-driver=local,volume-opt=type=nfs,\"volume-opt=o=nfsvers=4,addr=nfs.example.com\",volume-opt=device=:/Host/path \
    foo

Zuletzt können Sie das benannte Volume in Ihrer Compose-Datei definieren. Ein wichtiger Hinweis dabei ist, dass das Namensvolumen nur einmal erstellt und nicht mit Änderungen aktualisiert wird. Wenn Sie also das benannte Volume ändern müssen, möchten Sie ihm einen neuen Namen geben.

  # inside a docker-compose file
  ...
  services:
    example-app:
      volumes:
      - "nfs-data:/data"
  ...
  volumes:
    nfs-data:
      driver: local
      driver_opts:
        type: nfs
        o: nfsvers=4,addr=nfs.example.com,rw
        device: ":/path/to/dir"
  ...

In jedem dieser Beispiele:

  • Der Typ ist auf nfs gesetzt, nicht auf nfs4. Dies liegt daran, dass Docker einige nützliche Funktionen für das Feld addr bietet, jedoch nur für den Typ nfs.
  • Die o sind die Optionen, die an den Mount-Systemaufruf übergeben werden. Ein Unterschied zwischen dem Befehl mount syscall und mount unter Linux besteht darin, dass das Gerät den Teil vor dem Verschieben von : In eine Option addr hat.
  • nfsvers wird verwendet, um die NFS-Version festzulegen. Dies vermeidet Verzögerungen, da das Betriebssystem zuerst andere NFS-Versionen versucht.
  • addr kann ein DNS-Name sein, wenn Sie type=nfs verwenden, und nicht nur eine IP-Adresse. Sehr nützlich, wenn Sie mehrere VPCs mit unterschiedlichen NFS-Servern haben, die denselben DNS-Namen verwenden, oder wenn Sie den NFS-Server in Zukunft anpassen möchten, ohne jedes Volume-Mount zu aktualisieren.
  • Andere Optionen wie rw (Lese-/Schreibzugriff) können an die Option o übergeben werden.
  • Das Feld device ist der Pfad auf dem Remote-NFS-Server. Der führende Doppelpunkt ist erforderlich. Dies ist ein Artefakt dafür, wie der Befehl mount die IP-Adresse in das Feld addr für den Systemaufruf verschiebt. Dieses Verzeichnis muss auf dem Remote-Host vorhanden sein, bevor das Volume in einem Container bereitgestellt wird.
  • In der Syntax --mount Ist das Feld dst der Pfad innerhalb des Containers. Für benannte Volumes legen Sie diesen Pfad auf der rechten Seite des Volume-Mounts (in der kurzen Syntax) in Ihrem Befehl docker run -v Fest.

Wenn Sie Berechtigungsprobleme beim Zugriff auf ein Remote-NFS-Volume haben, ist eine häufige Ursache, dass Container als Root ausgeführt werden und der NFS-Server auf Root-Squash eingestellt ist (wodurch der gesamte Root-Zugriff auf den Benutzer nobody geändert wird). Sie müssen Ihre Container entweder so konfigurieren, dass sie als bekannte Nicht-Root-UID ausgeführt werden, die Zugriff auf die Verzeichnisse auf dem NFS-Server hat, oder Root-Squash auf dem NFS-Server deaktivieren.

0
BMitch

Meine Lösung für AWS EFS, die funktioniert:

  1. EFS erstellen (NFS-Port 2049 in Sicherheitsgruppe nicht vergessen)
  2. Installieren Sie das nfs-common-Paket:

    Sudo apt-get install -y nfs-common

  3. Überprüfen Sie, ob Ihr EFS funktioniert:

    mkdir efs-test-point 
     Sudo chmod go + rw efs-test-point
    Sudo mount -t nfs -o nfsvers = 4.1, rsize = 1048576, wsize = 1048576, hard, timeo = 600, retrans = 2, noresvport [YOUR_EFS_DNS]:/efs-test-point
    berühren Sie efs-testpoint/1.txt 
     Sudo umount efs-testpoint /
     ls -la efs-testpoint /

    das Verzeichnis muss leer sein

    Sudo mount -t nfs -o nfsvers = 4.1, rsize = 1048576, wsize = 1048576, hard, timeo = 600, retrans = 2, noresvport [YOUR_EFS_DNS]:/efs-test-point

    ls -la efs-test-point/

    datei 1.txt muss vorhanden sein

  4. Konfigurieren Sie die Datei docker-compose.yml:

    dienstleistungen:
     sidekiq: 
     Bände: 
     - uploads_tmp_efs:/home/application/public/uploads/tmp 
     ...
     Bände: 
     uploads_tmp_efs: 
     Treiber: lokal 
     driver_opts: 
     Typ: nfs 
     o: addr = [YOUR_EFS_DNS], nfsvers = 4.1, rsize = 1048576, wsize = 1048576, hart, timeo = 600, retrans = 2 
     Gerät: [YOUR_EFS_DNS]: /

0
super_p

Mein Problem wurde mit dem Ändern des Treiberoptionstyps auf NFS4 behoben.

volumes:
  my-nfs-share:
    driver: local
    driver_opts:
      type: "nfs4"
      o: "addr=172.24.0.107,rw"
      device: ":/mnt/sharedwordpress"
0
namaiiee