reqable 抓 HTTPS 流量的底層原理:MITM 中間人與腳本引擎怎麼協作
深入拆解 reqable 如何透過 CA 根證書建立中間人代理、用 Python 腳本鉤子改寫請求與響應,以及這套設計的邊界與取捨。
reqable 是什麼:一款把專業性拉滿的 HTTP 開發調試工具
如果你曾經在 Android 裝置上開發或測試 App,一定遇過這樣的場景:想看清 App 跟後端之間到底發了什麼請求、回了什麼內容,內建的調試工具要嘛資訊不全、要嘛需要改程式碼加 logging,改完還要重編譯重安裝,整個流程下來浪費掉的時間遠多過真正排查問題的時間。
reqable 就是為這件事而生的。它本質上是一個 HTTP/HTTPS 流量抓包代理,但跟傳統的 Fiddler 或 Charles 相比,它把三件事做到了手機端也能跑、而且體驗不打折:即時擷取並解析 App 的網路通信數據、支援 HTTP/1 到 HTTP/2 幾乎所有網路協定、抓到的流量能直接改寫或重發。對開發者來說,它省去了加 logging、重編譯、重安裝這條老路;對測試人員來說,它意味著能在不改程式碼的情況下還原各種網路環境下的 bug。
但 reqable 真正有意思的地方不在「能抓包」這件事本身——這件事已經被做了十年。它有意思的地方在底層的設計取捨:為什麼它在 Android 上也能抓到 HTTPS 明文?為什麼它提供 Python 腳本而不是自訂規則語言?這些設計背後的理由,才是理解這款工具的關鍵,進一步的細節可以參考 reqable官網 的說明。
安裝
reqable 的 Android 安裝包體積約 30.80M,目前最新版本是 3.0.30,更新活躍。安裝流程本身不複雜,但有一個繞不開的前置條件要先講清楚:你要抓 HTTPS 流量,就必須在裝置上安裝 CA 根證書。
先說 APK 安裝本身:reqable下載到 Android 裝置後,第一次安裝會提示開啟「未知來源」允許。這是 Android 的標準安全機制,不是 reqable 特有的問題。安裝完啟動,App 會引導你完成兩件事:一是設定系統代理,讓裝置的網路流量指向 reqable;二是安裝 CA 根證書。
證書這一步是很多人第一次用抓包工具時會卡住的地方。reqable 在首次啟動時會引導你下載並安裝它自動生成的 CA 根證書——每台裝置生成的證書都不同,用的是隨機密鑰,不存在一把通用私鑰的安全風險。安裝位置是 Android 系統的「使用者證書」儲存區,需要手動確認幾次系統彈窗。
一個常見坑:Android 7.0 起,預設不再信任使用者安裝的 CA 證書,這意味著某些 App(尤其是 targetSdkVersion 24+ 的)即使你裝了證書也抓不到 HTTPS 明文。這不是 reqable 的問題,是 Android 的安全策略——要繞過它需要 App 本身在 network security config 裡顯式允許使用者證書,或者 root 後把證書移到系統證書目錄。reqable文檔對這個限制有清楚說明,但很多人第一次碰到時還是會以為工具壞了。
安裝完成後,reqable 會進入待機狀態,這時候打開系統瀏覽器隨便訪問一個 https 的網站,回來看 reqable 的列表就應該能看到對應的請求條目——如果沒有,回頭檢查系統代理是否正確指向了 reqable 的監聽端口。
為什麼 HTTPS 能被解密:MITM 中間人機制的拆解
現在進入真正有意思的部分。HTTPS 本身是加密的,客戶端和伺服器之間的連線經過 TLS 握手建立後,所有流量都是密文——那麼 reqable 怎麼看到明文?
答案是它用了經典的 MITM(Man-in-the-Middle,中間人)代理模式。整個流程可以拆成三步:
第一步:客戶端把請求發給 reqable,而不是直接發給目標伺服器。 這是靠系統代理設定實現的——Android 裝置上的所有 HTTP/HTTPS 請求,只要系統代理開著,都會先到 reqable 的監聽端口。
第二步:reqable 充當中間人,分別跟客戶端和目標伺服器建立兩條獨立的 TLS 連線。 對客戶端來說,reqable 要冒充目標伺服器完成握手——這時候它需要一張證書來「證明」自己就是那個伺服器。這張證書不是真的,是 reqable 用你安裝的 CA 根證書重簽的。
第三步:客戶端驗證這張重簽證書的簽發者是不是自己信任的 CA。 這就是為什麼必須先裝 CA 根證書——沒有這一步,客戶端一眼就能看出這張證書的簽發者自己不認識,直接拒絕連線,也就是你第一次用抓包工具時一定會碰到的 SSL 握手失敗。
用一個生活化的類比:這就像你去銀行辦業務,正常情況下你跟銀行櫃檯直接對話。但如果有一個中間人站在你和櫃檯之間,他也能冒充櫃檯跟你說話——前提是你事先把銀行的公章給了他,他才能在冒充你的身份時蓋出你認得的章。你安裝 CA 根證書這件事,就是把公章交給 reqable 的那個動作。
這套機制的設計取捨很明確:它的優點是對 App 完全透明——不需要 App 做任何改動,只要系統代理生效、證書裝好,就能抓到所有明文流量。代價是安全隱患——把 CA 根證書裝到系統裡,理論上任何拿到這把私鑰的人都能對你的 HTTPS 流量做 MITM 攻擊。reqable 用「每台裝置自動生成不同密鑰」來規避這個風險,這是個不錯的工程決策——但如果你是在測試環境以外的場景用它,用完後最好把證書卸掉。
還有一個邊界條件:有些 App 會啟用 SSL Pinning——也就是把伺服器證書的指紋硬編碼在 App 裡,握手時直接比對證書本身而不是驗證 CA 鏈。這種情況下即使你裝了 CA 根證書也沒用,客戶端會發現證書指紋跟硬編碼的對不上,直接斷連。reqable 對這種場景的應對方式在文件裡有提到,但那已經超出了「正常抓包」的範疇。
Python 腳本引擎:為什麼選 Python 而不是自訂規則語言
抓包只是第一步,真正厲害的是抓到之後能做什麼。很多抓包工具提供「規則」功能——按 URL 匹配、改寫請求頭、攔截響應,這些功能都很實用,但複雜一點的場景就不夠了。reqable 的選擇是:直接嵌入 Python 解譯器,給你兩個鉤子函數。
它提供兩個入口:onRequest 在請求發出去之前被調用,onResponse 在響應回來之前被調用。兩個函數都接收 CaptureContext 和對應的 request/response 對象,返回修改後的對象或 None(返回 None 等於攔截這條流量)。這意味著你能做的事情是無限的——從簡單的改一個 Header、替換響應體,到複雜的跨請求狀態追蹤、條件性重寫、甚至串接外部 API 做資料轉換。
為什麼是 Python 而不是自訂規則語言?我的判斷是兩個原因。第一,Python 的普及度——開發者幾乎都會寫幾行 Python,不需要花時間學一套新的 DSL。第二,Python 的生態——如果你真的需要做複雜的資料處理、加密解密、格式轉換,Python 的標準庫和第三方套件直接能用,自訂語言做不到這一點。
但這裡有一個容易踩的坑,也揭示了這套設計的另一層取捨:onRequest 和 onResponse 運行在不同的進程中,不能直接共享變數。reqable 用 CaptureContext.shared 這個字典來解決跨函數資料傳遞的問題——在 onRequest 裡寫 context.shared = 'foobar',到了 onResponse 裡就能通過同一個鍵讀回來。這個設計的代價是:任何你想在兩個鉤子之間傳遞的資料都必須經過序列化(dict → JSON),複雜對象傳遞會有額外成本。
這套 Python 腳本引擎的優點在於靈活性——你能做任何你想做的事情。代價在於安全性與性能——腳本運行在抓包代理的同一個進程組裡,惡意腳本能做的事情很多;而且 Python 的執行速度當然比原生碼慢,如果你在每個請求上都跑一段複雜腳本,代理本身會成為性能瓶頸。reqable 的應對方式是給腳本規則提供 URL 匹配模式——只有命中的流量才進入腳本,其他流量透明透傳,把開銷控制在必要範圍內。

歷史記錄與書籤:後事回溯的設計邏輯
抓包是個「一次性視窗」的工作方式——你當下看到的流量,關掉 App 就沒了。但現實中問題常常不是當場定位的,你可能今天抓到了一個異常請求,三天後才意識到那個請求就是 bug 的根源。reqable 的歷史記錄和書籤功能就是為這個場景設計的。
歷史記錄面板(快捷鍵 F4)會自動保存過去會話的流量資料。你清空當前調試列表不影響歷史——隨時可以回去翻舊賬。免費社區版保留最近 30 天的歷史,付費版放開。這個設計的核心取捨是自動化——它不需要你手動操作,抓包資料自動落盤,代價是存儲空間佔用,reqable 允許你在設定裡調整歷史保留長度來平衡。
書籤是歷史的補充。對高頻復查的請求,收藏成書籤比每次翻歷史快得多——而且書籤支援資料夾組織,你可以按專案、按介面分門別類。免費版限制 2 個資料夾,付費版放開。
這兩個功能加上 API 集合(可復用的請求用例庫),三者的定位層級很清楚:歷史是自動的時間軸,書籤是手動的重要位點,集合是可復用的用例庫。按需分層使用,不用每次都去翻歷史,也不用每個請求都存成書籤。
這套設計意味著什麼
拆解完 MITM 代理、Python 腳本引擎和歷史回溯機制,我們可以得出一個判斷:reqable 的設計團隊面臨過很多取捨——透明性 vs 安全性、靈活性 vs 簡潔性、自動化 vs 存儲成本——但在每一個取捨面前,他們的選擇都偏向了「給開發者最大的控制力」。
這意味著 reqable 適合已經懂 HTTPS、懂網路協定、腳本寫得來的開發者和測試人員——如果你是初學者,看到 CA 根證書的 MITM 原理可能會有點懵,Python 腳本的鉤子機制也需要一點編寫基礎。但一旦你跨过了這個門檻,它帶來的效率提升是真實的:省去了加 logging 重編譯的老路、能在不改程式碼的情況下模擬各種網路場景、抓到的資料能直接轉成 cURL 或程式碼拷進專案。
不適用的場景也很明確:如果你要測的 App 啟用了 SSL Pinning、如果你在測試環境以外的場景長時間掛著 CA 根證書、如果你需要極低延遲的代理轉發——這些場景下 reqable 不是最佳選擇,甚至可能完全用不了。
但對 Android App 開發測試這個定位來說,它已經做到了幾乎所有能做到的事情,而且在每一個設計決策上都有明確的理由和取捨——這本身就是一款成熟工具的標誌。
本文为个人基于网络公开资料整理编写,非官方内容,仅供学习交流参考;软件版权归原作者所有,请支持正版;使用过程中遇到问题请查阅官方渠道,本文不承担任何责任。
