內網穿透—使用 frp 實現內外網互通

小葛師兄 發表於 2021-12-04

前言

什麼是內網穿透?

內網穿透,又叫 NET 穿透,是計算機用語。用通俗的說法就是你家裡的個人電腦,可以直接被外網的人訪問。例如你在公司,不通過遠端工具,直接也可以訪問到家裡的電腦(本文章特指 web 應用程式)。

正常來說我們的個人電腦是無法被別人訪問到的(有固定 ip 除外!),而且現在固定 ip 資源稀缺,運營商也不會隨便給你分配了,個人申請也挺難。

為什麼需要內網穿透?

就我個人而已,需要用到內網穿透的原因:

一是方便訪問公司的內網環境,不喜歡使用遠端工具,挺麻煩的。
二是方便把個人電腦上的應用開放到外網進行訪問。

資源準備

  • 能上網的個人電腦一臺;
  • 有公網 ip 的,個人雲伺服器一臺(阿里雲 or 騰訊雲);
  • 下載 frp 程式

考慮到 github 有些時候訪問不到,我這裡分別下載了 Linux 系統 和 windows 系統的 frp 程式供大家使用:

版本:frp_0.38.0_linux_amd64.tar.gz frp_0.38.0_windows_amd64.zip

https://fenxiangdayuan.lanzouo.com/b00v3dsri 密碼: i0fp

環境搭建

frp 工作原理

frp 的應用程式是分服務端和客戶端的,伺服器端的執行在有公網 ip 的伺服器上,客戶端就執行在需要穿透的內網機器上就行。

兩端的程式執行起來之後,就會建立好通訊的隧道,當我們訪問公網 ip+埠 時,就會對映到我們內網的機器上了。

服務端搭建

  • 把下載好的 frp 程式,上傳到我們雲伺服器上解壓出來即可:
tar -xvzf frp_0.38.0_linux_amd64 #解壓
mv frp_0.38.0_linux_amd64 frp  #重新命名一下
  • 進入到 frp 目錄下

image-20211204220122249

我們看到 frp 目錄下的一些檔案,很明顯分為兩部分:

frpc 開頭的代表著客戶端使用;

frps 開頭的代表服務端使用;

.ini 結尾的檔案是 frp 的配置檔案,也是需要我們進行修改的檔案。

  • 我們開啟 frps.ini 配置檔案檢視

image-20211204220725021

裡面就只有一個配置項,表示監聽伺服器的 7000 埠,作為客戶端通訊的入口;

在這裡有一個注意的點,如果我們雲伺服器沒開放這個埠的話,我們客戶端是無法和伺服器進行通訊的,這個時候我們需要在控制檯的安全組規則中開放 7000 埠;

  • 一切準備就緒,我們啟動一下服務端的 frp 程式
frps -c frps.ini
frps -c frps.ini &  #後臺執行

image-20211204221455871

看到服務端就正常啟動起來了,正在監聽 7000 埠;

這個時候我們繼續往下配置客戶端即可;

客戶端搭建

有了服務端的配置說明,配置客戶端也就是照貓畫虎,我們只需要關注 frpc 開頭的檔案即可;

windows 和 Linux 的檔案都一樣,只是執行的平臺不同而已。

下面演示在我個人電腦虛擬機器中的 Linux 系統,作為客戶端,frp 怎麼配置;

  • 同樣的步驟,解壓下 Linux 版本的 frp ,然後開啟 frpc.ini 檔案:

image-20211204222420329

server_addr : 需要填寫上你個人雲伺服器的公網 ip 地址,這個一定要填寫正確,不然無法和伺服器進行通訊;

server_port :就是伺服器監聽的埠,預設可以不用修改;

這兩部分就是用來和我們伺服器進行通訊的配置。

[ssh] 這部分就是建立隧道,也就對映對應的應用,這裡對映的是 ssh;

我們只需要關注 remote_port 這個配置就行,這裡需要填寫你伺服器上開放的埠,未開放的話,通過雲伺服器控制檯,安全組策略進行配置。

這裡的意思就是把伺服器的 6000 埠對映到內網機器的 22 埠上。

當我們訪問公網 ip + 6000 埠時,就會訪問到我們內網電腦 22 埠的應用,這裡就是 ssh;

  • 配置好之後,接下來我們執行 frp 的客戶端程式
frpc -c frpc.ini

image-20211204223439870

圖中我們可以看到,客戶端啟動成功,也和我們的伺服器建立了通訊;

TCP 穿透

TCP 穿透的意思,就是通訊協議型別為 TCP, 常見的 ssh、mysql等等

通過上面服務端和客戶端的配置,frp 就搭建成功了,對應 TCP 穿透的配置如下:

  • 服務端
[common]
bind_port = 7000
  • 客戶端
[common]
server_addr = 雲伺服器ip
server_port = 7000

[ssh]
type = tcp
local_ip = 127.0.0.1
local_port = 22
remote_port = 6000

接下來我們就來測試下,是否能穿透成功,在我們伺服器上進行連線我們內網的 Linux 系統:

ssh 127.0.0.1 -l root -p 6000

image-20211204224545282

從圖中我們可以看到,ssh 的穿透已經成功了,我們檢視 ip 也是內網中的ip;

通過 TCP 的穿透,我們就可以利用它來穿我們公司內網的伺服器了,從而在家裡我們也能正常操作公司的內網環境。

HTTP 穿透

HTTP 穿透,也就是我們應用層面的通訊協議,http協議;穿透它是為了方便我們訪問內網的 web 應用,例如我在內網機器,起了一個 tomcat 部署了一個網站,我想讓其他人外網的人來訪問我,那就需要進行 HTTP 的穿透;

對應的 frp 配置這時和 TCP 是有一點區別的,如下:

  • 服務端
[common]
bind_port = 7000
vhost_http_port = 80 #將伺服器的 80 埠用作 http 協議的通訊
vhost_https_port = 443 #進伺服器的 443 埠用作 https 協議通訊
privilege_token = token123456789 #frp的認證,對應的客戶也需要配置一樣,才可以進行通訊
  • 客戶端
[common]
server_addr = 雲伺服器ip
server_port = 7000
privilege_token = token123456789 #frp的認證

[web_http]
type=http #通訊型別為http
local_ip = 127.0.0.1
local_port = 8080
custom_domains = 二級域名/公網ip

[ssh]
type = tcp
local_ip = 127.0.0.1
local_port = 22
remote_port = 6000

http 的穿透,我們看到服務端和客戶端的配置檔案都進行了改動,我們重點來看下客戶單中的配置;

type = http : 這個是因為我們想要建立的隧道是進行 http 通訊的,也就是用來訪問本地 web 應用;

custom_domains = 二級域名/公網ip :這個配置一般使用一個二級域名來配置,用於通過域名來訪問你的穿透伺服器,如果沒有域名,那麼我們寫上一個伺服器的公網 ip 也是可以的,用 ip 的話,在外網訪問的時候,就只能通過 ip 進行訪問了,效果都一樣;

下面我們看下效果:

  • 先在我內網電腦啟動一個 tomcat,監聽埠為:8080

image-20211204232323142

image-20211204232429648

可以看到,在我的內網物理機中訪問,是正常啟動了的;

  • 接著我們把 frp 客戶端和服務端進行連線上

image-20211204232654119

  • 成功連線之後,我們直接通過外網 ip 進行訪問

image-20211204232932778

可以看到,我直接用公網 ip 訪問,同樣能開啟我們內網中的 tomcat 應用;

也證明了我們的 HTTP 穿透也是成功的。

注意事項

  • 客戶端的配置項,不同的隧道需要區分開,寫上不同的名字,如[ssh]、[mysql]、[web_http];

  • 客戶端中 remote_port 的埠號不能一樣,一樣會衝突;

  • 伺服器對映的埠需要放開範圍,沒有放開會造成無法通訊;

  • 服務端和客戶端都需要注意埠的衝突;

參考文章

frp 配置詳解:

https://www.cnblogs.com/sanduzxcvbnm/p/8508988.html

內網穿透不同工具(Ngrok、釘釘、花生殼、frp):

https://www.it235.com/實用工具/內網穿透/pierce.html