云计算百科
云计算领域专业知识百科平台

✨【运维实战】内网服务器无法联网?巧用 SSH 隧道实现反向代理访问公网资源 (Docker/PortForwarding)

【运维实战】内网服务器无法联网?巧用 SSH 隧道实现反向代理访问公网资源 (Docker/PortForwarding)

📚 前言

在企业运维和开发场景中,我们经常遇到这样的网络架构:

  • 服务器环境:出于安全考虑,服务器位于隔离内网,没有配置公网出口 IP,无法访问互联网。
  • 开发环境:运维人员的本地电脑(PC/Mac)可以通过 VPN 或堡垒机 SSH 连接到该服务器,且本地电脑拥有正常的互联网访问权限。
  • 痛点:服务器需要安装依赖(如 yum install, docker pull, pip install),但由于没网,只能离线拷贝安装包,效率极低。

本文将介绍一种利用 SSH 协议自带的 Remote Port Forwarding (远程端口转发) 功能,搭建一条临时隧道,让内网服务器通过本地开发机的网络访问公网资源(如阿里云镜像源、Maven 中央仓库等)。


💡 技术原理:SSH 反向隧道

SSH 不仅可以用于远程登录,还内置了强大的隧道功能。其中 -R 参数用于创建反向隧道。

原理流程:

  • 本地电脑开启一个流量转发服务(通常使用 HTTP 或 SOCKS 协议)。
  • 通过 SSH 建立连接,将服务器的某个端口(如 8888)映射到本地电脑的转发端口。
  • 服务器配置环境变量,将网络请求发送给自身的 8888 端口。
  • SSH 进程将请求加密,通过隧道传输到本地电脑,再由本地电脑代为请求公网资源。

  • 🛠️ 方案一:命令行快速通道 (SSH -R)

    适用于临时维护、拉取代码或安装少量软件。

    1. 前置准备

    确保你的本地电脑上已经开启了一个代理服务/转发服务。
    (注:如果本地没有现成的服务,可以使用 Python 或简单的 SOCKS 服务开启一个端口,例如监听在 1080 或 7890 端口)。

    2. 建立隧道

    在本地电脑的终端执行以下命令:

    # 语法:ssh -R <服务器端口>:localhost:<本地服务端口> <用户名>@<服务器IP>
    # 示例:将服务器的 8888 端口映射到本地的 7890 端口
    ssh -o ServerAliveInterval=60 -R 8888:localhost:7890 root@192.168.1.100

    • -R 8888:localhost:7890:核心参数,意为让远程服务器监听 8888,流量转发至本地 7890。
    • -o ServerAliveInterval=60:发送心跳包,防止连接因空闲断开。

    3. 服务器端验证

    登录到服务器,进行连通性测试:

    # 临时设置环境变量
    export http_proxy=http://127.0.0.1:8888
    export https_proxy=http://127.0.0.1:8888

    # 测试访问公网(以百度或阿里云镜像为例)
    curl -I https://www.baidu.com

    如果返回 HTTP/1.1 200 OK,说明隧道已打通。


    🐳 方案二:基于 Docker 的持久化方案 (推荐)

    如果需要长期保持通道稳定,使用基于 autossh 的 Docker 容器是最佳实践,它支持断线自动重连。

    1. 编写 docker-compose.yml

    在本地电脑上创建文件:

    version: '3'
    services:
    autossh-tunnel:
    image: jnovack/autossh
    container_name: sshreversetunnel
    environment:
    SSH_REMOTE_USER=root # 服务器用户名
    SSH_REMOTE_HOST=192.168.1.100 # 服务器内网IP
    SSH_REMOTE_PORT=22 # SSH端口
    # 🔥 核心配置:反向代理模式
    SSH_MODE=R
    SSH_TUNNEL_PORT=8888 # 服务器端监听的端口
    SSH_TARGET_HOST=host.docker.internal # 指向本地宿主机
    SSH_TARGET_PORT=7890 # 本地网络出口服务的端口
    volumes:
    ./id_rsa:/id_rsa:ro # 挂载私钥实现免密登录
    # 允许容器访问宿主机网络
    extra_hosts:
    "host.docker.internal:host-gateway"
    restart: always

    注意:请将私钥文件 id_rsa 放置在同级目录下。

    2. 启动服务

    docker-compose up -d

    容器启动后,会自动监控 SSH 连接状态,确保隧道全天候可用。


    ⚙️ 进阶:如何配置服务器软件走代理?

    打通隧道后,需要配置服务器上的软件使用该代理端口。

    1. 系统级配置 (APT/YUM/Curl)

    编辑 /etc/profile 或用户目录下的 .bashrc:

    export http_proxy=http://127.0.0.1:8888
    export https_proxy=http://127.0.0.1:8888
    # 如果本地服务支持 SOCKS5 协议
    export all_proxy=socks5://127.0.0.1:8888

    执行 source /etc/profile 生效。

    2. Docker Pull 加速

    Docker 守护进程需要单独配置代理。创建或修改 /etc/systemd/system/docker.service.d/http-proxy.conf:

    [Service]
    Environment="HTTP_PROXY=http://127.0.0.1:8888"
    Environment="HTTPS_PROXY=http://127.0.0.1:8888"
    # 配置不走代理的地址(如私有仓库、K8s内部地址)
    Environment="NO_PROXY=localhost,127.0.0.1,private-registry.internal"

    重启 Docker 服务:

    systemctl daemon-reload
    systemctl restart docker


    🚧 常见问题排查

  • 连接被拒绝 (Connection Refused):

    • 检查本地电脑的端口(如 7890)是否开启。
    • 检查本地电脑的防火墙设置,确保允许 Docker 容器或 SSH 进程访问该端口。
    • 部分本地网络服务默认只监听 127.0.0.1,需开启“允许局域网连接”或监听 0.0.0.0。
  • 速度慢:

    • 受限于 SSH 协议的加密解密开销以及本地电脑的上行带宽,该方案适合传输代码、配置文件或普通软件包,不建议传输超大文件。

  • 🎉 总结

    通过 SSH 反向隧道,我们无需在内网防火墙上开洞,利用现有的 SSH 通道即可巧妙解决内网服务器的公网资源访问问题。这对于隔离环境下的 DevOps 运维非常实用。

    希望这篇文章能帮到你!如果有疑问,欢迎在评论区留言交流。


    (本文归档于:服务器运维 / Linux技巧 / 网络配置)

    赞(0)
    未经允许不得转载:网硕互联帮助中心 » ✨【运维实战】内网服务器无法联网?巧用 SSH 隧道实现反向代理访问公网资源 (Docker/PortForwarding)
    分享到: 更多 (0)

    评论 抢沙发

    评论前必须登录!