Как прочитать информацию о сопоставлении портов докера? - PullRequest
0 голосов
/ 08 июля 2019

Я только начал изучать Docker, и я немного запутался с отображением портов в Docker. У меня есть контейнер (который запускает службу MySQL), как показано ниже:

CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS

59efytd163d3        myapp:mysql         "docker-entrypoint.s…"   10 months ago       Up 5 minutes        0.0.0.0:9991->3306/tcp  

Для поля PORTS что означает 0.0.0.0:9991->3306/tcp?

Я проверил номер порта mysql, работающего вне контейнера:

john@MacBook-Pro:~/Documents$ lsof -n -P -i TCP | grep mysql
mysqld     1742 john   58u  IPv4 0xd3c7de51ef6d2a49      0t0  TCP 127.0.0.1:3306 (LISTEN)

Как видите, порт - 3306, поэтому я подумал, что номер порта для mysql, работающего внутри контейнера, должен быть 9991. Однако после того, как я попал в контейнер и проверил mysql:

mysql> SHOW GLOBAL VARIABLES LIKE 'PORT'
    -> ;
+---------------+-------+
| Variable_name | Value |
+---------------+-------+
| port          | 3306  |
+---------------+-------+
1 row in set (0.00 sec)

Это также показывает 3306.

Обе службы mysql, работающие внутри и снаружи контейнера, имеют номер порта 3306. Где тогда означает 0.0.0.0:9991->3306/tcp? к чему относится 0.0.0.0:9991?

1 Ответ

2 голосов
/ 08 июля 2019

Docker запускает контейнеры в виртуальных сетях:

docker network ls
NETWORK ID          NAME                 DRIVER              SCOPE
1234567890ab        bridge               bridge              local
cdef01234567        deployment_default   bridge              local
890abcdef012        host                 host                local
34567890abcd        none                 null                local

Эти сопоставления портов связывают порты на вашем хост-компьютере с контейнерами, работающими в этих сетях.

Думайте о каждом контейнере как о своем локальном хосте свсе доступные ему порты.В этом случае ваш экземпляр MySQL предоставляет порт 3306 в своем контейнере.Это необходимо, потому что двоичный файл в контейнере также работает на 3306.Это объясняет, почему в контейнере вы видите 3306.

. Очень удобно, когда вы запускаете контейнер, Docker предоставляет механизм для переназначения портов контейнера (например, 3306) на другие порты (например,9991) на вашем хост-компьютере.

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

Итак, вы определяете отображение порта, как вы сделали.В вашем примере с локальной рабочей станции (хоста) вы можете получить доступ к экземпляру контейнера MySQL на localhost:9991, и Docker переназначит трафик этого порта на порт контейнера MySQL 3306, и контейнер направит его в двоичный файл MySQL (также на 3306).

Итак: 0.0.0.0:9991->3306/tcp означает:

  • 0.0.0.0 (псевдоним для любого адаптера на localhost)
  • 9991 порткарты трафика на порт этого контейнера 3306
  • Использование TCP (еще один протокол, который вы увидите UDP)

Три дополнительных примечания:

  • Dockerfile этого изображения может включать, например, EXPOSE 3306.Это чисто документально и никоим образом не влияет на команду docker run ... --publish=XXXX/3306...
  • Контейнеру не нужно публиковать порты на локальном хосте.Это необходимо сделать только в том случае, если к образу контейнера необходимо получить доступ с хоста.Если вы называете свои контейнеры и размещаете их в пользовательских сетях или используете Docker Compose, один контейнер может получить доступ к портам другого контейнера без доступа к портам для хоста.Предоставление таких портов должно быть (!) Соображением безопасности.
  • Когда вы запускаете образ контейнера, Docker использует сеть по умолчанию.Разрешение сопоставления портов (0.0.0.0:XXXX/YYYY) на самом деле является комбинацией определения того, какой контейнер (разрешение имени хоста) и какой порт.
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...