python网络爬虫三
使用表单和post请求
我们知道很多内容在我们进行登陆之前是查看不到的,所以如果我们想要爬取登陆之后网站上的内容,我们就需要使用表单和post请求
在web中,所有的表单都对应于标签form中包含的HTML的内容
许多标签代表表单字段本身,其中大多数是通过input标签提供,type属性指定了它应代表的字段类型
当我们希望向网络提交一些信息来登陆或者做其他操作,我们可以使用POST请求
状态码
这里我们简单的区分一下不同的状态码给我们的信息:
- 1XX : 信息状态码,表示已收到并理解请求,但服务器指示客户端应该等待额外的响应
- 2XX : 成功状态码,表示已收到并理解和成功处理了请求。200表示🆗,204表示NO CONTENT ,206表示返回服务器仅提供部分资源
- 3XX : 重定向状态码,表示客户端必须采取其他操作来完成请求,通常是通过执行可以找到实际内容的新请求
- 4XX : 客户端错误状态码。最最最常见的就是404,表示无法找到所请求的资源;410表示请求的资源可用一次;400表示HTTP请求格式不正确;403表示请求有效但是用户没有正确的凭据来访问此资源
- 5XX : 服务器错误状态码,表示请求有效,但服务器无法处理
header构造
我们一直以默认的header来发送请求,但是有的网站为了反爬虫,会通过一个简单的检查来阻止特定用户来访问他们的内容,比如对header的检查
因为一般的请求header的构造是这样的:
user-agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.105 Safari/537.36
accept: application/json, text/javascript, */*; q=0.01
accept-encoding: gzip, deflate, br
accept-language: zh-CN,zh;q=0.9
而我们默认使用的requests构造的头是这样的:
user-agent:python-requests/2.18.4
……
通过对header的检测就可以将一些简单的爬虫隔绝在网页之外
但是道高一尺魔高一丈,我们爬虫也可以伪装成浏览器的样子进行模拟浏览,我们只需要将头改造一下即可
实战例子:模拟登录开心网
import requests
from bs4 import BeautifulSoup
import re
"""该程序用于模拟登录开心网"""
url = 'http://login.kaixin001.com/'
params = {
'email': '******@163.com',
'password': '******'
}
headers = {'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 '
'(KHTML, like Gecko) Chrome/70.0.3538.102 Safari/537.36 Edge/18.18362'}
# 这里构造了一个简单的header用于通过简单的检查
def get_http(url, params, headers):
html = requests.post(url, data=params, headers=headers)
# 这里使用post方法来提交一个表单
print(html.status_code) # 返回状态码
bs = BeautifulSoup(html.text, 'html.parser')
for i in bs.find_all(re.compile('^s')):
print(i)
get_http(url, params, headers)
输出结果:
200 # 说明表单提交成功
<script type="text/javascript">var g_st_time=new Date().getTime();</script>
<script src="http://s.kaixin001.com.cn/js/_combo/base*Base,base*Array,base*Class,base*Function,base*Object,base*String,base*Browser,base*Pubsub,base*Module,base*CustEvent,base*Env,base*Util-00209b36e.js"></script>
<script type="text/javascript">var g_st_time=new Date().getTime();</script>
<script src="http://s.kaixin001.com.cn/js/_combo/prototype-1.6.1,jquery_min,kaixin-0037cc5f8.js"></script>
<script src="http://s.kaixin001.com.cn/js/_combo/common,lazyload,s,head,head_rgroup,webeditor*editor,webeditor*lite,comment_base,Kx_Utils,Kx_HtmlTpl,apps*common*FaceResource,Kx_Easy_Captcha,apps*common*UserCard,apps*common*AppCard-048651b03.js"></script>
<script src="http://s.kaixin001.com.cn/js/_combo/comment-0064c7582.js"></script>
<script src="http://s.kaixin001.com.cn/js/_combo/rshare_dlg,dialog,giftcommon,music-00781b4ef.js"></script>
<script src="http://s.kaixin001.com.cn/js/_combo/seclogin,apps*common*AQqLogin,apps*common*AOauthLogin-004835e68.js"></script>
<script type="text/javascript">KxLazyLoad(["js/comment.js", "js/dialog.js"]);</script>
<script language="javascript">
# 下面的省略
但是这里有一个小缺点就是构造的表单的键对,需要我们检查网页的元素通过input里面的type来获取
当然我们也可以使用BS来爬取这个信息,当然还是得检查元素。。。