将容器绑定到特定主机 VLAN
Binding containers to a specific host VLAN
我有一个连接到多个 VLAN 的主机,这些 VLAN 在我的路由器上具有特定的路由规则,它们具有不同的属性。
我在每个 VLAN 的 VM 中看到了关于 运行 docker 的其他建议,但这看起来也很丑陋和混乱。
例如
/etc/network/interfaces:
# Is routed out a VPN on my router
auto bond0.3
iface bond0.3 inet dhcp
iface bond0.3 inet6 auto
# Is null routed at my router (LAN only)
auto bond0.4
iface bond0.4 inet dhcp
dns-nameserver 192.168.3.1
iface bond0.4 inet6 auto
# Routed directly to my ISP for containers only
auto bond0.7
iface bond0.7 inet dhcp
iface bond0.7 inet6 auto
我在名为“external_7”的 docker 接口上使用了 macvlan 接口:
networks:
external_v7:
name: external_v7
driver: macvlan
driver_opts:
parent: bond0.7
enable_ipv6: false
ipam:
config:
- subnet: 192.168.7.0/24
gateway: 192.168.7.1
ip_range: 192.168.7.128/26
接下来我在 VPN 后面有一个 Bittorrent 客户端,我有单独的 VPN 隧道容器而不在我的路由器上使用它的主要原因是因为在下载某些东西时它阻塞了隧道,我无法使用它对于其他任何事情,所以我有一个用于 Bittorrent 的专用 VPN 隧道:
services:
vpn_bittorrent:
extends:
file: ../docker-vpn/docker-compose-vpn.yml
service: openvpn-client
container_name: vpn_bittorrent
networks:
external_v7:
ipv4_address: 192.168.7.128
volumes:
- /mnt/data/container_data/vpn:/data/vpn
ports:
- 192.168.7.128:26129:26129
- 192.168.7.128:26129:26129/udp
扩展自:
services:
openvpn-client:
image: ghcr.io/wfg/openvpn-client
cap_add:
- NET_ADMIN
devices:
- /dev/net/tun
restart: unless-stopped
我终于有了 qbittorrent 运行:
qbittorrent:
image: ghcr.io/linuxserver/qbittorrent
container_name: qbittorrent
network_mode: service:vpn_bittorrent
environment:
- PUID=1004
- PGID=1003
- WEBUI_PORT=8080
volumes:
- /mnt/data/container_data/qbittorrent:/config
- /mnt/data/shared/incoming:/mnt/shared/incoming
restart: unless-stopped
现在当然我喜欢在这前面有一个反向代理,因为我喜欢使用标准端口,如 :443 或其他。
web:
image: nginx:stable-alpine
container_name: web
hostname: web.internal
networks:
external_v4:
ipv4_address: 192.168.4.133
volumes:
- /mnt/data/container_data/web/nginx/auth-basic.conf:/etc/nginx/auth-basic.conf:ro
- /mnt/data/container_data/web/nginx/htpasswd:/etc/nginx/htpasswd:ro
- /mnt/data/container_data/web/nginx/http.d:/etc/nginx/http.d:ro
- /mnt/data/container_data/web/nginx/nginx.conf:/etc/nginx/nginx.conf:ro
- /mnt/data/container_data/web/nginx/proxy-control.conf:/etc/nginx/proxy-control.conf:ro
- /mnt/data/container_data/web/nginx/ssl.conf:/etc/nginx/ssl.conf:ro
- /mnt/data/container_data/web/nginx/ssl:/etc/nginx/ssl:ro
- /mnt/data/container_data/web/nginx/html:/etc/nginx/html:ro
command: [nginx-debug, '-g', 'daemon off;']
ports:
- 8080:8080
- 9090:9090
- 8989:8989
- 7878:7878
restart: unless-stopped
每个服务都必须需要一个配置:
server {
listen 443;
listen [::]:443;
include /etc/nginx/ssl/qbittorrent.web.internal/qbittorrent.web.internal.conf;
server_name qbittorrent.web.internal;
location / {
proxy_pass http://192.168.7.128:8080/;
include /etc/nginx/proxy-control.conf;
include /etc/nginx/auth-basic.conf;
}
}
现在有几个问题:
如果由于某种原因 VPN 容器 vpn_bittorrent
重新启动 nginx 代理 web
将无法再看到 bittorrent
容器,直到它也重新启动,结果是“502 Bad Gateway”错误。我怀疑这与 qbittorrent
和 vpn_bittorrent
之间的联系有关,即 network_mode: service:vpn_bittorrent
.
我想用 https://traefik.io/ 等更灵活的东西替换我的反向代理,我不想手动配置 nginx 配置来匹配某个 IP 地址,例如 192.168 .7.128
我认为远离 macvlan 地址可能是一件好事,所以我在我的主机上创建了一个网桥
auto br7
iface br7 inet static
address 192.168.7.252
netmask 255.255.255.0
gateway 192.168.7.1
bridge_ports bond0.7
bridge_stp 0
我以某种方式希望使用用户定义的网桥将我的容器绑定到该接口,然后根本不必担心 docker 方面的 VLAN。
似乎使 docker 使用特定接口进行出口的唯一方法是主机上的 macvlan 或路由规则:
- https://medium.com/@havloujian.joachim/advanced-docker-networking-outgoing-ip-921fc3090b09
- https://stewartadam.io/blog/2019/04/04/routing-packets-specific-docker-container-through-specific-outgoing-interface
如果有更简单的方法我忽略了请告诉我。
sudo nsenter --net=/var/run/netns/hostname
我最终解决了这个问题,诀窍是指定范围:
# docker network create --subnet=172.18.0.0/16 -d bridge -o com.docker.network.bridge.name=MY_NET MY_NET
然后使用防火墙标记在这种情况下我选择7
:
# iptables -t mangle -A PREROUTING -s 172.18.0.0/16 -j MARK --set-xmark 0x7/0xffffffff
确保为路由启用此sysctl
# sysctl -w net.ipv4.conf.all.rp_filter=2
添加容器 table 到 /etc/rt_tables
7 CONTAINERS
添加一些ip规则:
# ip rule add fwmark 7 table CONTAINERS prio 700
# ip route add default via 192.168.7.1 table CONTAINERS
# ip route add 192.168.7.1 dev bond0.7 table CONTAINERS
您可以使用以下方法进行测试:
wget -q -O - ifconfig.me
我有一个连接到多个 VLAN 的主机,这些 VLAN 在我的路由器上具有特定的路由规则,它们具有不同的属性。
我在每个 VLAN 的 VM 中看到了关于 运行 docker 的其他建议,但这看起来也很丑陋和混乱。
例如
/etc/network/interfaces:
# Is routed out a VPN on my router
auto bond0.3
iface bond0.3 inet dhcp
iface bond0.3 inet6 auto
# Is null routed at my router (LAN only)
auto bond0.4
iface bond0.4 inet dhcp
dns-nameserver 192.168.3.1
iface bond0.4 inet6 auto
# Routed directly to my ISP for containers only
auto bond0.7
iface bond0.7 inet dhcp
iface bond0.7 inet6 auto
我在名为“external_7”的 docker 接口上使用了 macvlan 接口:
networks:
external_v7:
name: external_v7
driver: macvlan
driver_opts:
parent: bond0.7
enable_ipv6: false
ipam:
config:
- subnet: 192.168.7.0/24
gateway: 192.168.7.1
ip_range: 192.168.7.128/26
接下来我在 VPN 后面有一个 Bittorrent 客户端,我有单独的 VPN 隧道容器而不在我的路由器上使用它的主要原因是因为在下载某些东西时它阻塞了隧道,我无法使用它对于其他任何事情,所以我有一个用于 Bittorrent 的专用 VPN 隧道:
services:
vpn_bittorrent:
extends:
file: ../docker-vpn/docker-compose-vpn.yml
service: openvpn-client
container_name: vpn_bittorrent
networks:
external_v7:
ipv4_address: 192.168.7.128
volumes:
- /mnt/data/container_data/vpn:/data/vpn
ports:
- 192.168.7.128:26129:26129
- 192.168.7.128:26129:26129/udp
扩展自:
services:
openvpn-client:
image: ghcr.io/wfg/openvpn-client
cap_add:
- NET_ADMIN
devices:
- /dev/net/tun
restart: unless-stopped
我终于有了 qbittorrent 运行:
qbittorrent:
image: ghcr.io/linuxserver/qbittorrent
container_name: qbittorrent
network_mode: service:vpn_bittorrent
environment:
- PUID=1004
- PGID=1003
- WEBUI_PORT=8080
volumes:
- /mnt/data/container_data/qbittorrent:/config
- /mnt/data/shared/incoming:/mnt/shared/incoming
restart: unless-stopped
现在当然我喜欢在这前面有一个反向代理,因为我喜欢使用标准端口,如 :443 或其他。
web:
image: nginx:stable-alpine
container_name: web
hostname: web.internal
networks:
external_v4:
ipv4_address: 192.168.4.133
volumes:
- /mnt/data/container_data/web/nginx/auth-basic.conf:/etc/nginx/auth-basic.conf:ro
- /mnt/data/container_data/web/nginx/htpasswd:/etc/nginx/htpasswd:ro
- /mnt/data/container_data/web/nginx/http.d:/etc/nginx/http.d:ro
- /mnt/data/container_data/web/nginx/nginx.conf:/etc/nginx/nginx.conf:ro
- /mnt/data/container_data/web/nginx/proxy-control.conf:/etc/nginx/proxy-control.conf:ro
- /mnt/data/container_data/web/nginx/ssl.conf:/etc/nginx/ssl.conf:ro
- /mnt/data/container_data/web/nginx/ssl:/etc/nginx/ssl:ro
- /mnt/data/container_data/web/nginx/html:/etc/nginx/html:ro
command: [nginx-debug, '-g', 'daemon off;']
ports:
- 8080:8080
- 9090:9090
- 8989:8989
- 7878:7878
restart: unless-stopped
每个服务都必须需要一个配置:
server {
listen 443;
listen [::]:443;
include /etc/nginx/ssl/qbittorrent.web.internal/qbittorrent.web.internal.conf;
server_name qbittorrent.web.internal;
location / {
proxy_pass http://192.168.7.128:8080/;
include /etc/nginx/proxy-control.conf;
include /etc/nginx/auth-basic.conf;
}
}
现在有几个问题:
如果由于某种原因 VPN 容器
vpn_bittorrent
重新启动 nginx 代理web
将无法再看到bittorrent
容器,直到它也重新启动,结果是“502 Bad Gateway”错误。我怀疑这与qbittorrent
和vpn_bittorrent
之间的联系有关,即network_mode: service:vpn_bittorrent
.我想用 https://traefik.io/ 等更灵活的东西替换我的反向代理,我不想手动配置 nginx 配置来匹配某个 IP 地址,例如 192.168 .7.128
我认为远离 macvlan 地址可能是一件好事,所以我在我的主机上创建了一个网桥
auto br7
iface br7 inet static
address 192.168.7.252
netmask 255.255.255.0
gateway 192.168.7.1
bridge_ports bond0.7
bridge_stp 0
我以某种方式希望使用用户定义的网桥将我的容器绑定到该接口,然后根本不必担心 docker 方面的 VLAN。
似乎使 docker 使用特定接口进行出口的唯一方法是主机上的 macvlan 或路由规则:
- https://medium.com/@havloujian.joachim/advanced-docker-networking-outgoing-ip-921fc3090b09
- https://stewartadam.io/blog/2019/04/04/routing-packets-specific-docker-container-through-specific-outgoing-interface
如果有更简单的方法我忽略了请告诉我。
sudo nsenter --net=/var/run/netns/hostname
我最终解决了这个问题,诀窍是指定范围:
# docker network create --subnet=172.18.0.0/16 -d bridge -o com.docker.network.bridge.name=MY_NET MY_NET
然后使用防火墙标记在这种情况下我选择7
:
# iptables -t mangle -A PREROUTING -s 172.18.0.0/16 -j MARK --set-xmark 0x7/0xffffffff
确保为路由启用此sysctl
# sysctl -w net.ipv4.conf.all.rp_filter=2
添加容器 table 到 /etc/rt_tables
7 CONTAINERS
添加一些ip规则:
# ip rule add fwmark 7 table CONTAINERS prio 700
# ip route add default via 192.168.7.1 table CONTAINERS
# ip route add 192.168.7.1 dev bond0.7 table CONTAINERS
您可以使用以下方法进行测试:
wget -q -O - ifconfig.me