本文講述瞭如何使用代碼模擬HTTP請求來實現數據爬取、點贊、評論回覆等功能。
內容包括:
1.抓包軟件WireShark的簡單使用方法
2.Python庫requests的基本使用
3.一個用代碼回覆博客的例子
一、思路闡述
首先,要模擬HTTP請求,我們要知道被模擬的真實HTTP它到底包含了哪些東西。它的目標URL是什麼,參數是什麼,是不是帶cookie?除此之外還包括了哪些(比如Header)?
爲了獲取這些信息,我們可以使用抓包軟件WireShark來捕獲我們真實提交請求時的數據。
這裏解釋一下爲什麼要用WireShark?(Chrome瀏覽器本身其實也自帶類似功能,有興趣的朋友可以去研究下,但是我還是覺得抓包軟件牛逼)
你可能覺得我要模擬HTTP請求來提交表單,只要看下網頁源代碼中的form表單有哪些字段就可以了。
沒錯,對於一些耿直的安全防護水平低的網站來說,這個方法確實可行。但對於大多數網站是行不通的。
拿某博客網站做例子,看到它源代碼中有個表單域如下:
然而我開着抓包軟件,在真實地完成一次評論操作後,獲取到的POST請求是這樣的:
當然,這可能是因爲它的onsubmit中修改了參數名字。但是就算是你正確填寫了參數名,可能也沒法獲得正確的結果。其中緣由,下文的例子會具體闡述。
通過抓包軟件,我們獲取到了真實的HTTP請求的內容(上面紅字所提到的)。接下來就可以通過代碼來模擬。當然,在模擬時肯定會碰到各種問題,這時候我們要做的就是比較模擬的包(即代碼發送的包。你看,不用抓包軟件你怎麼去獲取代碼發送的請求?)和真實請求的包的內容,來完善代碼(比如添加一些cookie、header等等)。
本文我使用Python來編寫,用了它強大的requests 庫來模擬。
OK,到這裏大致思路已經清楚了:使用抓包軟件獲取真實HTTP請求的內容,並用python代碼來模擬。接下來我們看一下怎麼去使用WireShark獲取我們需要的信息。
二、用抓包軟件抓到我們想要的包
打開WireShark,看到主界面如下:
這時候選擇一個正在使用的網絡連接之後Start(開始抓包),然後出現如下的界面:
在這裏我們看到各種各樣的包,一會兒就把整個屏給刷滿了。別急,我們給它做點過濾。
在Filter輸入欄中輸入過濾規則: ip.dst==116.213.120.41 and http.request.method=="POST"
解釋一下:目標IP地址爲116.... 以及 包內容爲: 以POST方法提交的HTTP請求(關於過濾規則網上查一下比比皆是)
現在清爽多了是不是:
這裏顯示的是我真實登錄慕課網所post的請求的內容。可以看到URL、提交的內容以及一些亂七八糟的信息。
有同學可能不清楚怎麼獲得慕課的IP:打開終端Ping一下慕課的網址就可以了,如下所示:
OK,到這裏想必讀者已經清楚如何利用WireShark來獲取真實請求的包了。有了包的數據,接下來就要用代碼來模擬了!
三、用代碼來爬取數據、提交請求
本來想拿新浪博客做例子的。抓了下包看了內容嚇哭了。也忒多了。還是拿某博客爲例吧。
首先給個鏈接看看回復博客的效果:
http://blog.csdn.net/u012422829/article/details/46491779 這篇博客裏抽風一樣的評論有的是我之前做測試的時候真實提交的,有的是用代碼提交的。
然後直接上代碼:
[python] view plaincopy
import requests
from bs4 import BeautifulSoup
# coding="utf-8"
url = 'https://passport.csdn.net/account/login'
sess = requests.session()
print sess
html1 = sess.get(url).text
soup1 = BeautifulSoup(html1)
p1 = soup1.select("[name=lt]")[0]["value"]
p2 = soup1.select("[name=execution]")[0]["value"]
data = {
"lt": p1,
"execution": p2,
"_eventId": "submit",
"username": "your name",
"password": "your psw"
}
r = sess.post(url, data)
print r.text
#below is the code how to reply your blog
commentUrl="http://blog.csdn.net/u012422829/comment/submit?id=46491779"
html2 = sess.get(url).text
commentdata = {
"commentid":'',
"content":"I am excited that I can reply my blog by my python code!",
"replyId":'',
}
headers = {'content-type': 'application/x-www-form-urlencoded',
'User-Agent': 'Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/41.0.2272.118 Safari/537.36'}
sess.headers.update(headers)
r2 = sess.post(commentUrl, commentdata)
print r2.text
#below is the code how to crawl the info you want
msg = BeautifulSoup(sess.get('http://msg.csdn.net/').text)
for li in msg.select(".user_name"):
print li.text
#below is the code how to up your blog in the home page of CSDN
url3='http://blog.csdn.net/common/digg.html?id=46541445&blog=1248879&user=u012422829&action=up'
msg = BeautifulSoup(sess.get(url3).text)
print msg
關於登錄代碼的解釋:
使用了Python強大的requests庫來完成。有關這個庫用法的介紹網上很多,讀者可以自己去找找。
我先用抓包軟件獲取到了包的內容,確認了發送的表單內容之後,發現有3個隱藏域,於是直接從網站返回消息中獲取。
一開始沒有添加Header,發送的請求被拒絕處理(403Forbidden)。觀察了兩個包的內容,猜想可能是Header中User-Agent爲Python腳本的原因,於是順手把真實請求的Header複製下來,替換了User-Agent之後,成功登錄。
看看爬下來的msg的輸出:
可以看到我把所有消息的來源者的name爬下來了。
============寫在後面====================================
爬其他網站數據也大同小異,不過很多都有反爬蟲機制。比如剛剛試驗知乎登錄,一開始還可以,後來就被驗證碼弄的405ERR了,憂傷。
任何問題歡迎留言!