本质是内网主机通过ssh -r主动将自身服务端口(如ssh、健康接口)安全暴露至堡垒机,实现“可被拉起”的单向通信通道;堡垒机需配置gatewayports clientspecified、放行映射端口,并用autossh保活隧道,配合健康端点实现状态汇报。

在受限内网环境中,用 ssh -R 向外部应急堡垒机“主动汇报受控状态”,本质是让内网主机把自己某个服务端口(比如 SSH、健康检查接口或自定义心跳端口)安全地暴露到堡垒机上,供运维人员随时连接验证。这不是常规远程控制,而是单向“可被拉起”的通信通道——只要隧道建好,堡垒机就能立刻 ssh 进来查状态,无需内网开放任何入向端口。
堡垒机端必须开启 GatewayPorts 并放行端口
这是最常卡住的一步:默认情况下,堡垒机收到反向隧道请求后,只允许 127.0.0.1 访问该端口,外部 IP 无法连入。
- 编辑
/etc/ssh/sshd_config,确保包含:GatewayPorts clientspecified(推荐)或GatewayPorts yes - 重启服务:
sudo systemctl restart sshd - 开放对应端口(如映射到 60022):
Ubuntu/Debian:sudo ufw allow 60022
CentOS/RHEL:sudo firewall-cmd --permanent --add-port=60022/tcp && sudo firewall-cmd --reload - 云服务器还需检查安全组规则,放行该端口(不是 22 端口)
内网主机执行带保活的反向隧道命令
不能只跑一次 ssh -R,断连即失联。需后台运行 + 心跳 + 自动重试:
- 基础命令(以暴露本机 SSH 为例):
ssh -fNTR *:60022:localhost:22 user@bastion-ip -o ServerAliveInterval=25 -o ExitOnForwardFailure=yes -o ConnectTimeout=10 -
*:60022表示绑定到所有网卡(含公网 IP),否则默认只绑127.0.0.1:60022,堡垒机自己都连不上 -
localhost:22指的是内网主机自己的 22 端口,不是堡垒机的;写127.0.0.1:22会出错 - 务必提前配置密钥登录,避免 autossh 或重连时卡密码提示
用 autossh 替代原生 ssh 实现可靠保活
原生命令无自动恢复能力。autossh 能检测隧道断裂并重建,更适合作为应急通道:
- 安装:
sudo apt install autossh(Debian/Ubuntu)或sudo yum install autossh(RHEL/CentOS) - 启动命令:
autossh -M 0 -f -N -R *:60022:localhost:22 -o ServerAliveInterval=30 -o ServerAliveCountMax=3 user@bastion-ip -
-M 0关闭 autossh 自带监控端口,减少冲突风险 - 验证是否运行:
ps aux | grep autossh;再登录堡垒机执行ss -tlnp | grep :60022,确认监听在*:60022
验证与应急响应联动设计
隧道建好只是起点,要让它真正支撑“状态汇报”,建议配合轻量机制:
- 在内网主机部署一个简易 HTTP 健康端点(如 Python 一行命令:
python3 -m http.server 8000 --bind 127.0.0.1:8000),然后用-R *:60080:localhost:8000暴露出去,堡垒机 curl 即可获取时间戳、进程数等信息 - 把关键状态写入
/tmp/last-report,并通过inotifywait监听变化,触发隧道重连或日志上报 - 禁止使用
StrictHostKeyChecking=no,首次连接应手动确认指纹,防止中间人劫持导致误报“已受控”











