Sit*_*_NO 7 ipv6 docker docker-swarm
我有一台运行 IPv4 和 IPv6(双栈)的 Ubuntu 服务器 16.04 LTS。该服务器也在运行 Docker。但是,每当我尝试访问群中的容器时都会遇到问题,但只能通过 IPv6。这是我的步骤:
我创建了一个运行 gnuicron 网络服务器的简单应用程序:
def app(environ, start_response):
"""Simplest possible application object"""
data = b'Hello, World!\n'
status = '200 OK'
response_headers = [
('Content-type', 'text/plain'),
('Content-Length', str(len(data)))
]
start_response(status, response_headers)
return iter([data])
Run Code Online (Sandbox Code Playgroud)
我gunicorn -w 4 -b [::]:5678 myapp:app在我的服务器上运行它,并通过在我的网络中的双栈客户端上运行它来验证它是否有效:
$ curl --connect-timeout 15 http://[2001:db8:db0::5]:5678
Hello, World!
$ curl --connect-timeout 15 http://192.168.10.5:5678
Hello, World!
Run Code Online (Sandbox Code Playgroud)
我写了一个Dockerfile并运行它:
docker build -t docker_ipv6_test .
docker run --rm --init -p 5678:5678 docker_ipv6_test
Run Code Online (Sandbox Code Playgroud)
我运行与 about 相同的验证,它按预期工作。然后我写了一个docker-compose.yml:
version: '3'
services:
ipv6_test:
image: docker_ipv6_test:latest
deploy:
replicas: 1
restart_policy:
condition: on-failure
ports:
- '5678:5678/tcp'
Run Code Online (Sandbox Code Playgroud)
并运行它:
docker stack deploy -c docker-compose.yml ipv6_test
Run Code Online (Sandbox Code Playgroud)
然后发生这种情况:
$ curl --connect-timeout 15 http://[2001:db8:db0::5]:5678
curl: (28) Operation timed out after 0 milliseconds with 0 out of 0 bytes received
$ curl --connect-timeout 15 http://192.168.10.5:5678
Hello, World!
Run Code Online (Sandbox Code Playgroud)
但我想知道是我做错了什么,还是我遇到了错误?
我所有的代码和文件都可以在这里找到:https : //github.com/SitronNO/docker_ipv6_test
您遇到了错误并做了错误的事情。从许多 github 问题和https://docs.docker.com/compose/compose-file/#ipv4_address-ipv6_address上的评论来看,ipv6 目前无法在 swarms 中工作:
如果需要 IPv6 寻址,则必须设置 enable_ipv6 选项,并且必须使用版本 2.x Compose 文件。IPv6 选项当前不适用于集群模式。
你可能想尝试 IPv6 NAT https://github.com/robbertkl/docker-ipv6nat但这似乎也很难设置,特别是如果你没有 ipv6tables 等。
你做错的不是设置一个启用了 ipv6 的 docker swarm 范围桥接网络,或者启动启用了 ipv6 的 docker - 但考虑到当前的文档,这并不奇怪。
-我建议没有人回答这个问题,因为还没有一个好的答案。-
但一个答案是让 docker 做它最擅长的事情,让 linux 的其余部分做剩下的事情。将 docker swarm 保留为纯 ipv4 网络,并将 ipv6 流量转发到该网络。ip 表从 ipv4 转发到 ipv6 是不可能的,但可以使用socat例如:
sudo socat TCP6-LISTEN:80,,su=nobody,fork,reuseaddr TCP4:127.0.0.1:81
注意,我将 docker 端口移至侦听端口 81,因为虽然 swarm 的 docker_gwbridge 可能没有“启用”ipv6,但它仍会绑定到 ipv6:80 端口(叹气)。注意 socat 现在会将 ipv4 和 ipv6 流量转发到 ipv4 端口 80。
您可以使用sudo nohup socat ... &该命令将其置于后台。
请参阅如何以透明方式将端口从 IPv4 隧道传输到远程 IPv6 设备?等人。
| 归档时间: |
|
| 查看次数: |
1418 次 |
| 最近记录: |