library - Copiando archivos desde el host al contenedor Docker
download docker image (30)
Estoy intentando crear una solución de copia de seguridad y restauración para los contenedores de Docker con los que trabajamos.
Tengo una imagen base de Docker que he creado, ubuntu:base
, y no quiero tener que reconstruirla cada vez con un archivo Docker para agregarle archivos.
Quiero crear un script que se ejecute desde la máquina host y cree un nuevo contenedor utilizando la imagen de ubuntu:base
Docker y luego copie los archivos en ese contenedor.
¿Cómo puedo copiar archivos desde el host al contenedor?
Muy fácil
Cree un nuevo archivo docker y use la imagen existente como su base.
FROM myName/myImage:latest ADD myFile.py bin/myFile.py
Luego construye el contenedor:
docker build .
Obtenga el nombre del contenedor o la identificación del contenedor corto:
$ docker ps
Obtener la identificación del contenedor completo:
$ docker inspect -f ''{{.Id}}'' SHORT_CONTAINER_ID-or-CONTAINER_NAME
Copiar archivo:
$ sudo cp path-file-host /var/lib/docker/aufs/mnt/FULL_CONTAINER_ID/PATH-NEW-FILE
EJEMPLO:
$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
d8e703d7e303 solidleon/ssh:latest /usr/sbin/sshd -D cranky_pare
$ docker inspect -f ''{{.Id}}'' cranky_pare
o
$ docker inspect -f ''{{.Id}}'' d8e703d7e303
d8e703d7e3039a6df6d01bd7fb58d1882e592a85059eb16c4b83cf91847f88e5
$ sudo cp file.txt /var/lib/docker/aufs/mnt/**d8e703d7e3039a6df6d01bd7fb58d1882e592a85059eb16c4b83cf91847f88e5**/root/file.txt
Con Docker 1.8, docker cp
puede copiar archivos del host al contenedor. Consulte la publicación del blog de Docker Anunciando Docker 1.8: Content Trust, Toolbox y Actualizaciones para el Registro y la Orquestación .
Cuando no tenga un directorio definido como un volumen en el Dockerfile, funcionará / var / lib / docker / aufs / mnt //. Pero hay casos en los que el directorio dentro del contenedor se define como un volumen. En este caso, los contenidos en aufs / mnt / * / y los contenidos vistos por el contenedor son diferentes.
Deberá inspeccionar el contenedor utilizando la ventana acoplable inspeccionar y luego buscar los volúmenes. Allí encontrará una mención para algo como / var / lib / docker / vfs / dir / fe940b ... (el id). Deberá agregar / modificar los archivos aquí en lugar de en aufs / mnt / *.
La parte confusa es que los archivos también aparecen en / aufs / mnt / *. Pasé bastante tiempo rascándome la cabeza por qué los cambios aquí no me funcionaron. Espero que esto ayude a alguien.
El comando cp
se puede utilizar para copiar archivos. Un archivo específico se puede copiar como:
docker cp foo.txt mycontainer:/foo.txt
docker cp mycontainer:/foo.txt foo.txt
Para enfatizar, mycontainer
es una ID de contenedor , no una ID de imagen .
Varios archivos contenidos en la carpeta src
se pueden copiar en la carpeta de target
usando:
docker cp src/. mycontainer:/target
docker cp mycontainer:/src/. target
Referencia: Docker CLI docs para cp
En las versiones de Docker anteriores a la 1.8, solo era posible copiar archivos de un contenedor al host. No desde el host a un contenedor.
En caso de que no quede claro para alguien como yo lo que significa mycontainer
en @ h3nrik, en realidad es la identificación del contenedor. Para copiar un archivo WarpSquare.mp4
en /app/example_scenes/1440p60
de un contenedor de docker salido a la carpeta actual, utilicé esto.
docker cp `docker ps -q -l`:/app/example_scenes/1440p60/WarpSquare.mp4 .
donde la docker ps -q -l
extrae el ID de contenedor de la última instancia salida. En caso de que no sea un contenedor salido, puede obtenerlo mediante el docker container ls
o el docker ps
En un entorno docker, todos los contenedores se encuentran en el directorio:
/var/lib/docker/aufs/required-docker-id/
Para copiar el directorio / archivo de origen a cualquier parte del contenedor, escriba el comando dado:
sudo cp -r mydir/ /var/lib/docker/aufs/mnt/required-docker-id/mnt/
Esta es una respuesta directa a la pregunta "Copia de archivos del host al contenedor Docker" que se plantea en esta pregunta en el título.
Prueba la docker cp
. Es la forma más fácil de hacerlo y funciona incluso en mi Mac. Uso:
docker cp /root/some-file.txt some-docker-container:/root
Esto copiará el archivo some-file.txt
en el directorio /root
en su máquina host en el contenedor de Docker denominado some-docker-container
en el directorio /root
. Está muy cerca de la sintaxis de copia segura. Y como se muestra en el post anterior, puedes usarlo viceversa. Es decir, también copia los archivos del contenedor al host.
Y antes de enlazar este post, ingrese docker cp --help
. Leer la documentación puede ser muy útil, a veces ...
Si no te gusta de esa manera y quieres volúmenes de datos en tu contenedor ya creado y en ejecución, entonces la recreación es tu única opción hoy. Consulte también ¿Cómo puedo agregar un volumen a un contenedor Docker existente? .
Este es un programa en línea para copiar un solo archivo mientras se ejecuta un contenedor tomcat.
docker run -v /PATH_TO_WAR/sample.war:/usr/local/tomcat/webapps/myapp.war -it -p 8080:8080 tomcat
Esto copiará el archivo war en el directorio webapps y hará que su aplicación se ejecute en muy poco tiempo.
Hay buenas respuestas, pero demasiado específicas. Descubrí que docker ps
es una buena manera de obtener la identificación del contenedor en la que está interesado. Entonces, haga
mount | grep <id>
Para ver donde está montado el volumen. Eso es
/var/lib/docker/devicemapper/mnt/<id>/rootfs/
para mí, pero podría ser una ruta diferente según el sistema operativo y la configuración. Ahora simplemente copia los archivos a esa ruta.
Usar -v
no siempre es práctico.
La forma más limpia es montar un directorio de host en el contenedor al iniciar el contenedor:
{host} docker run -v /path/to/hostdir:/mnt --name my_container my_image
{host} docker exec -it my_container bash
{container} cp /mnt/sourcefile /path/to/destfile
La mejor manera de copiar archivos al contenedor que encontré es montar un directorio en el host usando la opción -v
del comando de ejecución de la ventana acoplable.
La siguiente es una forma bastante fea de hacerlo, pero funciona.
docker run -i ubuntu /bin/bash -c ''cat > file'' < file
La solución se da a continuación,
Desde el shell Docker,
root@123abc:/root# <-- get the container ID
Desde el host
cp thefile.txt /var/lib/docker/devicemapper/mnt/123abc<bunch-o-hex>/rootfs/root
El archivo se copiará directamente en la ubicación donde se encuentra el contenedor en el sistema de archivos.
Mi método favorito:
CONTENEDORES:
CONTAINER_ID=$(docker ps | grep <string> | awk ''{ print $1 }'' | xargs docker inspect -f ''{{.Id}}'')
archivo.txt
mv -f file.txt /var/lib/docker/devicemapper/mnt/$CONTAINER_ID/rootfs/root/file.txt
o
mv -f file.txt /var/lib/docker/aufs/mnt/$CONTAINER_ID/rootfs/root/file.txt
Montaría y luego ejecutaría la imagen con un demonio, cualquiera que se haya dado aquí;
docker run -d -v /blah1/blah2:/mnt --name mntcontainer ubuntu /bin/sh -c "while true; do echo hello world; sleep 1; done"
entonces
docker exec -it mntcontainer bash
Muchos de los que encuentran esta pregunta pueden tener el problema de copiar archivos en una imagen de Docker mientras se está creando (lo hice).
En ese caso, puede usar el comando COPY
en el Dockerfile
que usa para crear la imagen.
Otra solución es usar el viejo scp
bueno. Esto es útil en el caso de que necesite copiar un directorio.
Desde su host ejecute:
scp FILE_PATH_ON_YOUR_HOST IP_CONTAINER:DESTINATION_PATH
scp foo.txt 172.17.0.2:foo.txt
En el caso de que necesite copiar un directorio:
scp -r DIR_PATH_ON_YOUR_HOST IP_CONTAINER:DESTINATION_PATH
scp -r directory 172.17.0.2:directory
Asegúrese de instalar ssh en su contenedor también.
apt-get install openssh-server
Otra solución para copiar archivos en un contenedor en ejecución es usar tar:
tar -c foo.sh | docker exec -i theDockerContainer /bin/tar -C /tmp -x
Copia el archivo foo.sh
en /tmp
del contenedor.
Edición: Eliminar reduntant -f
, gracias al comentario de Maarten .
Para copiar archivos / carpetas entre un contenedor y el sistema de archivos local, escriba el comando:
docker cp {SOURCE_FILE} {DESTINATION_CONTAINER_ID}:/{DESTINATION_PATH}
Por ejemplo,
docker cp /home/foo container-id:/home/dir
Para obtener el ID de Contianer, escriba el comando dado:
docker ps
El contenido anterior está tomado de docker.com .
Para copiar un archivo del host al contenedor en ejecución
docker exec -i $CONTAINER /bin/bash -c "cat > $CONTAINER_PATH" < $HOST_PATH
Basado en la respuesta de Erik y los comentarios de Mikl y z0r.
Probé la mayoría de las soluciones (upvoted) aquí, pero en la ventana acoplable 17.09 (en 2018) ya no existe la carpeta / var / lib / docker / aufs.
Este sencillo docker cp
resolvió esta tarea.
docker cp c:/path/to/local/file container_name:/path/to/target/dir/
¿Cómo obtener container_name? (Hay una sección de NAMES
. No uses IMAGE
.)
docker ps
Si el host es CentOS o Fedora, hay un proxy NO en /var/lib/docker/aufs
, pero está bajo /proc
:
cp -r /home/user/mydata/* /proc/$(docker inspect --format "{{.State.Pid}}" <containerid>)/root
Este cmd copiará todo el contenido del directorio de data
en /
del contenedor con el ID "containerid".
Si necesita hacer esto en un contenedor en ejecución, puede usar el docker exec (agregado en 1.3).
Primero, encuentre el nombre o identificación del contenedor:
$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
b9b7400ddd8f ubuntu:latest "/bin/bash" 2 seconds ago Up 2 seconds elated_hodgkin
En el ejemplo anterior podemos usar b9b7400ddd8f
o elated_hodgkin
.
Si desea copiar todo en /tmp/somefiles
en el host a /var/www
en el contenedor:
$ cd /tmp/somefiles
$ tar -cv * | docker exec -i elated_hodgkin tar x -C /var/www
Luego podemos ejecutar exec /bin/bash
en el contenedor y verificar que funcionó:
$ docker exec -it elated_hodgkin /bin/bash
root@b9b7400ddd8f:/# ls /var/www
file1 file2
Si usa Windows como host, puede usar WinSCP para conectarse a Docker y transferir archivos a través de la GUI.
Si está en Linux, el comando scp
también funcionará a través del terminal.
Simplemente copio el archivo directamente desde donde se encuentra el contenedor desde la máquina host.
Por ejemplo:
Primero averigua la identificación del contenedor:
root@**3aed62678d54**:/home#
Y luego desde el host, digamos que el archivo está en el directorio de inicio:
root@saasdock:/home/dnepangue# cp cheering_nasa.gif /var/lib/docker/aufs/mnt/**3aed62678d54**a5df47a4a00a58bb0312009c2902f8a37498a1427052e8ac454b/home/
De vuelta al contenedor ...
root@**3aed62678d54**:/home# ls cheering_nasa.gif
Simplemente puede rastrear la dirección IP de su máquina local usando
ifconfig
Luego simplemente ingrese a su contenedor Docker y escriba
scp user_name@ip_address:/path_to_the_file destination
En cualquier caso, si no tiene un cliente y un servidor SSH instalados, simplemente instálelo usando:
sudo apt-get install openssh-server
Sintaxis de contenedor arriba:
docker run -v /HOST/folder:/Container/floder
En archivo docker
COPY hom* /myFolder/ # adds all files starting with "hom"
COPY hom?.txt /myFolder/ # ? is replaced with any single character, e.g., "home.txt"
Suponiendo que el contenedor ya se está ejecutando, escriba el comando dado:
# cat /path/to/host/file/ | docker exec -i -t <container_id> bash -c "/bin/cat > /path/to/container/file"
Para compartir archivos usando un directorio compartido, ejecute el contenedor escribiendo el comando dado:
# docker run -v /path/to/host/dir:/path/to/container/dir ...
Nota: Los problemas con los permisos pueden surgir ya que los usuarios del contenedor no son los mismos que los usuarios del host.
tar
y docker cp
son una buena combinación para copiar todo en un directorio.
Crear un contenedor de volumen de datos
docker create --name dvc --volume /path/on/container cirros
Para preservar la jerarquía de directorios
tar -c -C /path/on/local/machine . | docker cp - dvc:/path/on/container
Revisa tu trabajo
docker run --rm --volumes-from dvc cirros ls -al /path/on/container