Cloudflared SSH 快速公网访问
本 Skill 把"用 Cloudflare quick tunnel 把本地 SSH 暴露到公网"封装成一条命令,让任何云 Linux 机器都能被外网 SSH 进来——不需要公网 IP、不需要自有域名、不需要 Cloudflare 账号。
适用场景
- 云机器没有固定公网 IP / 被 NAT 隔离,想从外地 SSH 进来
- 临时演示、远程协助、临时开发机
- 任何"我需要从别处 SSH 进这台机器"的时刻
目录结构
cloudflared-ssh/
├── SKILL.md
└── scripts/
├── setup.sh # 安装 + 配置 + 启动 tunnel + 输出连接信息
├── stop.sh # 关闭 tunnel(--full 同时停 sshd),撤销公网暴露
└── status.sh # 查看当前 tunnel 状态与域名
前置条件
- 有
root或sudo权限(非 root 会自动 sudo 重跑) - 机器能出网(至少能访问
github.com或pkg.cloudflare.com之一) - 本机(用来连接的那台)需安装
cloudflared(作为 SSH 的 ProxyCommand 代理) - 支持架构:
x86_64(amd64)、aarch64(arm64)、armv7、i386;arm 架构仅 github 路径可用
用法
# 1) 随机密码(自动生成 16 位强密码,仅 root 登录)
bash <skill-directory>/scripts/setup.sh
# 2) 自定义 root 密码
bash <skill-directory>/scripts/setup.sh myStrongPass123
# 3) 更安全的模式:新建 cfuser 专用账号 + 强制密钥登录,禁用 root 密码
bash <skill-directory>/scripts/setup.sh --no-root
# 然后把自己的公钥写入 /home/cfuser/.ssh/authorized_keys
# 查看当前域名 / tunnel 状态(不重跑、不换域名)
bash <skill-directory>/scripts/status.sh
# 用完关闭公网暴露
bash <skill-directory>/scripts/stop.sh # 仅关 tunnel
bash <skill-directory>/scripts/stop.sh --full # 连 sshd 一起停
<skill-directory>指本 Skill 所在目录,即cloudflared-ssh/。
脚本做了什么(幂等、自包含、多架构)
- 安装 cloudflared:优先从 github release 下载对应架构;若 github 被墙且为 amd64,自动改用
pkg.cloudflare.com官方 apt 仓库(已实测可用)。 - 安装并启动 sshd:
openssh-server+ 生成缺失的 host key(ssh-keygen -A,修复容器/新镜像启动即退出的问题)+ 监听0.0.0.0:22。 - 设置密码 / 账号:root 自定义或随机 16 位(
openssl rand);--no-root时新建cfuser并强制密钥登录。 - 启动 quick tunnel:
cloudflared tunnel --url ssh://localhost:22,自动循环抓取分配的*.trycloudflare.com域名。 - 输出访问信息:域名、用户、密码、连接命令,并保存到
/root/.cf-ssh-info(权限 600)。
从本机连接
本机先装 cloudflared(mac/Win: brew install cloudflared / winget install Cloudflare.cloudflared),然后:
ssh -o ProxyCommand="cloudflared access ssh --hostname %h" root@<域名>
或写入 ~/.ssh/config:
Host sandbox
HostName <域名>
User root
ProxyCommand cloudflared access ssh --hostname %h
之后 ssh sandbox 输密码即可。
关键:不能裸连 22 端口。Cloudflare 边缘只收 443,SSH 流量必须经本机
cloudflared客户端做隧道封装。
底层原理
- SSH 服务跑在本地
:22,本身不出网。 cloudflared在本地起一个到 Cloudflare 边缘(quic/http2)的反向隧道,把ssh://localhost:22暴露为https://xxx.trycloudflare.com。- 连接时,本机
cloudflared access ssh把 SSH 流量封装进隧道,回源到这台机器的:22。
安全建议(重要)
| 风险 | 建议 |
|---|---|
| root + 密码直曝公网 | trycloudflare.com 域名公开可扫。优先用 setup.sh --no-root(新建专用账号 + 密钥);若必须 root,连上立即 passwd 改密码 |
| 长期暴露 | 用完即 stop.sh 关 tunnel;不要用它做长期入口 |
| 机器重启 | 脚本不注册 systemd 服务,重启后需重新 setup.sh(且域名会变) |
| 固定域名替代 | 有 Cloudflare 账号 + 自有域名时,用持久隧道:cloudflared tunnel --hostname 子域.域名 --url ssh://localhost:22 |
| 连接侧 | 客户端也应装 cloudflared,且建议本地 ~/.ssh/config 固定 Host 别名 |
注意事项
| 项 | 说明 |
|---|---|
| 域名是临时的 | quick tunnel 域名随机,进程退出 / 机器重启即失效,需重跑脚本拿新域名(status.sh 可在不重跑时查当前域名) |
| 会休眠的机器 | 若机器休眠/回收,tunnel 随之失效 |
| arm 架构 | 仅 github 下载路径可用;pkg.cloudflare.com 只提供 amd64 deb |
| 信息落盘 | 连接信息(含密码)写入 /root/.cf-ssh-info,权限 600;请妥善保管或及时删除 |
排错
- 连不上 22:先看
setup.sh输出里22 端口未监听警告;多因缺 host key,脚本已自动ssh-keygen -A。本机需装cloudflared才能用 ProxyCommand。 - 域名一直抓不到:看
/tmp/cf-ssh-tunnel.log,通常是机器出网被限制;确保能访问region1.argotunnel.com。 - github 下载失败:amd64 会自动走
pkg.cloudflare.com兜底;arm 架构无兜底,需手动上传对应二进制到/usr/local/bin/cloudflared。 - 架构不匹配:脚本按
uname -m自动选 amd64/arm64;若手动放置二进制请确认架构一致,否则运行即崩溃。