python爬蟲學習——requests庫的基本用法

獲取某個網頁

import requests 
r = requests. get('https://www.baidu.com/') 
print(type(r)) 
print(r. status_code) 
print (type(r. text)) 
print(r. text) 
print(r.cookies)

各種請求

# 發送一個 HTTP POST 請求:
r = requests.post("http://httpbin.org/post",
data = {'key':'value'})
r = requests.delete('http://httpbin.org/delete')    
# 發送一個 HTTP delete 請求:
r = requests.head('http://httpbin.org/get')        
 # 發送一個 HTTP head 請求:
r = requests.options('http://httpbin.org/get')      
# 發送一個 HTTP options 請求:

構造get請求傳遞參數

對於 GET 請求,利用 params 這個參數

import requests 
data={
    "key1":"value1",
    "key2":"value2"}
r = requests.get('http://httpbin.org/get', params=data)
print(r.url)
#http://httpbin.org/get?key1=value1&key2=value2

還可以將一個列表作爲值傳入

import requests 
data={
    "key1":"value1",
    "key2":["value2","value3"]}
r = requests.get('http://httpbin.org/get', params=data)
print(r.url)
#http://httpbin.org/get?key1=value1&key2=value2&key2=value3

注意:字典裏值爲 None 的鍵都不會被添加到 URL 的查詢字符串裏。

另外,網頁的返回類型實際上是str類型,但是它很特殊,是 JSON 格式的。 所以,如果想直接解析返回結果,得到一個字典格式的話,可以直接調用 json()方法。 示例如下:

import requests 
r = requests.get('http://httpbin.org/get')
print(r.json())
'''
{'args': {}, 
'headers': {'Accept': '*/*', 'Accept-Encoding': 'gzip, deflate', 'Host': 'httpbin.org', 'User-Agent': 'python-requests/2.23.0', 'X-Amzn-Trace-Id': 'Root=1-5e9b0b15-4d6629f8460bc48037fa4244'}, 'origin': '124.164.123.240', 'url': 'http://httpbin.org/get'}
'''

抓取網頁

以知乎-新聞頁爲例,需要構造請求頭header。可以在開發者工具中找到。

import requests 
headers={
    'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64; rv:68.0) Gecko/20100101 Firefox/68.0'
}
r = requests.get("https://daily.zhihu.com/",headers=headers)
print(r.text)

當然,我們可以在 headers 這個參數中任意添加其他的字段信息。

抓取二進制數據

在上面的例子中,我們抓取的是知乎的一個頁面, 實際上它返回的是一個 HTML 文檔。 如果想抓圖片、音頻、 視頻等文件,應該怎麼辦呢?

圖片、音頻、視頻這些文件本質上都是由二進制碼組成的,由於有特定的保存格式和對應的解析方式, 我們纔可以看到這些形形色色的多媒體。 所以,想要抓取它們,就要拿到它們的二進制碼。

import requests 
r = requests.get("https://github.com/favicon.ico")
with open("favicon.jpg","wb") as f:
    f.write(r.content)

這裏用了 open ()方法,它的第一個參數是文件名稱,第二個參數代表以二進制寫的形式打開,可以向文件裏寫入二進制數據。 運行結束之後,可以發現在文件夾中出現了名爲 favicon.ico 的圖標。

在此構建循環語句即可不斷抓取數據。

POST請求

import requests 
data ={'name ':'germey', 'age':'22'} 
r = requests.post("http://httpbin.org/post", data=data) 
print(r.text) 
#部分輸出:
# "form": {
#   "age": "22", 
#  "name ": "germey"
#}

form 部分就是提交的數據,這就證明 POST請求成功發送了。

響應

發送請求後,得到的自然就是響應。 在上面的實例中,我們使用 text 和 content 獲取了響應的內容。 此外,還有很多屬性和方法可以用來獲取其他信息,比如狀態碼、響應頭、 Cookies 等。

import requests 
r = requests.get('http://www.baidu.com') 
print(type(r.status_code), r.status_code) 
print(type(r.headers), r.headers) 
print ( type(r.cookies), r.cookies)
print(type(r. url), r. url)
print(type(r.history), r.history) 

這裏分別打印輸出 status_code 屬性得到狀態碼,輸出 headers 屬性得到響應頭,輸出cookies 屬性得到 Cookies,輸出 url 屬性得到 URL,輸出 history 屬性得到請求歷史。

文件上傳

import requests 
files = {'file' : open ('favicon.ico','rb')}
r = requests.post('http://httpbin.org/post', files=files) 
print(r.text) 

需要注意的是, favicon.ico 需要和當前腳本在同一 目錄下。 如果有其他文件,當然也可以使用其他文件來上傳,更改 下代碼即可。

這個網站會返回響應,裏面包含 files 這個字段,而 form 字段是空的,這證 明文件上傳部分會單獨有一個 files 字段來標識。

Cookies

先看獲取Cookies

import requests 
r = requests.get('https://www.baidu.com') 
print(r.cookies) 
for key,value in r.cookies.items():
    print(key + '=' + value) 
#<RequestsCookieJar[<Cookie BDORZ=27315 for .baidu.com/>]>
#BDORZ=27315

這裏我們首先調用 Cookies 屬性即可成功得到 Cookies, 可以發現它是 RequestCookieJar 類型。 然後用 items()方法將其轉化爲元組組成的列表, 遍歷輸出每一個 Cookie 的名稱和值, 實現 Cookie 的遍歷解析。

我們也可以直接用 Cookie 來維持登錄狀態, 下面以知乎爲例來說明。

import requests 

header={
    'Host':'www.zhihu.com',
    'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64; rv:68.0) Gecko/20100101 Firefox/68.0',
    'Cookie':'_zap=4f14e95a-0cea-4c5e-b2f7-45cfd43f9809; d_c0="AJCZtnMxyBCPTgURbVjB11p6-JAwsTtJB4E=|1581092643"; _xsrf=VaBV0QQwGFjz01Q9n2AmjAilhHrJXypa; tst=h; q_c1=516c72a5ff954c66b6563ff42e63387d|1585814979000|1582104705000; tshl=; Hm_lvt_98beee57fd2ef70ccdd5ca52b9740c49=1587179989,1587216876,1587216886,1587267050; capsion_ticket="2|1:0|10:1587267052|14:capsion_ticket|44:YTUwMDY3MGYyNmJlNDU0ZTgxNjlhNjMwNWNkYzAxNmQ=|7b8a5ebd3649fb076617379e734a79cd7ef54d1242ddd1841aba6844c9d14727"; l_cap_id="YjJiNjc1MzY0ZmEzNGNlYjlkYThkODEyYmEzOWRiOTk=|1587222516|5a01a93ea68209c1116647750ed2131efa309a3d"; r_cap_id="N2EwMjY0N2NlNTM1NGZlMjliNGNhMGJmOTkyMDc1OTE=|1587222516|238b677c781f1ef90a7ad343d6cdd3871aff3269"; cap_id="OTVhNjZiMDQ3MDkzNGVjY2I5ZTUyNTlhOTcxNzk3Njg=|1587222516|6dd1ed77526aa949bccd4146ef218d8164804a6e"; KLBRSID=031b5396d5ab406499e2ac6fe1bb1a43|1587267062|1587267049; Hm_lpvt_98beee57fd2ef70ccdd5ca52b9740c49=1587267062; SESSIONID=wopWDVALc4X3RJObFrIWNChoNDJpogYSdBPicuRm7vV; JOID=WlgXBkLsoG-SjPrGduF5tDN1xettk80YycmkhT2OnDWm0rGBFgxg_8GF8MN9HDmwsdmzwZheWKVLuonghNnDleo=; osd=V1gXB0vhoG-ThffGduBwuTN1xOJgk80ZwMSkhTyHkTWm07iMFgxh9syF8MJ0ETmwsNC-wZhfUahLuojpidnDlOM=; z_c0="2|1:0|10:1587267060|4:z_c0|92:Mi4xT2JORUJnQUFBQUFBa0ptMmN6SElFQ1lBQUFCZ0FsVk45Qk9KWHdEa0NUcXVheUJDdnJtRzRUVEFHNjFqQThvd013|bb30373e1f13c8b751a3ffc09e8ab4c98780350f77989d93b20be7eb3a0b2fad"'

}
r = requests.get('https://www.zhihu.com/hot',headers=header) 
print(r.text) 

結果中包含了登錄後的結果,當然,你也可以通過 cookies 參數來設置,不過這樣就需要構造 RequestsCookieJar 對象,而且需 要分割一下 cookies。這相對煩瑣

會話維持

在 requests 中,如果直接利用 get()或 post()等方法的確可以做到模擬網頁的請求,但是這實際 上是相當於不同的會話,也就是說相當於你用了兩個瀏覽器打開了不同的頁面。

其實解決這個問題的主要方法就是維持同一個會話, 也就是相當於打開一個新的瀏覽器選項 卡而不是新開一個瀏覽器。 但是我又不想每次設置 cookies ,那該怎麼辦呢?這時候就有了新的 利器——Session 對象。

import requests 
s = requests.Session() 
s.get('http://httpbin.org/cookies/set/number/123456789') 
r = s.get('http://httpbin.org/cookies')
print(r.text) 
#{
#  "cookies": {
#    "number": "123456789"  }}

利用 Session ,可以做到模擬同一個會話而不用擔心Cookies 的問題。 它通常用於模擬登錄 成功之後再進行下一步的操作。

SLL證書驗證

此外, requests 還提供了證書驗證的功能。 當發送 HTTP 請求的時候,它會檢查 SSL 證書,我們 可以使用 verify 參數控制是否檢查此證書。 其實如果不加 verify 參數的話,默認是 True,會自動驗證。

比如12306的網站,沒有被官方CA,信任。

import requests 
response = requests.get('https://www.12306.cn', verify=False) 
print(response.status_code)

代理設置

爲了防止多次訪問後彈出驗證碼,或者跳轉到登錄認證頁面的情況發生,我們需要設置代理來解決這個問題,這就需要用到 proxies 參數。 可以用這樣的方式設置:

import requests 
proxies = { 'http':'http:10 .10.1.10:3128',
 'http':'http: //10.10.1.10: 1080', }
requests.get('https://www.taobao.com', proxies=proxies) 
#代理無效,請換用自己的代理

requests 還支持 SOCKS 協議的代理。

超時設置

在本機網絡狀況不好或者服務器網絡響應太慢甚至無響應時,我們可能會等待特別久的時間纔可 能收到響應,甚至到最後收不到響應而報錯。 爲了防止服務器不能及時響應,應該設置一個超時時間, 即超過了這個時間還沒有得到響應,那就報錯。 這需要用到 timeout 參數。 這個時間的計算是發送請求到服務器返回響應的時間。 示例如下:

import requests 
r=requests.get('https://www.taobao.com', timeout=1)
print(r.status_code) 

如果想永久等待,可以直接將 timeout 設置爲 None,或者不設置直接留空,因爲默認是 None。

身份驗證

requests 提供了一個簡單的寫法,可以直接傳一個元組,它會默認使用 HTTPBasicAuth 這個類來認證。

import requests 
r = requests.get('https://localhost:5000',
auth=(' username',' password'))

requests 還提供了其他認證方式,如 OAuth 認證。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章