
У меня есть следующие файлы-примеры
docker-compose.yml
version: '3'
services:
web:
image: webapp:${VARIABLE_A:-${VARIABLE_B}}
env.conf
VARIABLE_B=123
VARIABLE_A
не установлено специально, поэтому оно должно вернуться кVARIABLE_B
Docker Compose может разрешить значение по умолчанию переменной среды, однако docker stack deploy
не может сделать то же самое разрешение
user@laptop:~$ docker compose --env-file ./env.conf convert
name: dockercomposetest
services:
web:
image: webapp:123
networks:
default: null
networks:
default:
name: dockercomposetest_default
user@laptop:~$ env $(cat ./env.conf | xargs) docker stack deploy --compose-file docker-compose.yml stack
Creating service stack_web
failed to create service stack_web:
Error response from daemon:
rpc error:
code = InvalidArgument desc = ContainerSpec: "webapp:${VARIABLE_B}" is not a valid repository/tag
Как вы можете видеть, при использовании docker stack deploy
он обнаруживает ${VARIABLE_A:-${VARIABLE_B}}
переменную окружения, которая, поскольку VARIABLE_A
не установлена, должна иметь значение по умолчанию, ${VARIABLE_B}
однако он не разрешает ее значение, которое является123
Очевидно, что webapp не существует, это всего лишь пример, но приведенный выше вывод ошибки должен быть таким:
user@laptop:~$ env $(cat ./env.conf | xargs) docker stack deploy --compose-file docker-compose.yml stack
Creating service stack_web
failed to create service stack_web:
Error response from daemon:
rpc error:
code = InvalidArgument desc = ContainerSpec: "webapp:123" is not a valid repository/tag
Почему это происходит? Есть ли какие-то обходные пути?
решение1
Для справки см. mobyDocker Stack Deploy в версии 1.13 не загружает файл .env, как это делает docker-compose up. КонкретноКомментарий от kinghuang
«Мои разработчики используют конфигурацию docker-compose для предварительной обработки проектов Docker Compose перед их передачей в развертывание стека docker. Вы можете сделать это одной строкой:
docker stack deploy -c <(docker-compose config) stack-name-here
Таким образом, все функции Docker Compose, включая обработку .env, будут полностью применены».
решение2
Обходной путь, который я в итоге применил, docker stack deploy
— это envsubst
замена переменных окружения
user@laptop:~$ env $(cat ./env.conf | xargs) envsubst < ./docker-compose.yml | docker stack deploy --compose-file - stack
В документации говорится, что при использовании --compose-file -
он принимает stdin
файл docker compose, поэтому по сути это сначала разрешает все переменные в , docker-compose.yml
а затем передает результат с помощью конвейера вdocker stack deploy
решение3
Вот еще один хороший способ, как вы можете преодолеть эту проблему. Вам нужно создать файл ".env" со всеми переменными, которые вы хотите добавить в среду, например: APP_NAME=Example
. Затем в вашем stack-compose.yml вы можете объявить его следующим образом:
version: "3.9"
services:
myservice:
env_file:
- .env
После этого необходимо выполнить следующую команду:
docker stack config -c stack-compose.yml | docker stack deploy -c - mystackname
Что вставит переменные, объявленные вами в файле .env, в stack_compose.yml следующим образом:
version: "3.9"
services:
myservice:
environment:
APP_NAME: "Example"
По этой ссылкеКак передать переменные env в стек Docker Swarm
Вы найдете очень хорошее объяснение, как это сделать. У меня была та же проблема, и я ее преодолел таким образом. С уважением