Нельзя сопоставить несколько портов контейнера с одним и тем же портом хоста.Любой контейнер, который появится первым, будет привязан к порту 80, а второй контейнер выбрасывает порт, который уже используется, если вы попытаетесь связать тот же порт.
Для решения этой проблемы вы можете запустить еще одну пустышку Nginx , которая просто делает proxy_pass
до demo1 и demo2 .В этом случае http://app
будет родительским Nginx, а /dev1
будет proxy_pass
до demo1 и /dev2
будет proxy_pass
до demo2 .
Здесь вам просто нужно привязать порт родительского Nginx к хосту.Вам не нужно связывать порты дочернего Nginx, если вы подключаете все это к одной сети и используете docker service discovery .Если вы будете следовать этим правилам, вы обнаружите еще одну проблему , т. Е. Nginx будет кэшировать IP-адреса контейнеров, разрешенных с помощью обнаружения служб, и будет использовать этот IP-адрес, чтобы всегда попадать в контейнеры.После перезапуска дочернего контейнера существует вероятность того, что IP-адрес дочернего элемента может измениться, поэтому родительский Nginx выбрасывает 502 .Чтобы решить эту проблему, вы должны перезапускать родительский Nginx каждый раз, когда вы перезапускаете demo1 или demo2 .Чтобы решить эту проблему, вы должны использовать resolver
как 127.0.0.11
с действительностью в родительском Nginx.Поэтому каждый раз, когда Nginx будет пытаться разрешить IP-адрес после последнего разрешения в соответствии с действительностью.
Я добавил фиктивные файлы конфигурации, суммирующие все вышеперечисленные пункты.
Родительский Nginx составляет:
version: '3'
services:
parent:
image: nginx:alpine
volume:
- ./nginx.conf:/etc/nginx/nginx.conf
ports:
- 80:80
networks:
default:
external:
name: dev
Конфигурация родительского Nginx (./nginx.conf):
server {
listen 80;
resolver 127.0.0.11 valid=5s; #this is local docker DNS and the internal IP getting resolved will be valid only for 5 seconds.
location /app/dev1 {
proxy_pass http://dev1:80;
}
location /app/dev2 {
proxy_pass http://dev2:80;
}
}
docker-compose.yml в ~ / demo1 /
version: '3'
services:
web:
image: nginx:alpine
networks:
default:
aliases:
- dev1
networks:
default:
external:
name: dev
docker-compose.yml в ~ / demo2 /
version: '3'
services:
web:
image: nginx:alpine
networks:
default:
aliases:
- dev2
networks:
default:
external:
name: dev
Теперь вы можете использовать demo1, нажав URL http://app/dev1 и demo2 с использованием http://app/dev2.
Ссылки:
- Обратный прокси NGINX
- NGINX proxy_pass
- NGINX resolver
- Необходимость Docker DNS
- Сеть Docker-контейнеров