Статьи

Docker-контейнер, соединяющий несколько хостов

Связывание с Docker-контейнерами — это важная концепция, так как любое производственное приложение обычно работает в кластере контейнеров на нескольких хостах. Но простая связь с контейнером не позволяет осуществлять связь между хостами.

В чем проблема со связыванием контейнера Docker?

Контейнеры Docker могут обмениваться данными друг с другом, связываясь вручную, как показано в Техническом совете № 66, или организовывая их, используя рис, как показано в Техническом совете № 68 . Оба они используют связывание контейнеров, но им присущи недостатки, заключающиеся в том, что они ограничены одним хостом. Связывание не работает, если контейнеры работают на нескольких хостах.

Каково решение?

В этом техническом совете будет создан образец, встроенный в технические советы № 66 и № 68, и показано, что контейнеры можно подключать, если они работают на нескольких хостах.

Связывание контейнера Docker между несколькими хостами может быть легко выполнено путем явной публикации хоста / порта и использования его из контейнера на другом хосте.

Давайте начнем!

  1. Запустите MySQL контейнер как:
    1
    docker run --name mysqldb -e MYSQL_USER=mysql -e MYSQL_PASSWORD=mysql -e MYSQL_DATABASE=sample -e MYSQL_ROOT_PASSWORD=supersecret -p 5306:3306 -d mysql

    Контейнер MySQL явно перенаправляет порт 3306 на порт 5506 .

  2. Git repo имеет файл customization / execute.sh, который создает источник данных MySQL. Команда выглядит так:
    1
    data-source add --name=mysqlDS --driver-name=mysql --jndi-name=java:jboss/datasources/ExampleMySQLDS --connection-url=jdbc:mysql://$DB_PORT_3306_TCP_ADDR:$DB_PORT_3306_TCP_PORT/sample?useUnicode=true&characterEncoding=UTF-8 --user-name=mysql --password=mysql --use-ccm=false --max-pool-size=25 --blocking-timeout-wait-millis=5000 --enabled=true

    Эта команда создает ресурс JDBC для WildFly, используя jboss-cli. Он использует $DB_PORT_3306_TCP_ADDR и $DB_PORT_3306_TCP_PORT которые определены для переменных среды, связанных с контейнером . Схема, по которой создаются переменные окружения для контейнеров, довольно странная. Он выставляет номер порта в самом имени переменной. Я надеюсь, что это улучшится в следующих выпусках.

    Эту команду необходимо обновить, чтобы вместо нее можно было использовать явный хост / порт.

    Так что обновите команду:

    1
    data-source add --name=mysqlDS --driver-name=mysql --jndi-name=java:jboss/datasources/ExampleMySQLDS --connection-url=jdbc:mysql://$MYSQL_HOST:$MYSQL_PORT/sample?useUnicode=true&characterEncoding=UTF-8 --user-name=mysql --password=mysql --use-ccm=false --max-pool-size=25 --blocking-timeout-wait-millis=5000 --enabled=true

    Единственным изменением в команде является использование $MYSQL_HOST и $MYSQL_PORT . Эта команда уже существует в файле, но закомментирована. Так что просто прокомментируйте предыдущий и раскомментируйте этот.

  3. Создайте образ и запустите его как:
    1
    2
    docker build -t arungupta/wildfly-mysql-javaee7 .
    docker run --name mywildfly -e MYSQL_HOST=<IP_ADDRESS> -e MYSQL_PORT=5306 -p 8080:8080 -d arungupta/wildfly-mysql-javaee7

    Обязательно замените <IP_ADDRESS> IP-адресом вашего хоста. Для удобства я запустил его на том же хосте. IP-адрес в этом случае может быть легко получен с помощью boot2docker ip .

  4. Быстрая проверка развертывания может быть выполнена путем доступа к конечной точке REST:
    1
    2
    curl http://192.168.59.103:8080/employees/resources/employees/
    <?xml version="1.0" encoding="UTF-8" standalone="yes"?><collection><employee><id>1</id><name>Penny</name></employee><employee><id>2</id><name>Sheldon</name></employee><employee><id>3</id><name>Amy</name></employee><employee><id>4</id><name>Leonard</name></employee><employee><id>5</id><name>Bernadette</name></employee><employee><id>6</id><name>Raj</name></employee><employee><id>7</id><name>Howard</name></employee><employee><id>8</id><name>Priya</name></employee></collection>

Благодаря этому ваш WildFly и MySQL могут работать на двух отдельных хостах, никакой специальной настройки не требуется.

Наслаждайтесь!

Docker позволяет связывать контейнеры между хостами с помощью Ambassador Containers, но добавляет избыточный переход для доступа к службе. Более чистое решение — использовать Kubernetes или Swarm, об этом позже.

Марек также написал в блоге о более сложном решении в разделе «Подключение контейнеров Docker к нескольким хостам» .