python requests模組session的使用建議及整個會話中的所有cookie的方法
話不多說,直接上程式碼
測試程式碼
服務端
下面是用flask做的一個服務端,用來設定cookie以及列印請求時的請求頭
# -*- coding: utf-8 -*- from flask import Flask, make_response, request app = Flask(__name__) @app.route('/a1') def a1(): print(request.headers) rp = make_response() rp.set_cookie('a1', '123') return rp @app.route('/a2') def a2(): print(request.headers) rp = make_response() # rp.set_cookie('a2', '234') return rp @app.route('/a3') def a3(): print(request.headers) rp = make_response() rp.set_cookie('a3', '345') return rp if __name__ == '__main__': app.run(host='0.0.0.0')
客戶端
# -*- coding: utf-8 -*- import requests url1 = 'http://192.168.2.159:5000/a1' url2 = 'http://192.168.2.159:5000/a2' url3 = 'http://192.168.2.159:5000/a3' cookies = requests.utils.cookiejar_from_dict({'test': 'test'}) print(type(cookies), cookies) # RequestsCookieJar 物件 s = requests.session() s.cookies = cookies # 這裡設定的cookie test=test 是所有請求中都會附帶的 s.headers = {'h1':'h1'} # 這裡設定的請求頭h1=h1是所有請求中都會附帶的 r1 = s.get(url1, cookies={'r1': 'r1'},headers={'h2':'h2'}) # 臨時加上cookie r1=r1 和 header h2=h2 下一個請求中不會有此 cookie 和header r2 = s.get(url2) requests.utils.add_dict_to_cookiejar(s.cookies, {'xx': 'xx'}) # 在接下來的請求中,永久新增xx cookie r3 = s.get(url3) # r1.cookies 是一個RequestsCookieJar物件,可以使用 requests.utils.dict_from_cookiejar(r1.cookies) 將其轉換成dict # 我發現可以直接用dict進行轉換,這樣寫起來更方便 print(dict(r1.cookies)) # 列印r1請求的返回結果中設定的cookies print(dict(r2.cookies)) # 列印r2請求的返回結果中設定的cookies print(dict(r3.cookies)) # 列印r3請求的返回結果中設定的cookies print(dict(s.cookies)) # s.cookies中包含整個會話請求中的所有cookie(臨時新增的如上面的r1不包含在內)
先啟動服務端,再啟動客戶端
執行結果
服務端列印結果
192.168.2.159 - - [26/Jun/2019 17:28:00] "GET /a1 HTTP/1.1" 200 - Host: 192.168.2.159:5000 Accept-Encoding: identity H1: h1 H2: h2 Cookie: test=test; r1=r1 192.168.2.159 - - [26/Jun/2019 17:28:00] "GET /a2 HTTP/1.1" 200 - Host: 192.168.2.159:5000 Accept-Encoding: identity H1: h1 Cookie: test=test; a1=123 192.168.2.159 - - [26/Jun/2019 17:28:00] "GET /a3 HTTP/1.1" 200 - Host: 192.168.2.159:5000 Accept-Encoding: identity H1: h1 Cookie: test=test; xx=xx; a1=123
客戶端列印結果
<class 'requests.cookies.RequestsCookieJar'> <RequestsCookieJar[<Cookie test=test for />]>
{'a1': '123'}
{}
{'a3': '345'}
{'test': 'test', 'xx': 'xx', 'a1': '123', 'a3': '345'}
總結及使用建議
通過服務端列印可以看出,如果我們不設定User-Agent, requests模組的請求頭是python-requests/2.21.0,這不是正常瀏覽器的請求頭,這也是為什麼我們做爬蟲時一定要修改請求頭的一個原因
使用requests.session()可以幫助我們儲存這個會話過程中的所有cookie,可以省去我們自己獲取上一個請求的cookie,然後更新cookie後重新設定再進行請求這類操作
通過s.cookies 和s.headers設定的整個會話中都會攜帶的cookie和header
通過s.get(url1, cookies={'r1': 'r1'},headers={'h2':'h2'}) 這種形式設定的cookie和header 不會覆蓋s.cookies和s.headers中設定的請求頭和cookie,只是在此次請求中新增此cookie和header,下個請求中不會攜帶這裡的r1和h2
requests.utils.add_dict_to_cookiejar(s.cookies, {'xx': 'xx'}) 可以給s設定固定cookie: xx ,這種設定的cookie 不是臨時的,後面的請求中都會攜帶
r1.cookies 的結果是RequestsCookieJar物件,可以通過dict對其轉換,得到一個dict,其內容是r1請求響應頭中設定的cookie,如果當前請求沒有被設定新cookie,則dict後的是一個空字典
s.cookies 的結果是整個會話過程(通過s傳送的所有請求的過程)被設定的cookie,所有通過dict(s.cookies) 可以得到所有被設定cookie
建議我們再使用的過程中,把公共部分提前設定好,比如headers,cookies,proxies