爬蟲(5)一文搞懂cookie原理和使用(客官裏面請,下飯文章喫飽再走)

什麼是cookie:

在網站中,http請求是無狀態的。也就是說即使第一次和服務器連接後並且登錄成功後,第二次請求服務器依然不能知道當前請求是哪個用戶。(看過’夏洛特煩惱’的朋友應該能知道在夏洛的夢境中的那次聚會,老師不認識同學們,但是當學生提到我就是送您收音機那個的時候,老師就明白這個學生是誰了,而這個cookie就好似是學生給老師說的送過的禮物在)cookie的出現就是爲了解決這個問題,第一次登錄後服務器近回一些數據(cookie)給瀏覽器,然後瀏覽器保存在本地,當該用戶發送第二次請求的時候,就會自動的把上次請求存儲的cookie數據攜帶給服務器,服務器通過瀏覽器攜帶的數據就能判斷當前用戶是哪個了。cookle 存儲的數據量有限,不同的瀏覽器有不同的存儲大小,但一般不超過4KB。因此快用cookde只能存儲一些小量的數據。

cookie的格式:

Set-Cookie: NAME-VALUE: Expires/Max-age-DATE: Path-PATH: Domain-DOMAIN_NAME : SECURE

參數意義:

  • NAME: cookie的名字。
  • VALUE: cookie的值。
  • Expires: cookie的過期時間。
  • Path: cookie作用的站徑.
  • Domain: cookie作用的域名。
  • SECURE: 是否只在https協許下起作用。

使用cookielib庫和HTTPCookieProcessor模擬登錄:

Cookie是指網站服務器爲了精別用戶身份和進行Session跟蹤。而儲存在用戶時覽器上的文本文件,Cookie可以保持登錄信息到用戶下次與服務器的會話。
這裏以人人用爲例,人人網中,要訪問某個人的主頁。必須先登錄才能訪問。登錄說白了就是要有cookie信息。那麼如果我們使用代碼的方式訪問,就必須要有正確的cookie信息才能抗問。解決方案有兩種。第一種是使用瀏覽器訪問,然後將cookie信息複製到headers下.
這裏先示例不使用cookie時的訪問主頁:

  • 因爲這裏沒有使用cookie信息,因此人人網會拒絕我們訪問別人的首頁而轉到登錄頁面,而我們實際爬取到的也不是主頁的信息,而是登錄的頁面信息.

1.cookie複製的方式爬取信息

#encoding: utf-8
from urllib import request

#人人網大鵬url=http://www.renren.com/880151247/profile
#人人網登陸url = http://www.renren.com/PLogin.do
#不使用cookie登陸
dapeng_url ='http://www.renren.com/880151247/profile'
headers= {
    'User-Agent' : 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.132 Safari/537.36'

}
req = request.Request(url=dapeng_url,headers=headers)
resp = request.urlopen(req)
#爲了觀察的結果會更直觀,我們把這個讀出來的頁面寫入一個頁面中打開,看一看爬出來的是不是大鵬的頁面
#print(resp.read().decode('utf-8'))
with open('renrendapeng.html','w')as fp:
    """注意write函數只能傳入一個str數據類型
    resp.read()讀出來的是一個bytes類型的數據
    bytes -> decode  ->str
    str ->encode  ->bytes
    """
    fp.write(resp.read().decode('utf-8'))

在這裏插入圖片描述
爬取到的不是大鵬的主頁而是登錄的頁面,現在我們使用cookie的第一種使用方式(瀏覽器複製方式)來添加了cookie之後在看一下爬取到的數據.

#encoding: utf-8
#使用cookie模擬登錄
#人人網大鵬url=http://www.renren.com/880151247/profile
#人人網登陸url = http://www.renren.com/PLogin.do
from urllib import request
dapeng_url ='http://www.renren.com/880151247/profile'
headers= {
    'User-Agent' : 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.132 Safari/537.36',
    'Cookie': 'anonymid=k8wlyoy1-ny0une; depovince=GW; _r01_=1; JSESSIONID=abcE68Al2HqR_-7Do3Sfx; ick_login=c3dc2658-5708-41b8-9d34-bdf50537cd5c; taihe_bi_sdk_uid=79da7caa8254d05786dfbb1e1775e688; taihe_bi_sdk_session=019401f871b1b3589abe2676f13b7211; loginfrom=null; XNESSESSIONID=dec74922ed95; wp_fold=0; t=36b16d19d7f0427b2f537aa7fec812bb4; societyguester=36b16d19d7f0427b2f537aa7fec812bb4; id=974213094; xnsid=93156620; jebecookies=246bde88-55b9-414e-84fe-91dfcac13f4f|||||; ver=7.0; l4pager=0',

}
req = request.Request(url=dapeng_url,headers=headers)
resp = request.urlopen(req)
#爲了觀察的結果會更直觀,我們把這個讀出來的頁面寫入一個頁面中打開,看一看爬出來的是不是大鵬的頁面
#print(resp.read().decode('utf-8'))
with open('renrendapeng2.html','w')as fp:
    """注意write函數只能傳入一個str數據類型
    resp.read()讀出來的是一個bytes類型的數據
    bytes -> decode  ->str
    str ->encode  ->bytes
    """
    fp.write(resp.read().decode('utf-8'))

在這裏插入圖片描述
可以看到,這裏已經成功的爬取到了大鵬的主頁的信息
特別注意的一點是:

  • cookie信息是會過期的,因此這也是採用了第一種方式的弊端所在,你今天寫的代碼是能爬取到信息的,但是當cookie過期後,即使添加了cookie信息也是爬取不到主頁的信息的.

2.實現cookie的自動化獲取,並爬取信息

但是每次在訪問需要cookie的頁面都要從瀏覽器中複製cookie比較麻煩,在Python處理cookie,一般是通過http.cookiejar模塊和urllib模塊的HTTPCookieProcessor處理類一起使用.

  • http.cookiejar模塊主要作用是提供存儲cookie對象.
  • HTTPCookieProcessor處理器主要作用是處理這些cookie對象,並構建handler對象.

http.cookiejar模塊:
該模塊主要的類有CookieJar. FlleCookieJar. MozillaCookieJC LWPCookieJar.這四個類的作用分別如下:

  1. CookieJar:管理HTTP cookie值、存儲HTTP請求生成的cookie.向傳出的HTTP請求添加cookie的對象。整個cookie都存儲在內存中,對CookieJar實例進行垃圾回收後cookie也將丟失。
  2. FileCookieJar: (flename,delayload=None polcy=None):從CookieJar派生而來,用來創建FleCookie.Jar實例,檢索cookie信息並將cookie存儲到文件中。filename是存儲cookie的文件名。delayload爲True時支持延遲訪問訪問文件,即只有在需要時纔讀取文件或在文件中存儲數據。
  3. MozillaCookieJar :(flename delayload=None policy=None),FleCookieJar派生而來,創建與Mozilla瀏覽器cookies txt兼容的FileCookieJar實例。
  4. LWPCookieJar: (flename,delayloadeNonepolcyaNone):從FileCookieJar派生 而來,創建與libwww-per標準的Set-Cookie3文件格式兼容的FileCookieJa實例。
    利用http.cookdejarrequest.HTTPCookieProcessor登錄人人網。相關示例代碼如下:
#encoding: utf-8
#使用cookie模擬登錄
#人人網大鵬url=http://www.renren.com/880151247/profile
#人人網登陸url = http://www.renren.com/PLogin.do
from urllib import request
from urllib import parse
from http.cookiejar import CookieJar

#1.登錄
#1.1創建一個cookiejar對象
cookiejar = CookieJar()
#1.2使用cookiejar創建一個HTTPCookieProcese對象
handler = request.HTTPCookieProcessor(cookiejar)
#1.3使用上一步創建的handler創建一個opener
opener = request.build_opener(handler)
#1.4使用opener發送登錄的請求(人人網的郵箱和密碼)
headers ={
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.132 Safari/537.36',

}
data ={
    'email' : '[email protected]',
    'password':'pythontest1234'

}
login_url = 'http://www.renren.com/PLogin.do'
req = request.Request(login_url,data=parse.urlencode(data).encode('utf-8'),headers=headers)
opener.open(req)


#僅僅是爲了登錄,所以響應什麼並不重要,我們這裏不接收它

#2.訪問個人主頁
dapeng_url = 'http://www.renren.com/880151247/profile'
'''獲取我們要訪問的主頁時,我們直接使用上面創建好的opener,因爲它已經包含了cookiejar和handler的信息'''
req = request.Request(dapeng_url,headers= headers)
resp =opener.open(req)
with open ('renrendapeng3.html','w') as fp:
    fp.write(resp.read().decode('utf-8'))

代碼重構後:

#encoding: utf-8

'''
實現對cookie_test3代碼的重構,讓可讀性提高
'''
#encoding: utf-8
#使用cookie模擬登錄
#人人網大鵬url=http://www.renren.com/880151247/profile
#人人網登陸url = http://www.renren.com/PLogin.do
from urllib import request
from urllib import parse
from http.cookiejar import CookieJar

headers = {
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.132 Safari/537.36',

}

def get_opener():
    cookiejar = CookieJar()
    handler = request.HTTPCookieProcessor(cookiejar)
    opener = request.build_opener(handler)
    return opener

#1.4使用opener發送登錄的請求(人人網的郵箱和密碼)
def login_renren(opener):
    data ={
    'email' : '[email protected]',
    'password':'pythontest1234'

    }
    login_url = 'http://www.renren.com/PLogin.do'
    req = request.Request(login_url,data=parse.urlencode(data).encode('utf-8'),headers=headers)
    opener.open(req)


#僅僅是爲了登錄,所以響應什麼並不重要,我們這裏不接收它

#2.訪問個人主頁
def visit_profile(opener):
    dapeng_url = 'http://www.renren.com/880151247/profile'
    '''獲取我們要訪問的主頁時,我們直接使用上面創建好的opener,因爲它已經包含了cookiejar和handler的信息'''
    req = request.Request(dapeng_url,headers= headers)
    resp =opener.open(req)
    with open ('renrendapeng4.html','w') as fp:
        fp.write(resp.read().decode('utf-8'))
if __name__ == '__main__':
    opener = get_opener()
    login_renren(opener)
    visit_profile(opener)


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