把 base64 訂閱、原生 JSON 設定與 vmess、vless 分享連結三種格式拆開對照,給出「訂閱 → 連結清單 → 單一節點欄位 → 原生 JSON」的完整轉換路徑,並列出轉換過程中最容易遺失的欄位。適合已經能連上節點、需要手動修改設定或跨用戶端移轉的讀者。
三種格式分別是什麼
同一組節點資訊,放進不同載體後長得完全不一樣。base64 訂閱是批次清單,原生 JSON 是完整設定,分享連結是單筆記錄。
三者的資訊量並不對等:訂閱裡的一條連結通常只描述一個出站(outbound),而原生 JSON 還要額外承擔入站、路由、DNS、日誌這些用戶端側設定。混淆這一點,是後面所有轉換問題的起點。
| 維度 | base64 訂閱 | 原生 JSON | 分享連結 |
|---|---|---|---|
| 承載內容 | 多行分享連結 | 完整設定,含出站、入站與路由 | 單一節點的連線參數 |
| 自動更新 | 用戶端定時拉取 | 手動替換檔案 | 不支援 |
| 典型來源 | 面板批次匯出 | 伺服器端設定檔或手動撰寫 | 用戶端、面板單筆複製 |
| 適用情境 | 多裝置共用一份節點清單 | 精細分流與固定本機連接埠 | 臨時匯入、跨用戶端移轉 |
base64 訂閱的編碼規則
base64 訂閱只多一層編碼:伺服器端把多行分享連結拼成純文字,整體做一次 base64,再作為 HTTP 回應傳回。用戶端拉取後先解碼,拿到每行一條的連結清單。
解碼失敗時,用戶端會退回以明文處理,所以同一套解析邏輯能同時處理 base64 與明文兩種訂閱。自己動手解碼時,記住下面這條指令就夠。
# 訂閱回傳的原文存成 sub.txt,整體解碼一次
base64 -d sub.txt > nodes.txt # GNU coreutils
base64 -D sub.txt > nodes.txt # macOS / BSD
wc -l nodes.txt # 行數一般等於節點條數
head -n 2 nodes.txt
解碼結果裡每行開頭就是協議前綴,常見的是 vmess:// 與 vless://。同一條訂閱混用多種前綴是正常的,用戶端會按行逐條解析。
- URL-safe 變體:部分面板會把
+、/換成-、_,解碼前要換回來,或直接用支援 URL-safe 的解碼器。 - padding:結尾的
=常被省略,長度不是 4 的倍數時手動補齊再解。 - 逐行與整體:少數訂閱會對每行連結個別編碼,這種情況要按行解碼,整體解一次只會得到亂碼。
如果解出來的第一行不是 vmess:// 也不是 vless://,代表原文本來就是明文訂閱,不需要再解。
分享連結的欄位結構
vmess 與 vless 的差別在編碼方式:vmess 連結是「base64 包一層 JSON」,vless 連結是「URI 加查詢參數」。前者解出來的欄位名稱全是縮寫,後者直接在網址列就能讀。
把 vmess:// 後面的整段 base64 解一次,得到的是下面這個物件:
{
"v": "2", // 連結格式版本,固定為 2
"ps": "香港-01", // 備註,匯入後作為節點名稱
"add": "example.com", // 伺服器位址
"port": "443", // 連接埠,這裡是字串
"id": "b831381d-6324-4d53-ad4f-8cda48b30811",
"aid": "0", // alterId,僅 VMess 有
"scy": "auto", // 加密方式
"net": "ws", // 傳輸層
"type": "none", // 偽裝類型
"host": "example.com", // WS 的 Host 標頭
"path": "/ws", // WS 路徑
"tls": "tls" // 是否啟用 TLS
}
vless 連結沒有內層 base64,所有參數都寫在 ? 之後的查詢字串裡,# 之後是備註。參數名稱比 vmess 的縮寫更直觀,但要按 URI 規則做 URL 編碼。
vless://[email protected]:443?encryption=none&security=reality&sni=www.example.com&fp=chrome&pbk=UuMBgl8KtNqHqY7p&sid=0123abcd&flow=xtls-rprx-vision&type=tcp#香港-01
兩種連結描述的是同一件事,只是欄位名稱和擺放位置不同。下面四張卡片把常用欄位、原生 JSON 的頂層結構與本機連接埠慣例放在一起對照。
vmess 連結欄位
- add / port
- 位址與連接埠,port 是字串
- id / aid
- UUID 與 alterId
- scy
- 加密方式,常用 auto 或 none
- net / type
- 傳輸層與偽裝類型
- path / host
- WS 路徑與 Host 標頭
整段是 base64(JSON),解一次即可讀。
vless 連結參數
- encryption
- 固定為 none,不可省略
- security
- none / tls / reality
- sni
- TLS 憑證網域名稱
- flow
- Reality 節點填 xtls-rprx-vision
- pbk / sid
- Reality 公鑰與短 ID
參數寫在查詢字串裡,注意 URL 編碼。
原生 JSON 頂層
- inbounds
- 本機監聽,如 SOCKS 10808
- outbounds
- 出站節點,含 tag 與 streamSettings
- routing
- 分流規則,依 outboundTag 指向出站
- dns
- 解析方式與上游伺服器
- log
- 日誌等級,排查時用 debug
欄位名稱區分大小寫,port 必須是數字。
本機連接埠慣例
- SOCKS
- 10808
- HTTP
- 10809
- 日誌等級
- warning / debug
- 出站 tag
- proxy、direct、block 三個常用名稱
連接埠與 tag 由本機設定決定,與訂閱無關。
三種格式怎麼互相轉換
轉換路徑固定為四步:訂閱解出連結清單,連結還原成欄位,欄位再拼成原生 JSON。反向走一遍就是匯出。
取出訂閱原文
用瀏覽器開啟訂閱網址,把回傳內容整段存成 sub.txt。回傳的可能是一整段 base64,也可能是明文連結清單。
解出連結清單
執行
base64 -d sub.txt > nodes.txt,得到每行一條的分享連結;協議前綴在行首,備註在行尾#之後。還原單一節點
vmess 要把
vmess://後的內容再解一次 base64 得到 JSON;vless 直接讀?後的查詢參數,不需要再解碼。拼成原生 JSON
把欄位填進
outbounds的vnext與streamSettings:port改成數字,tag自己命名,address不帶協議前綴。
第四步拼出來的出站大致長這樣,欄位與上面的 vless 連結一一對應:
{
"outbounds": [{
"tag": "proxy",
"protocol": "vless",
"settings": {
"vnext": [{
"address": "example.com",
"port": 443,
"users": [{
"id": "b831381d-6324-4d53-ad4f-8cda48b30811",
"encryption": "none",
"flow": "xtls-rprx-vision"
}]
}]
},
"streamSettings": {
"network": "tcp",
"security": "reality",
"realitySettings": {
"serverName": "www.example.com",
"publicKey": "UuMBgl8KtNqHqY7p",
"shortId": "0123abcd",
"fingerprint": "chrome"
}
}
}] // 出站陣列
}
反向轉換同理:原生 JSON 裡的 settings.vnext[0] 與 streamSettings 就是連結參數的展開形式,把 address、port、id 取出來,再按協議規則編碼回 URI 即可。VMess 還要把 alterId 寫回 aid。
用戶端裡還有兩條更省事的路徑:v2rayN 支援「自訂設定」類型的伺服器,把完整 JSON 貼進設定框後核心直接讀取,不再由用戶端拼裝出站;反過來,從訂閱清單複製單一節點的分享連結,可以直接貼到另一台裝置的 v2rayNG 裡,走「⋮」→「從剪貼簿匯入設定」。
轉換時最容易遺漏的欄位
掉欄位幾乎都發生在手動搬運的環節:複製貼上時被截斷、字串與數字混用、縮寫看漏一個字母。下面這些位置逐條對一遍,能涵蓋大部分「匯入成功但連不上」的情況。
flow=xtls-rprx-vision:Reality 節點必填。漏掉後用戶端會以一般 VLESS 處理,伺服器端握手直接失敗。pbk與sid:Reality 的公鑰與短 ID 成對出現,只複製其中一個等於沒抄。encryption=none:VLESS 的固定值,漏寫時部分用戶端會拒絕匯入這條連結。aid:VMess 的 alterId,連結裡是字串,原生 JSON 裡是數字;舊伺服器端常用 2 或 64,漏填會以 0 處理而導致握手失敗。port的型別:連結 JSON 裡是"443",原生 JSON 裡必須是443,帶引號會被核心判定為無效設定。serviceName:type=grpc時用它代替path,兩者填反會導致請求路徑對不上。host與sni:前者是 WS 的 Host 標頭,後者是 TLS SNI。CDN 情境下兩者不同是正常的,填反會回傳 403。outboundTag:routing.rules裡的值必須與outbounds的tag完全一致,且區分大小寫。
注意
手動修改原生 JSON 時,儲存前先用編輯器跑一次 JSON 語法檢查,尾隨逗號與缺少的引號是最常見的兩類錯誤。排查階段先把 log.loglevel 設為 debug,讓核心把出錯欄位寫進日誌,定位完再改回 warning。
什麼情境該用哪一種
三種格式沒有優劣,只有分工。判斷依據只有兩條:節點清單會不會變,以及本機需不需要分流規則。
選擇依據:節點是否會變、是否需要本機分流
base64 訂閱
- 一條網址管理全部節點
- 換裝置只填一次,清單自動同步
- 節點增刪由伺服器端決定,本機不用改
- 適合多裝置、節點會調整的情境
原生 JSON
- 可以寫 routing 分流規則與 DNS 策略
- 本機 SOCKS 10808、HTTP 10809 連接埠固定
- 節點異動要手動替換檔案
- 適合單機、需要精細控制的情境
兩者可以並存:訂閱負責節點清單,原生 JSON 裡的 routing 負責決定哪些流量走代理。
分享連結則居中:它比訂閱更適合臨時匯入,比原生 JSON 更適合跨用戶端複製。同一條連結貼進 v2rayN 與 v2rayNG,得到的出站參數是一樣的,差別只在用戶端把本機連接埠與分流規則放在自己的設定裡。
實際使用中更常見的組合是:伺服器端維護一條訂閱網址,用戶端裡再補一份本機路由規則。節點跟隨訂閱更新,分流邏輯留在本機,兩邊互不干擾。
常見問題
訂閱網址在瀏覽器裡開啟是一串亂碼?
那是 base64 原文,不是出錯。整段複製下來解一次,或直接把網址填進用戶端的訂閱設定裡更新。
vmess 連結匯入後節點名稱變成問號?
ps 欄位是 UTF-8 中文,解碼工具以 GBK 處理就會亂碼。改用 UTF-8 重新解一次再匯入。
vless 連結匯入後提示缺少 flow?
Reality 節點要在 flow 裡填 xtls-rprx-vision,同時補齊 pbk、sid、fp 三組參數。
自己寫的 JSON 被判為無效設定?
先查尾隨逗號與引號,再把 port 從字串改成數字,最後核對 routing.rules[].outboundTag 與出站的 tag 是否一致。
三種格式的轉換關係並不複雜:訂閱解一層得到連結,vmess 連結再解一層得到欄位,欄位展開就是原生 JSON。真正費時間的從來不是解碼,而是把欄位一個不漏地放到正確位置。