Scu_laji

mac ssh 通过代理链接服务器

mac ssh 通过代理链接服务器

最近升级了 mac 系统,记不清从什么时候开始,mac 走 ss 链接内网的服务器总是异常的慢,几乎每次都需要一分钟来建立连接。

以前的做法

我是从 2015 年开始使用 Mac 的,刚开始可以使用 proxychains-ng 来使得 ssh 走代理,那时的 ssh 还不带自动检测代理设置。(macos 10.10 and 10.11),也许应该叫 OSx 更合适一点。

10.12 中的做法

当你设置 ss 为系统代理时,ssh 会自动走代理。这时,ssh 貌似让 Apple 改成单纯的静态 c 程序了,proxychains 已失效。proxychains 的做法是劫持连接的动态链接库,使得程序支持 socks 代理

10.13 中的做法

我曾在知乎中回答过这个问题,当时的做法是使用一个代理软件。叫 proxifier + ssh 可以做到穿透内网(当时用的是 shadowsocks).

回答在这里 zhihu

现在的状况

做外包赚了点 💰,加上我自己对科学上网的需要,我买了号称最好用的代理软件的 surge。刚开始时用着没什么问题, 不得不说 surge 的规则是真的方便和强大,少许的几行配置就能使得我的上网环境得到极大的改善。我可以不需要记住我的 server 在哪里,就直接连接(无论内网还是公网)。

但是,我遇到了上面那个状况。每次链接内网的 ssh, 总要花费 1 分钟多的时间,这令我感觉到十分的难受(即使这段时间可以摸 🐟,哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈)

经过我的检测,发现,其实是现在的 ssh client 先会尝试直连,直连连不上的话,才会走代理去进行连接。

尝试连接的话,先会经过一个很长时间的 tcp 连接失败,这时,就造成了每次连接都需要一分多钟的情况。

此时,我们需要让 ssh 直接走代理,不经过第一次的尝试过程。经过 Google 一下,果然 ok。

这样做的前提是你本地有一个 socks 代理,(socks4 socks5)均可。下面以 socks5 举例

当你连接服务器的时候,可以使用 (surge 的 socks5 端口是 6153)

1
ssh myserver -o "ProxyCommand=nc -X 5 -x 127.0.0.1:6153 %h %p"

当然,不想每次都使用这么繁琐的命令是可以的。

在你的.ssh/config 文件里加上

1
2
Host *
ProxyCommand=nc -X 5 -x 127.0.0.1:6153 %h %p

就可以让你的所有服务器连接先经过一遍代理,再由 surge 来控制服务器是走直连, 还是走内网跳板机,还是走国外跳板机。

参考资料

Stack Overflow connect-with-ssh-through-a-proxy