轉(zhuǎn)載自:http://mrpeak.cn/blog/mitmproxy/
現(xiàn)階段給iOS設(shè)備進(jìn)行網(wǎng)絡(luò)抓包的手段非常之多,除了我之前介紹的tcpdump,wireshark之外,還有Charles,以及和Charles同樣好用的mitmproxy,其實(shí)還有更多,比如更小眾的debookee。似乎知道Charles的同學(xué)更多一些,但其實(shí)Charles有的功能mitmproxy基本都有,mitmproxy還免費(fèi),而且對(duì)于terminal用戶來說使用起來更親近。
如何使用mitmproxy?
安裝mitmproxy
我們可以通過brew或者pip來安裝mitmproxy,沒有安裝brew的同學(xué)可以先通過如下命令安裝brew:
/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"
完成之后,執(zhí)行如下命令安裝mitmproxy
使用mitmproxy抓包
第一步,首先啟動(dòng)mitmproxy,在terminal輸入:
第二步,再在iPhone上設(shè)置http代理:

IP地址填你Mac系統(tǒng)當(dāng)前的IP,端口默認(rèn)8080。
可以通過在terminal輸入ifconfig en0獲取Mac的IP地址:

第三步,第一次使用mitmproxy的時(shí)候需要在iPhone上安裝CA證書,這一步和Charles一樣都需要做,原因后面解釋。打開iPhone Safari,輸入地址:mitm.it,在下圖中點(diǎn)擊Apple安裝證書。

第三步只需要做一次。
觀察mitmproxy流量
接下來我們就可以使用mitmproxy查看所有通過iPhone端的http請(qǐng)求了,包括https請(qǐng)求,如何破解https流量的后面也會(huì)分析。
mitmproxy初看起來可能不如Charles直觀,其實(shí)稍微把玩下就用起來很順了,mitmproxy是基于terminal交互的,主要分為兩個(gè)界面:請(qǐng)求列表界面和請(qǐng)求詳情界面。
請(qǐng)求列表界面

請(qǐng)求詳情界面

大部分時(shí)候我們都是在這兩個(gè)界面之間切換,切換方式也非常簡(jiǎn)單。可以在列表界面,用鼠標(biāo)點(diǎn)擊某個(gè)請(qǐng)求進(jìn)入詳情界面,但mitmproxy美妙之處在于可以用快捷鍵來完成界面的切換和功能的使用,而且快捷鍵與vim保持一致。
所以我們可以:
- 在列表界面,按用j,k或者上下方向鍵在列表上瀏覽。
- 在列表界面,按回車進(jìn)入詳情界面。
- 在詳情界面,按q,返回列表界面。
- 在詳情界面,按tab鍵或者h(yuǎn),l,在Request,Response,Detail三個(gè)tab之間切換。按j,k或者上下方向鍵可以滾動(dòng)查看詳情。
- 在列表界面,按G跳到最新一個(gè)請(qǐng)求。
- 在列表界面,按g跳到第一個(gè)請(qǐng)求。
- 在列表界面,按d刪除當(dāng)前選中的請(qǐng)求,按D恢復(fù)剛才刪除的請(qǐng)求。
上面上面的幾個(gè)快捷鍵就基本可以完成絕大部分的HTTP請(qǐng)求分析。
攔截http請(qǐng)求
mitmproxy也可以攔截請(qǐng)求,操作起來也很方便。
我們現(xiàn)在列表界面輸入i,進(jìn)入Intercept Filter模式。按esc可以退出intercept filter模式。

在intercept filter模式輸入我們想要的filter就可以開始攔截了,比如我輸入baidu\.com,按回車,所有域名中帶baidu.com的請(qǐng)求就被攔截了,被攔截的請(qǐng)求會(huì)用橙色標(biāo)記出來:

請(qǐng)求攔截會(huì)后可以編輯后再發(fā)送,也可以直接放行,按a就直接放行了。
編輯請(qǐng)求再發(fā)送
在上面攔截請(qǐng)求之后,我們可以編輯之后再發(fā)送。首先當(dāng)選中被攔截的請(qǐng)求按回車進(jìn)入詳情頁面,在詳情頁面按tab鍵可以在三個(gè)tab(Request,response,detail)之間切換,按e之后進(jìn)入詳情編輯模式:

按e進(jìn)入編輯模式之后,我們要進(jìn)一步選擇編輯的request部分,如下圖箭頭所示選中一個(gè)按對(duì)應(yīng)的字母就可以了:

之后就可以使用方向鍵或者h(yuǎn),j,,k,l,選中自己想要編輯的字段,回車之后就可以輸入新內(nèi)容,按esc退出當(dāng)前編輯,按a可以再新建一個(gè)field,按d可以刪除當(dāng)前field,按esc退回上一個(gè)界面,下圖為Request Header的edit界面:

看著快捷鍵挺多,其實(shí)和vim非常相似,把玩?zhèn)€幾分鐘之后就可以熟練使用了,比Charles的圖形界面點(diǎn)擊起來要快捷很多。
mitmproxy還有很多其他的功能,感興趣的可以去官網(wǎng)https://mitmproxy.org查看。
用一句話總結(jié)mitmproxy:既免費(fèi)又好用。
為何要安裝CA證書?
同Charles一樣,mitmproxy也需要在iPhone設(shè)備上安裝CA證書。
這是因?yàn)閙itmproxy要攔截解析https請(qǐng)求的話,要實(shí)施中間人攻擊。正常情況下中間人攻擊無法通過客戶端的證書校驗(yàn),mitmproxy的做法是臨時(shí)實(shí)時(shí)的生成自己的證書,但這臨時(shí)的證書要被客戶端信任,就只能在iPhone設(shè)備上安裝一個(gè)被信任的CA來簽發(fā)臨時(shí)的證書。也就是說,你信任了安裝的mitmproxy的證書,也就信任了mitmproxy作為CA所簽發(fā)的所有證書。
但是,這是一個(gè)非常危險(xiǎn)的行為。
安裝信任第三方CA證書是個(gè)危險(xiǎn)的行為,無論是Charles還是mitmproxy,信任之后,第三方就可以無條件實(shí)施中間人攻擊了,你手機(jī)上很多App自以為安全的https連接通道都不再安全了,你的Safari通過https瀏覽的網(wǎng)頁內(nèi)容也可能被竊聽了。
所以,建議調(diào)試完之后在手機(jī)上刪除第三方CA證書。
無論是Charles,還是mitmproxy,在調(diào)試完之后記得在【設(shè)置】-【通用】-【描述文件】中刪除證書。
mitmproxy是如何實(shí)施中間人攻擊的?
知其然還要知其所以然,學(xué)會(huì)用工具之后還要明白工具背后的原理,mitmproxy是如何實(shí)施中間人攻擊的呢?
證書校驗(yàn)中一個(gè)重要環(huán)節(jié)是hostname驗(yàn)證。
獲取正確的hostname
mitmproxy作為https代理,捕捉到手機(jī)端的請(qǐng)求之后,會(huì)發(fā)送一個(gè)同樣的請(qǐng)求到server,并和server展開安全握手獲取server的Certificate,再?gòu)腃ertificate中獲取Common Name和Subject Alternative Name。簽一個(gè)和Common Name,Subject Alternative Name一致的證書就可以騙過客戶端了。所以即使客戶端請(qǐng)求是使用的IP地址,這種方式也是行得通的。
如何防止中間人攻擊?
iOS預(yù)防上述的中間人攻擊也很簡(jiǎn)單,在客戶端App做ssl pinning就可以了。
ssl pining分為certificate pinning和public key pinning兩種,目前主流的第三方HTTP framework(AFNetworking和Alamofire)都支持ssl pinning功能。
做了證書或者公鑰綁定之后,Charles和mitmproxy的https流量都無法正常獲取了。
另外我個(gè)人建議不光要做ssl pinning,任何經(jīng)過https發(fā)送的內(nèi)容App要再自己做一層加密,沒有絕對(duì)的安全,保不準(zhǔn)哪天https流量就被人破解了。
之前Path偷偷上傳用戶通訊錄的丑聞就是因?yàn)椋琍ath既沒有做ssl pinning,也沒有對(duì)上傳的內(nèi)容做加密,最后就只有程序員背鍋了,這種事情產(chǎn)品經(jīng)理又怎么會(huì)了解呢。