Масштабирование Docker Containers с изолированными сетями
Я использую docker-compose (v 3.3) и у меня есть набор служб, как показано ниже.
version: '3.3'
services:
jboss:
build:
context: .
dockerfile: jboss/Dockerfile
ports:
- 8080
depends_on:
- mysql
- elasticsearch
networks:
- ${NETWORK}
# - front-tier
# - back-tier
mysql:
hostname: mysql
image: mysql:latest
ports:
- 3306
networks:
- ${NETWORK}
# - back-tier
elasticsearch:
image: elasticsearch:1.7.3
ports:
- 9200
networks:
- ${NETWORK}
# - back-tier
networks:
# front-tier:
# driver: bridge
Проблема / вопрос связан с возможностью изолировать эти сервисы, когда я масштабирую свои контейнеры в некоторой подсети (кстати, я здесь не использую swarm) в том смысле, что jboss1 может видеть только mysql1 и asticsearch1. То же самое для jboss2 - mysql2 - es2 и так далее. Я знаю, что это довольно странно, но задача состоит в том, чтобы распараллелить некоторые тесты, и они должны быть полностью изолированы.
Как вы, вероятно, поняли, я пробовал некоторые подходы (которые прокомментированы в compose) для определения некоторых сетей, но если я масштабирую контейнеры, они, очевидно, будут в одной сети - что означает, что я мог бы случайно пинговать на MySQL -n из jboss-1.
Затем я попробовал другой подход, объясненный здесь Аруном Гуптой http://blog.arungupta.me/docker-bridge-overlay-network-compose-variable-substitution/ где он упомянул подстановку переменных в атрибуте сети (для этого ${NETWORK} там). Но оказывается, что если я попытаюсь "поднять" свои контейнеры через:
NETWORK=isolated-net1 docker-compose up -d
а потом
NETWORK=isolated-net2 docker-compose up -d
он не будет масштабировать контейнеры, но вместо этого воссоздает их все:
Recreating docker_mysql_1 ...
Recreating docker_elasticsearch_1 ...
Recreating docker_jboss_1 ...
В двух словах: есть ли способ изолировать группу служб при выполнении docker-compose up --scale
?
Спасибо
1 ответ
Что ж, получается, что после нескольких дней, когда я изо всех сил пытался найти правильное готовое решение проблемы, возможный способ достичь этого (на самом деле, тот, который подходит мои потребности) делал следующее:
I. Создание определенного тома для экземпляра, который будет вызывать другие контейнеры (в данном случае, JBoss):
jboss:
build:
context: jboss
dockerfile: Dockerfile
volumes:
- /var/run/docker.sock:/var/run/docker.sock
# ... omitting the rest
II. Немного отредактирую мой Dockerfile с помощью скрипта, который действительно делает изоляцию:
FROM my-private-jboss:latest
ADD isolateNetwork.sh /opt/jboss/jboss-eap/jboss-as/server/default/bin/isolateNetwork.sh
RUN chmod +x /opt/jboss/jboss-eap/jboss-as/server/default/bin/isolateNetwork.sh
CMD ["/opt/jboss/jboss-eap/jboss-as/server/default/bin/isolateNetwork.sh"]
III. Наконец, isolateNetwork.sh (предупреждение: мне пришлось установить jq на мой контейнер JBoss, чтобы помочь в этих извлечениях из docker API):
#!/usr/bin/env bash
curl -s --unix-socket /var/run/docker.sock http://localhost/containers/$(hostname)/json > container.json
export DOCKER_CONTAINER_NUMBER=$(cat container.json | jq -r '.Config.Labels["com.docker.compose.container-number"]')
export DOCKER_PROJECT_NAME=$(cat container.json | jq -r '.Config.Labels["com.docker.compose.project"]')
export MYSQL_CONTAINER_NAME=${DOCKER_PROJECT_NAME}_mysql_${DOCKER_CONTAINER_NUMBER}
export MYSQL_IP=$(curl -s --unix-socket /var/run/docker.sock http://localhost/containers/$MYSQL_CONTAINER_NAME/json | jq -r '.NetworkSettings.Networks[].IPAddress')
#Now it's just required to edit the Datasources
find . -iname "MySql*-ds.xml" -exec sed -i s/mysql:3306/${MYSQL_CONTAINER_NAME}:3306/g {} +
Как видите, том, созданный на шаге 1, служит для доступа к API-интерфейсу докера из контейнера. Таким образом, я мог бы запросить упомянутую информацию и отредактировать конфигурацию так, чтобы она вызывала то же самое DOCKER_CONTAINER_NUMBER
, Кроме того, важно упомянуть, что моя команда масштабирования имеет очень специфическое требование: каждый Jboss будет иметь одинаковое количество источников данных, что подразумевает, что DOCKER_CONTAINER_NUMBER
будет когда-либо соответствовать.
docker-compose up --scale jboss=%1 --scale elasticsearch=%1 --scale mysql=%1 --no-recreate -d