背景
最近想在加登录下公司的电脑,奈何没有公网地址,无法实现远程登录。为了解决这个问题,开始寻求内网穿透的方案。根据目前了解,frp方案是目前用得相对比较多的方案。不过这个方案有个特点,需要搭建自己的服务器,而且需要开启某些端口到公网上,虽然用下来感觉还可,不过还是希望有其他方案可以尝试一下。
Cloudflare tunnel介绍
cloudflare tunnel是一个cloudflare提供的隧道服务,其最大的用处就是可以实现内网穿透。其原理如下图: 本质就是在本地运行了一个cloudflared的服务,其实现本地与cloudflare服务器通信,并通过dns绑定对应域名到具体的隧道连接中实现内网穿透。 对比frp,个人认为优点如下:
- 无需搭建自己的服务器;
- 安全,无需将自己服务器的多个端口暴露到公网,提升安全性;
- 可以实现多路复用,同一个隧道实现多种流量转发;
但是,也有缺点:
- 需要拥有一个自己的域名并托管到cloudflare。不过域名帮助记忆,整体还是可以接受;域名申请可以参考:[[使用Cloudflare的DNS服务#申请域名|Cloudflare DNS服务使用]]
- 速度慢;(这个不太忍受比较合适是搭建自己的frp服务)
教程
基于Web Dashboard
docker方式一
添加站点
参考[[使用Cloudflare的DNS服务#如何使用Cloudflare的DNS服务]]
创建Tunnel
- 进入站点,点击Access,同意Zero Trust;
可能会需要一些付款信息,如实填就好,然后选择Free的套餐;
-
创建隧道;
-
输入隧道名称,继续;
-
选择Docker方式(具体的方式按自己觉得合适的方式就可以) 由于比较习惯使用docker-compose来管理docker,因此这里给出docker-compse.yml的内容
version: "3.9"
services:
tunnel:
image: cloudflare/cloudflared:2023.3.1
container_name: cloudflared
command: tunnel --no-autoupdate --protocol http2 run --token $TOKEN
user: root
restart: unless-stopped
network_mode: host
然后再创建一个.env文件,输入以下内容
TOKEN=<YOUR TOKEN FROM WEB>
- 继续配置隧道 配置域名和支持的服务,例如这里增加ssh的支持,然后点击保存。
[!note]
- 如果配置的域名不在DNS服务中,会自动添加到域名的DNS记录中;
- DNS是一条CNAME,即某个链接的别名,这个链接为
TUNNEL-ID.cfargotunnel.com
;
启动服务
进入到docker-compose.yml电脑进行操作,执行docker-compose up -d
, 然后检查Cloudflare上tunnel的情况,如果是HEALTHY则表示成功。
配置ssh客户端
在需要连接ssh的电脑上执行ssh <YOUR-NAME>@<DOMAIN NAME>
会发现一个问题,无法登录上。其原因是在客户端还需要进行以下配置。
- 下载cloudflared客户端,如果是windows就下载windows的,linux就下载linux的;
- 配置cloudflared二进制所在的地址到环境变量中;
- 打开
~/.ssh/config
文件,添加以下内容:
Host <YOUR-DOMAIN-NAME>
ProxyCommand cloudflared.exe access ssh --hostname %h
- 然后执行ssh指令: 然后发现即可登录成功。
**这一步非常重要**
docker方式二
使用docker还有一种方式,不适用token,而是使用config.yml
和TUNNEL-ID.json
的方式,这里基于这个方式做一些介绍。
前面几步基本一致,不过docker-compose文件需要做一些修改:
version: "3.9"
services:
tunnel:
image: cloudflare/cloudflared:2023.3.1
container_name: cloudflared
command: tunnel --no-autoupdate --config /root/.cloudflared/config.yml run
user: root
restart: unless-stopped
network_mode: host
volumes:
- ./data:/root/.cloudflared
然后,再在当前目录创建一个data目录,然后创建两个文件config.yml
和<YOUR-TUNNEL-ID>.json
,例如(这里除了配置ssh以外还配置了http):
这里对config.yml
文件的内容和<YOUR-TUNNEL-ID>.json
进行一些介绍。
config.yml
一个例子:
tunnel: <YOUR-TUNNEL-ID>
credentials-file: /root/.cloudflared/<YOUR-TUNNEL-ID>.json
protocol: http2
ingress:
- hostname: YOUR-DOMAIN-NAME
service: ssh://localhost:22
- service: http_status:404
很容易看出来,主要是根据配置对tunnel进行描述。这里有几个需要提及的:
- 最后一个
service: http_status: 404
,保留,保底规则; credentials-file
:认证文件,扮演的角色和token是一样的,其本质是token的base64解析后简单调整的内容;
<YOUR-TUNNEL-ID>.json
{"AccountTag":"<YOUR-ACCOUT-TAG>","TunnelSecret":"<YOUR-TUNNEL-SECRET>","TunnelID":"<YOUR-TUNNEL-ID>"}
其中用<>
包裹的内容可以通过对token的base64解析得到。
可以通过`cloudflared tunnel token <YOUR-TUNNEL-ID>`来获取,也可以通过网页上获取。
评论区