如何从 WSL2 访问主机上运行的服务(连接被拒绝)

如何从 WSL2 访问主机上运行的服务(连接被拒绝)

我的主机上运行着 selenium,我的应用程序位于 docker 容器内(在 WSL2 内)。

我正在尝试让应用程序连接到正在监听端口 4445 的 selenium。它几个月前还可以用,我认为 WSL 中发生了一些变化。

主机正在监听 4445:

PS> netstat -ano | findstr :4445
  TCP    0.0.0.0:4445           0.0.0.0:0              LISTENING       11604
  TCP    [::]:4445              [::]:0                 LISTENING       11604

我可以从 Windows 主机访问 Selenium:

>curl -X POST http://DESKTOP-HED9HVG:4445/wd/hub
{"state":".....}

但不是来自 WSL2:

$ curl -X POST http://172.22.241.214:4445/wd/hub
curl: (7) Failed to connect to 172.22.241.214 port 4445: Connection refused

我尝试了在 curl 中使用的 ip 的几个选项:

  • ip addreth0 网络接口
  • $(hostname)
  • 从结果中获取 IP 地址ipconfig /all | findstr IPv4
  • ip 地址结果route -n | grep UG | head -n1 | awk '{print $2}'

我在 WSL 上安装了 tcptraceroute 并运行它。这是输出:

$ tcptraceroute $(hostname) 4445
Selected device lo, address 127.0.0.1, port 53915 for outgoing packets
Tracing the path to DESKTOP-WXYZ1 (127.0.1.1) on TCP port 4445, 30 hops max
 1  DESKTOP-WXYZ1.localdomain (127.0.1.1) [closed]  0.075 ms  0.082 ms  0.074 ms

顺便说一下,从 WSL ping 到主机确实有效:

$ ping $(hostname)
PING DESKTOP-WXYZ1.localdomain (127.0.1.1) 56(84) bytes of data.
64 bytes from DESKTOP-WXYZ1.localdomain (127.0.1.1): icmp_seq=1 ttl=64 time=0.053 ms

我尝试完全禁用 Windows 防火墙,但没有用。我还在“Windows Defender 防火墙”中添加了一条规则,专门启用端口 4445。但仍然没有用

有关 WSL 的信息:

>wsl -l -v
  NAME                   STATE           VERSION
* Ubuntu-20.04           Running         2
  docker-desktop         Running         2
  docker-desktop-data    Running         2

知道如何解决这个问题吗?

答案1

尝试了很多次之后,我们终于从 github issues 中的一个模糊评论中找到了解决方案: https://github.com/Microsoft/WSL/issues/1032#issuecomment-891618766

基本上:

if you also use Docker Desktop, you can access your Windows host with host.docker.internal

答案2

我实际上自己在工作中做的一个项目中也遇到了这个问题,无法使用docker桌面。

我要做的是建立防火墙和端口代理规则以绕过 wsl 和 windows 防火墙。您需要主机以太网适配器的 ip,因此请在 windows 中运行 ipconfig 来获取它。您还需要 windows 上服务的侦听端口和 WSL ip(wsl 中的 ifconfig,查找 eth0 的 ivp4 inet 值)。

主机上 powershell 的防火墙规则命令:

New-NetFireWallRule -DisplayName 'WSL firewall unlock' -Direction Outbound -LocalPort your_port_here -Action Allow -Protocol TCP

New-NetFireWallRule -DisplayName 'WSL firewall unlock' -Direction Inbound -LocalPort your_port_here -Action Allow -Protocol TCP

绕过 Windows 防火墙后,您还可以从 Windows 提示符将端口“转发”到 WSL:

netsh interface portproxy add v4tov4 listenport=your_port_here listenaddress=host_ip_here connectport=your_port_here connectaddress=wsl_ip_here

运行所有命令后,您应该能够从容器通过 <host_ip>:<host_port> 访问主机服务。

答案3

请参阅此处的指南

https://docs.microsoft.com/en-us/windows/wsl/networking#accessing-windows-networking-apps-from-linux-host-ip

如果您想从 Linux 发行版(即 Ubuntu)访问在 Windows 上运行的网络应用程序(例如在 NodeJS 或 SQL 服务器上运行的应用程序),则需要使用主机的 IP 地址。虽然这不是常见的情况,但您可以按照以下步骤使其工作。

通过从 Linux 发行版运行以下命令来获取主机的 IP 地址:cat /etc/resolv.conf 复制术语“nameserver”后面的 IP 地址。使用复制的 IP 地址连接到任何 Windows 服务器。下图显示了通过 curl 连接到在 Windows 中运行的 Node.js 服务器的示例。

您还需要允许主机中该端口的入站连接。(通过防火墙规则)。

答案4

只需使用127.0.0.1:<端口>在 WSL 中而不是 Windows 主机的主机名 - 对我来说不需要添加防火墙规则就可以工作。

https://github.com/Microsoft/WSL/issues/1032#issuecomment-244160207

你好@netroby——在 WSL 中,实际上没有你所指的“主机”这样的东西;它只是 Windows。甚至你的 Linux 环境实际上都是直接在 Windows 中运行的;它只是使用使其工作的包装器库运行。因此,例如,如果你在 Windows 上的 127.0.0.1 上运行服务,Linux 程序也应该在 127.0.0.1 上的同一端口上连接到它。0.0.0.0 是一个特殊的 IP;它表示“任何 IP 地址”。因此 Linux 进程可以选择 Windows 主机上有效的任何 IP 地址。~aseering

相关内容