У меня есть простое python приложение, которое хранит и ищет свои данные в экземпляре Elasticsearch. Приложение python работает в своем собственном контейнере, как и Elasticsearch. Elasticsearch предоставляет порты по умолчанию 9200 и 9300, приложение python предоставляет порт 5000. Тип сети, используемый для Docker, - это пользовательская мостовая сеть. Когда я запускаю оба контейнера, приложение хорошо запускается, оба контейнера видят друг друга по имени контейнера и нормально общаются.
Но с хоста docker (linux) невозможно подключиться к незащищенному порт 5000. Таким образом, простой curl http://localhost:5000/
рендерится в тайм-аут. Docker советов из этой документации: https://docs.docker.com/network/bridge/ не решили эту проблему.
После долгих попыток я попробовал что-то совершенно другое, я попытался подключиться извне docker хост для python приложения. Я был сбит с толку, из любой точки мира я мог сделать curl http://<fqdn>:5000/
и получил заявление. Значит, настоящая проблема решена, потому что я могу подать заявку во внешний мир. (Так что да, приложение внутри контейнера прослушивает 0.0.0.0, как и решение для 90% проблем сети, о которых сообщают другие.)
Но это все еще оставляет меня озадаченным, что вызывает это странное поведение? На моей машине разработки (Windows 10, WSL, Docker рабочий стол, Linux контейнеры) я могу подключиться к службе на локальном хосте: 5000, 127.0.0.1:5000 et c. На моей Linux (производственной) машине все работает, кроме подключения от хоста docker к контейнерам.
Я надеюсь, что кто-то может пролить свет на это, я пытаюсь понять, почему это происходит.
Некоторая релевантная информация
Docker хост:
# ifconfig -a
br-77127ce4b631: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
inet 172.18.0.1 netmask 255.255.0.0 broadcast 172.18.255.255
[snip]
docker0: flags=4099<UP,BROADCAST,MULTICAST> mtu 1500
inet 172.17.0.1 netmask 255.255.0.0 broadcast 172.17.255.255
[snip]
ens3: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
inet 1xx.1xx.199.134 netmask 255.255.255.0 broadcast 1xx.1xx.199.255
# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
1e7f2f7a271b pplbase_api "flask run --host=0.…" 20 hours ago Up 19 hours 0.0.0.0:5000->5000/tcp pplbase_api_1
fdfa10b1ce99 elasticsearch:7.5.1 "/usr/local/bin/dock…" 21 hours ago Up 19 hours 0.0.0.0:9200->9200/tcp, 0.0.0.0:9300->9300/tcp pplbase_elastic_1
# docker network ls
NETWORK ID NAME DRIVER SCOPE
[snip]
77127ce4b631 pplbase_pplbase bridge local
# iptables -L -n
[snip]
ACCEPT tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:5000
Chain FORWARD (policy ACCEPT)
target prot opt source destination
DOCKER-USER all -- 0.0.0.0/0 0.0.0.0/0
DOCKER-ISOLATION-STAGE-1 all -- 0.0.0.0/0 0.0.0.0/0
ACCEPT all -- 0.0.0.0/0 0.0.0.0/0 ctstate RELATED,ESTABLISHED
DOCKER all -- 0.0.0.0/0 0.0.0.0/0
ACCEPT all -- 0.0.0.0/0 0.0.0.0/0 ctstate RELATED,ESTABLISHED
DOCKER all -- 0.0.0.0/0 0.0.0.0/0
Chain DOCKER (2 references)
target prot opt source destination
ACCEPT tcp -- 0.0.0.0/0 172.18.0.2 tcp dpt:9300
ACCEPT tcp -- 0.0.0.0/0 172.18.0.2 tcp dpt:9200
ACCEPT tcp -- 0.0.0.0/0 172.18.0.3 tcp dpt:5000
Chain DOCKER-ISOLATION-STAGE-1 (1 references)
target prot opt source destination
DOCKER-ISOLATION-STAGE-2 all -- 0.0.0.0/0 0.0.0.0/0
DOCKER-ISOLATION-STAGE-2 all -- 0.0.0.0/0 0.0.0.0/0
RETURN all -- 0.0.0.0/0 0.0.0.0/0
Chain DOCKER-ISOLATION-STAGE-2 (2 references)
target prot opt source destination
DROP all -- 0.0.0.0/0 0.0.0.0/0
DROP all -- 0.0.0.0/0 0.0.0.0/0
RETURN all -- 0.0.0.0/0 0.0.0.0/0
Chain DOCKER-USER (1 references)
target prot opt source destination
RETURN all -- 0.0.0.0/0 0.0.0.0/0
Docker составить файл:
version: '3'
services:
api:
build: .
links:
- elastic
ports:
- "5000:5000"
networks:
- pplbase
environment:
- ELASTIC_HOSTS=elastic localhost
- FLASK_APP=app.py
- FLASK_ENV=development
- FLASK_DEBUG=0
tty: true
elastic:
image: "elasticsearch:7.5.1"
ports:
- "9200:9200"
- "9300:9300"
networks:
- pplbase
environment:
- discovery.type=single-node
volumes:
- ${PPLBASE_STORE}:/usr/share/elasticsearch/data
networks:
pplbase:
driver: bridge
После дополнительных копаний в загадке становится все больше и больше. При использовании netcat я могу установить sh соединение
Connection to 127.0.0.1 5000 port [tcp/*] succeeded!
Проверка с помощью netstat, когда клиенты не подключены, см .:
tcp6 0 0 :::5000 :::* LISTEN 27824/docker-proxy
При попытке установить соединение с Dockerhost, соединение сделано:
tcp 0 1 172.20.0.1:56866 172.20.0.3:5000 SYN_SENT 27824/docker-proxy
tcp6 0 0 :::5000 :::* LISTEN 27824/docker-proxy
tcp6 0 0 ::1:58900 ::1:5000 ESTABLISHED 31642/links
tcp6 592 0 ::1:5000 ::1:58900 ESTABLISHED 27824/docker-proxy
Итак, я подозреваю, что теперь некоторые сети Voodoo на хосте docker.