SSH 能连上,但用一会儿就断,比完全连不上更烦。
常见报错大概是这几种:
client_loop: send disconnect: Broken pipe
packet_write_wait: Connection to x.x.x.x port 22: Broken pipe
Connection reset by peer
Connection closed by remote host
Operation timed out
这类问题和 Permission denied 不是一回事。Permission denied 是认证没过;Broken pipe 和 Connection reset 通常表示连接已经建立过,但中途被某一层断掉了。
可能断你连接的地方很多:你的本地网络、公司/校园网 NAT、路由器、省际线路、云厂商安全策略、VPS 的 sshd 配置、系统资源压力,甚至是你终端长时间空闲。
这篇按最实用的顺序排:先让 SSH 不再空闲断开,再判断是 VPS 问题还是线路问题。
先看你属于哪种:
| 现象 | 更可能的方向 |
|---|---|
一连接就 Permission denied | 用户、密钥、权限、sshd 配置 |
一连接就 Connection timed out | 防火墙、安全组、端口、线路 |
| 能连上,几分钟不操作就断 | 空闲超时、NAT 回收、keepalive |
| 正在执行命令时也断 | 网络抖动、VPS 负载、sshd 被重启 |
| 晚上高峰更容易断 | 线路拥堵、丢包、回程质量差 |
如果你是一连接就认证失败,先看:VPS SSH Permission denied 怎么办。
如果你是开启防火墙后完全连不上,先看:VPS 开启 UFW 后 SSH 进不去怎么办。
下面主要处理“能连上,但中途断”的情况。
最常见的情况是:SSH 窗口放着不动几分钟,回来一敲键盘就断。
这通常是中间网络设备认为连接空闲,把 TCP 会话回收了。家庭路由器、公司网关、运营商 NAT、移动热点都可能这么干。
先在你本地电脑的 SSH 配置里加:
mkdir -p ~/.ssh
nano ~/.ssh/config
写入:
Host *
ServerAliveInterval 30
ServerAliveCountMax 3
含义很简单:客户端每 30 秒给服务器发一次保活包;连续 3 次没有回应才认为连接死了。
保存后重新连接:
ssh root@your_server_ip
如果你用自定义端口:
ssh -p 2222 root@your_server_ip
只要你之前是“空闲一会儿就断”,这一步通常就能明显改善。
如果你不想先改配置,也可以临时加参数测试:
ssh -o ServerAliveInterval=30 -o ServerAliveCountMax=3 root@your_server_ip
如果这样连接稳定了,再写入 ~/.ssh/config。
你也可以只对某台 VPS 生效:
Host my-vps
HostName your_server_ip
User root
Port 22
ServerAliveInterval 30
ServerAliveCountMax 3
以后连接:
ssh my-vps
这比每次手打参数省事,也不容易漏。
客户端保活不够时,再看 VPS 服务端配置。
打开 sshd 配置:
sudo nano /etc/ssh/sshd_config
确认或添加:
ClientAliveInterval 60
ClientAliveCountMax 3
TCPKeepAlive yes
然后先测试配置有没有语法错误:
sudo sshd -t
没有输出通常表示没问题。再重载 SSH:
sudo systemctl reload ssh
有些系统服务名叫 sshd:
sudo systemctl reload sshd
别一上来就重启机器。先 sshd -t,再 reload。改错 sshd 配置会把自己锁外面,尤其是你没有控制台的时候。
如果连接断开不是因为空闲,服务端日志会给线索。
Ubuntu / Debian:
sudo journalctl -u ssh --since "1 hour ago"
sudo tail -n 100 /var/log/auth.log
CentOS / Rocky / AlmaLinux:
sudo journalctl -u sshd --since "1 hour ago"
sudo tail -n 100 /var/log/secure
重点看这些关键词:
sudo journalctl -u ssh --since "1 hour ago" | grep -Ei "disconnect|reset|timeout|error|kex|fatal|oom"
如果日志里能看到 Received disconnect,说明服务端知道连接被断开了。
如果日志里完全没有对应记录,但客户端直接 Broken pipe,更像中间网络断了,或者本地链路不稳定。
客户端调试信息很有用:
ssh -vvv root@your_server_ip
断开前后重点看:
debug1: client_input_channel_req: channel 0 rtype [email protected]
packet_write_wait: Connection to x.x.x.x port 22: Broken pipe
Connection reset by peer
如果断开前反复 keepalive 没回应,说明客户端发包后等不到服务器回复。这个时候不要急着改 sshd,先测网络丢包。
在本地电脑测:
ping your_server_ip
观察 1-2 分钟,看是否有丢包、延迟突然飙升。
更建议用 mtr:
mtr -rw your_server_ip
如果本地没有 mtr,macOS 可以用 Homebrew 装,Linux 可以用包管理器装:
sudo apt install mtr-tiny
看结果时别只盯最后一跳。中间某一跳丢包不一定代表问题,关键看最后几跳是否持续丢包、延迟是否规律性抬高。
如果只在晚上断,白天不怎么断,可以顺手看这篇:VPS 晚高峰为什么会卡。SSH 断开有时不是配置问题,而是线路晚高峰抖动。
如果 VPS CPU、内存、磁盘 I/O 压力很大,SSH 会话也会卡住甚至断开。尤其是低配机跑 Docker、数据库、备份压缩、日志写入时。
登录后执行:
uptime
free -h
df -h
看实时进程:
top
如果有 htop 更直观:
sudo apt install htop
htop
看系统是否有 OOM 或磁盘错误:
dmesg -T | grep -Ei "oom|killed process|i/o error|reset|ext4|nvme"
如果 SSH 断开前机器已经明显卡顿,命令输入也延迟,问题可能不是 SSH,而是 VPS 本身压力过高。
如果每次断开都发生在某个固定时间,比如每天凌晨,可能是服务 reload、自动更新、面板任务或日志轮转影响。
看 ssh 服务最近状态:
sudo systemctl status ssh
sudo journalctl -u ssh --since "24 hours ago"
CentOS 系:
sudo systemctl status sshd
sudo journalctl -u sshd --since "24 hours ago"
如果看到 sshd 频繁重启,要继续查是谁触发的:
sudo journalctl --since "24 hours ago" | grep -Ei "ssh|sshd|restart|reload|apt|dnf|yum|unattended"
自动更新一般不该频繁断 SSH,但如果系统包升级、配置管理工具或面板在改 sshd,就要小心。
即使你修好了 keepalive,也不建议把长任务直接跑在裸 SSH 会话里。网络总会有波动。
安装 tmux:
sudo apt update
sudo apt install tmux
新建会话:
tmux new -s work
在里面跑任务。临时退出但不结束任务:
Ctrl+b 然后按 d
下次回来:
tmux attach -t work
如果你要跑编译、备份、迁移、数据库导入,tmux 比祈祷 SSH 不断靠谱得多。
如果你经常用移动热点、机场网络、跨境线路,SSH 对 IP 切换和弱网并不友好。mosh 会更抗抖动。
服务器安装:
sudo apt install mosh
本地也安装 mosh,然后连接:
mosh root@your_server_ip
注意:mosh 需要 UDP 端口,默认范围通常是 60000-61000/udp。如果你开了 UFW 或云防火墙,需要放行:
sudo ufw allow 60000:61000/udp
如果你只是普通管理 VPS,先把 SSH keepalive 和 tmux 配好就够了;mosh 更适合弱网和移动场景。
本地 ~/.ssh/config:
Host *
ServerAliveInterval 30
ServerAliveCountMax 3
TCPKeepAlive yes
服务端 /etc/ssh/sshd_config:
ClientAliveInterval 60
ClientAliveCountMax 3
TCPKeepAlive yes
改服务端后记得:
sudo sshd -t
sudo systemctl reload ssh
如果服务名不对,再用:
sudo systemctl reload sshd
一个判断方法很简单:
- 只有 SSH 断,网站、ping、mtr 都正常:优先看 keepalive 和 sshd
- SSH、网站、数据库连接一起抖:优先看 VPS 负载或线路
- 只在某个网络环境断:优先看本地网络、公司网关、移动热点
- 只在晚高峰断:优先看线路拥堵和丢包
- 一直连不上:优先看防火墙、安全组、端口和认证
SSH 只是最先暴露问题的地方,不一定是真正的根因。
- VPS 连接不上怎么办? SSH 无法登录解决方案:如果现在已经完全连不上,从端口和防火墙开始排。
- VPS SSH Permission denied 怎么办:如果是认证失败,重点看密钥、用户和权限。
- VPS 开启 UFW 后 SSH 进不去怎么办:如果刚开防火墙后 SSH 断了,先处理 UFW。
- VPS 晚高峰为什么会卡:如果 SSH 断开有明显时间段,排查线路和宿主资源。
最后给一个实际建议:只要你经常登录 VPS,就把 ServerAliveInterval 和 tmux 配上。前者减少空闲断开,后者保证断开后任务还在。SSH 连接可以断,任务不要跟着断。
