Python P2P 网络(NAT 穿透)

3 投票
3 回答
4333 浏览
提问于 2025-04-17 22:15

为了便于理解,我们假设这两台机器都在使用ipv4,并且都在NAT网络后面。我想在这两台机器上打开一个套接字,让它们通过这些套接字连接起来(或者用类似的方式)。我知道这需要用到NAT穿透,但我不太明白NAT穿透是怎么回事(一个曾经连接的套接字现在可以变成接受连接的吗?)如果有谁在Python中使用过NAT穿透,我会非常感激你们的帮助。

3 个回答

0

听起来你需要设置端口转发,也就是告诉你的路由器,把它收到的特定端口的请求转发给后面的某个服务。

这个通常是在你路由器的管理界面里进行设置的。

2

打洞技术在维基百科上有很好的介绍。

打洞是一种计算机网络技术,用于在两个不同组织之间建立通信,这两个组织都在限制性防火墙后面。这个技术常用于在线游戏、点对点(P2P)和网络电话(VoIP)等应用。两个客户端会先与一个没有限制的第三方服务器建立连接,这样服务器就能获取它们的外部和内部地址信息。因为每个客户端都是主动向服务器发起请求的,所以服务器知道它们的IP地址和为这个会话分配的端口号,并把这些信息互相分享。拥有有效的端口号后,防火墙就会接受来自双方的进来的数据包。ICMP打洞、UDP打洞和TCP打洞分别使用互联网控制消息、用户数据报和传输控制协议。通过TCP的恶意打洞,可以将压缩的SYN数据包发送到一个共同的ACK路径中。

在这里有关于TCP、UDP和ICMP打洞的各种技术链接。

一般来说,要从A打洞到B(两者都在NAT后面),需要一个第三方服务器C,A和B都可以先连接到这个服务器。服务器会把A的连接信息发送给B,反之亦然。然后A和B使用这些信息尝试直接连接,但这个过程并不是100%可靠的。

如果没有第三方服务器,我觉得这个方法是行不通的。

编辑

你可能还想了解一下UPnP,具体可以查看这个链接。我不太确定路由器对它的支持程度,但听起来很适合你的应用。

4

这被称为“NAT 穿越问题”
有三种解决方案

  1. 静态配置 NAT,将进入的连接请求转发到你的服务器的指定端口。这也叫端口转发
    enter image description here

  2. 互联网网关设备(IGD)协议。这个协议允许 NAT 后的主机:
    - 学习 NAT 路由器的公共 IP 地址
    - 添加/删除端口映射(带有租约时间)
    也就是说,可以自动配置静态 NAT 端口映射。
    enter image description here

  3. 中继(在 Skype 中使用)
    - NAT 客户端与中继/服务器建立连接
    - 外部客户端连接到中继
    - 中继在两个连接之间转发数据包
    enter image description here

更多信息请参考书籍《计算机网络:自顶向下方法》第六版 - James F. Kurose, Keith W. Ross 第四章>>网络地址转换(NAT)

撰写回答