Buscamos por el mundo on line y así traerte la solución a tu problema, en caso de alguna duda déjanos tu pregunta y te contestamos con mucho gusto, porque estamos para ayudarte.
Solución:
Después de descubrir que esto está enormemente indocumentado, esta es la forma correcta de montar un volumen NFS usando stack y docker compose.
Lo más importante es que debes utilizar version: "3.2"
o mas alto. Tendrá errores extraños y no obvios si no los tiene.
El segundo problema es que los volúmenes son no actualizado automáticamente cuando cambia su definición. Esto puede llevarte a pensar que tus cambios no son correctos, cuando simplemente no se han aplicado. Asegúrese docker rm VOLUMENAME
donde sea que pueda estar, como si el volumen existiera, no se validará.
El tercer problema es más un problema de NFS: la carpeta NFS no ser creado en el servidor si no existe. Así es como funciona NFS. Debe asegurarse de que exista antes de hacer cualquier cosa.
(No elimine ‘soft’ y ‘nolock’ a menos que esté seguro de saber lo que está haciendo; esto evita que la ventana acoplable se congele si su servidor NFS desaparece)
Aquí tienes un ejemplo completo:
[[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]#
Ahora, en 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]:~#
Este volumen se creará (pero no destruido) en cualquier nodo de enjambre en el que se esté ejecutando la pila.
[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]:~#
Dependiendo de cómo necesite usar el volumen, tengo las siguientes 3 opciones.
Primero, puede crear el volumen con nombre directamente y usarlo como un volumen externo en componer, o como un volumen con nombre en un docker run
o docker service create
mando.
# 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
A continuación, está el --mount
sintaxis que funciona desde docker run
y docker service create
. Esta es una opción bastante larga, y cuando está incrustada una opción delimitada por comas dentro de otra opción delimitada por comas, debe pasar algunas comillas (escapadas para que el shell no las elimine) al comando que se está ejecutando. Tiendo a usar esto para un contenedor único que necesita acceder a NFS (por ejemplo, un contenedor de utilidades para configurar directorios NFS):
# 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
Por último, puede definir el volumen con nombre dentro de su archivo de redacción. Una nota importante al hacer esto, el volumen de nombre solo se crea una vez y no se actualiza con ningún cambio. Entonces, si alguna vez necesita modificar el volumen nombrado, querrá darle un nuevo nombre.
# 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"
...
En cada uno de estos ejemplos:
- El tipo está configurado en
nfs
, nonfs4
. Esto se debe a que la ventana acoplable proporciona una buena funcionalidad en eladdr
campo, pero solo para elnfs
escribe. - los
o
son las opciones que se pasan a mount syscall. Una diferencia entre el mount syscall y el comando mount en Linux es que el dispositivo tiene la parte antes del:
se mudó a unaddr
opción. nfsvers
se utiliza para configurar la versión de NFS. Esto evita retrasos ya que el sistema operativo prueba primero otras versiones de NFS.addr
puede ser un nombre DNS cuando usatype=nfs
, en lugar de solo una dirección IP. Muy útil si tiene varias VPC con diferentes servidores NFS que utilizan el mismo nombre DNS, o si desea ajustar el servidor NFS en el futuro sin actualizar cada montaje de volumen.- Otras opciones como
rw
(lectura-escritura) se puede pasar alo
opción. - los
device
El campo es la ruta en el servidor NFS remoto. Se requiere el colon inicial. Este es un artefacto de cómo el comando mount mueve la dirección IP a laaddr
campo para el syscall. Este directorio debe existir en el host remoto antes de que el volumen se monte en un contenedor. - En el
--mount
sintaxis, ladst
campo es la ruta dentro del contenedor. Para volúmenes con nombre, establezca esta ruta en el lado derecho del montaje de volumen (en la sintaxis corta) en sudocker run -v
mando.
Si tiene problemas de permisos para acceder a un volumen NFS remoto, una causa común que he encontrado son los contenedores que se ejecutan como root, con el servidor NFS configurado como root squash (cambiando todos los accesos de root al usuario de nadie). Debe configurar sus contenedores para que se ejecuten como un UID no root conocido que tenga acceso a los directorios del servidor NFS, o deshabilitar el squash root en el servidor NFS.
Sí, puede hacer referencia directamente a un NFS desde el archivo de redacción:
volumes:
db-data:
driver: local
driver_opts:
type: nfs
o: addr=$SOMEIP,rw
device: ":$PathOnServer"
Y de forma análoga, podría crear un volumen nfs en cada host.
docker volume create --driver local --opt type=nfs --opt o=addr=$SomeIP,rw --opt device=:$DevicePath --name nfs-docker
Si te sientes impulsado, eres capaz de dejar una sección acerca de qué le añadirías a este enunciado.