requests 庫在使用 cntlm 代理時(shí)的 CONNECT 請(qǐng)求失敗問題及解決方案

昨天有一個(gè)粉絲提出了一個(gè)關(guān)于使用requests庫和cntlm代理的問題,問題涉及到HTTP協(xié)議版本的沖突。在這篇文章中,我們將探討這個(gè)問題的背景和解決方案。
我們在使用requests庫時(shí),通過cntlm代理進(jìn)行認(rèn)證,但是cntlm代理只支持HTTP/1.1協(xié)議。然而,當(dāng)requests庫發(fā)起HTTPS連接時(shí),使用的是HTTP/1.0協(xié)議,這導(dǎo)致了連接失敗的問題。下面我們給出解決方案。
針對(duì)這個(gè)問題,requests庫的開發(fā)者在2017年1月13日給出了回復(fù)。他們指出,目前很難直接在urllib3中解決這個(gè)問題,因?yàn)榘l(fā)起CONNECT請(qǐng)求的是httplib庫,而更改協(xié)議版本并不能解決問題。這是因?yàn)镃ONNECT請(qǐng)求不包含Host頭字段,這不符合HTTP/1.1協(xié)議的要求。
為了解決這個(gè)問題,開發(fā)者建議用戶可以采用以下兩種方法之一:
1. 使用Monkeypatch:用戶可以通過Monkeypatching(代碼注入)的方式來修改httplib庫的行為,使其在發(fā)起CONNECT請(qǐng)求時(shí)使用HTTP/1.1協(xié)議而不是HTTP/1.0協(xié)議。這樣可以暫時(shí)解決問題,但需要謹(jǐn)慎處理,因?yàn)镸onkeypatching可能引入其他不穩(wěn)定性。
2. 重寫httplib的tunnel()邏輯:用戶還可以選擇重寫httplib庫的tunnel()方法,以適應(yīng)cntlm代理的要求。這需要一些編程技巧,但可以更靈活地解決問題。
總結(jié)
這個(gè)問題的根本原因是httplib庫在發(fā)起CONNECT請(qǐng)求時(shí)使用的是HTTP/1.0協(xié)議,而cntlm代理只支持HTTP/1.1協(xié)議,導(dǎo)致了協(xié)議版本的沖突。解決這個(gè)問題的方法是在等待urllib3的v2版本發(fā)布之前,采用Monkeypatch或重寫httplib的tunnel()邏輯。用戶可以根據(jù)自己的需求選擇其中一種方法,以解決這個(gè)問題。希望這個(gè)解決方案對(duì)解決問題的發(fā)起者以及其他遇到類似問題的人有所幫助。