Как подключить один файл в томе

Я пытаюсь закрепить приложение php. В файле dockerfile я загружаю архив, извлекаю его и т.д.

Все работает отлично, однако, если новая версия будет выпущена, и я обновляю файл докеров, я должен переустановить приложение, потому что config.php перезаписывается.

Поэтому я думал, что смогу монтировать файл как том, как я делаю с базой данных.

Я пробовал это двумя способами: с томом и прямым путем.

докер-Compose:

version: '2'
services:
  app:
    build: src
    ports:
      - "8080:80"
    depends_on:
      - mysql
    volumes:
      -  app-conf:/var/www/html/upload
      -  app-conf:/var/www/html/config.php
    environment:
      DB_TYPE: mysql
      DB_MANAGER: MysqlManager

  mysql:
    image: mysql:5.6
    container_name: mysql
    volumes:
      - mysqldata:/var/lib/mysql
    ports:
      - 3306:3306
    environment:
      MYSQL_ROOT_PASSWORD:
      MYSQL_DATABASE:
      MYSQL_USER:
      MYSQL_PASSWORD:

volumes:
  mysqldata:
  app-conf:

Это приводит к ошибке:

И я попробовал это с заданным путем, как смонтированный том.

/src/docker/myapp/upload:/var/www/html/upload
/src/docker/myapp/upload:/var/www/html/config.php

Однако оба способа не работают. С установленным томом я вижу, что загрузка создается.

Но с

/var/www/html/config.php\\"вызвал \\" не каталог \\"\" "

Если я попробую с помощью /src/docker/myapp/upload/config.php: /var/www/html/config.php

Docker создает папку для загрузки, а затем папку config.php. Не файл.

Или существует другой способ сохранения конфигурации?

Ответ 1

TL; DR/Примечание:

Если вместо файла, который вы пытаетесь смонтировать, создается каталог, возможно, вам не удалось указать действительный и абсолютный путь. Это распространенная ошибка в тихом и запутанном режиме сбоя.

Тома файлов создаются таким образом в Docker (пример абсолютного пути (можно использовать переменные env), и вам нужно указать имя файла):

    volumes:
      - /src/docker/myapp/upload:/var/www/html/upload
      - /src/docker/myapp/upload/config.php:/var/www/html/config.php

Вы также можете сделать:

    volumes:
      - ${PWD}/upload:/var/www/html/upload
      - ${PWD}/upload/config.php:/var/www/html/config.php

Если вы запускаете docker-compose из папки /src/docker/myapp

Ответ 2

У меня была аналогичная проблема. Я пытался импортировать свой файл конфигурации в свой контейнер, чтобы я мог исправлять его каждый раз, когда мне нужно, без повторного создания изображения.

Я имею в виду, я думал, что приведенная ниже команда будет отображать $(pwd)/config.py с хоста Docker в /root/app/config.py в контейнер в виде файла.

docker run -v $(pwd)/config.py:/root/app/config.py my_docker_image

Однако он всегда создавал каталог с именем config.py, а не файл.

в поисках подсказки, я нашел причину (отсюда)

Если вы используете -v или - -v olume для привязки монтирования файла или каталога, который еще не существует на хосте Docker, -v создаст конечную точку для вас. Он всегда создается как каталог.

Поэтому он всегда создается как каталог, потому что у моего узла докера нет $(pwd)/config.py.

Даже если я создам config.py в хосте docker. $(pwd)/config.py просто перезагружает /root/app/config.py не экспортируя /root/app/config.py.

Ответ 3

Для любого, кто использует контейнер Windows, такой как я, знайте, что вы НЕ МОЖЕТЕ связывать или монтировать отдельные файлы, используя контейнер Windows.

Следующие примеры не будут работать при использовании контейнеров на основе Windows, так как местом назначения тома или монтирования привязки внутри контейнера должен быть один из: несуществующего или пустого каталога; или диск, отличный от C :. Кроме того, источником подключения bind должен быть локальный каталог, а не файл.

net use z: \\remotemachine\share

docker run -v z:\foo:c:\dest ...

docker run -v \\uncpath\to\directory:c:\dest ...

docker run -v c:\foo\somefile.txt:c:\dest ...

docker run -v c:\foo:c: ...

docker run -v c:\foo:c:\existing-directory-with-contents ...

Трудно заметить, но это там

Ссылка на проблему Github относительно отображения файлов в контейнер Windows

Ответ 4

Используйте монтировать (--mount) вместо громкости (-v)

Дополнительная информация: https://docs.docker.com/storage/bind-mounts/

Пример:

Убедитесь, что /tmp/a.txt существует на хосте докера

docker run -it --mount type=bind,source=/tmp/a.txt,target=/root/a.txt alpine sh

Ответ 5

Вы также можете использовать относительный путь к файлу docker-compose.yml например так (проверено на хосте Windows, контейнере Linux):

 volumes:
      - ./test.conf:/fluentd/etc/test.conf

Ответ 6

Для меня проблема заключалась в том, что у меня была сломанная символическая ссылка на файл, который я пытался установить в контейнер

Ответ 7

У меня была такая же проблема на Windows, Docker 18.06.1-ce-win73 (19507).

Извлечение и повторное добавление общего диска через панель настроек Docker, и все снова заработало.

Ответ 8

В Windows, если вам нужна переменная $ {PWD} env в вашем docker-compose.yml, вы можете создать файл .env в том же каталоге, что и ваш файл docker-compose.yml, а затем вставить вручную местоположение вашей папки.

CMD (pwd_var.bat):

echo PWD=%cd% >> .env

Powershell (pwd_var.ps1):

$PSDefaultParameterValues['Out-File:Encoding'] = 'utf8'; echo "PWD=$(get-location).path" >> .env

Есть больше полезных возможностей для docker-compose переменных .env: https://docs.docker.com/compose/reference/envvars/, особенно для COMPOSE_CONVERT_WINDOWS_PATHS env COMPOSE_CONVERT_WINDOWS_PATHS которая позволяет docker compose принимать путь к Windows с символом baskslash "\".

Если вы хотите поделиться файлом в Windows, файл должен существовать до того, как вы поделитесь им с контейнером.

Ответ 9

Может быть, это кому-то поможет.

У меня была эта проблема и все перепробовал. Привязки томов выглядели хорошо, и даже если я смонтировал каталог (не файлы), у меня были имена файлов в смонтированном каталоге, но они были смонтированы как каталоги.

Я попытался снова включить общие диски, и Docker пожаловался, что брандмауэр активен.

После отключения брандмауэра все работало нормально.

Ответ 10

У меня такая же проблема на моей Windows 8.1

Оказалось, что это связано с регистрозависимостью пути. Я вызвал docker-compose up из каталога cd/c/users/alex/ и внутри контейнера файл превратился в каталог.

Но когда я сделал cd/c/Users/alex/ (а не Users прописными буквами) и вызвал docker-compose up оттуда, это сработало.

В моей системе оба пользователя dir и Alex dir пишутся с большой буквы, хотя кажется, что значение имеет только Users dir.