爬虫概念
- 爬虫是模拟浏览器发送请求,获取响应
爬虫的流程
- url—> 发送请求,获取响应,—>提取数据—>保存
- 发送请求,获取响应—>提取url
页面上的数据在哪里
- 当前的url地址对应的响应中
- 其他的url地址对应的响应中
- 比如ajax请求中
- js生成的
- 部分数据在响应中
- 全部通过js生成
requests中解决编码的方法
- response.content.decode()
- response.content.decode(‘gbk’)
- response.text
- response.content 与response.text数据类型不一样
- response.content返回的是一个bytes型的二进制文件
- response.text返回的是一个unicode型的文本数据,默认“iso-8859-1
- response.content 与response.text数据类型不一样
如何判断是否请求成功
- 通过判断response.status_code的值是否为200
assert response.status_code == 200
断言失败会抛出异常AssertionError,
url编码
https://www.baidu.com/s?wd=%E4%BC%A0%E6%99%BA%E6%92%AD%E5%AE%A2
字符串格式化的另一种方式
"你好,{}同学.format(小明)
使用代理ip
-
准备一堆的ip地址,组成ip池,随机选择一个ip来时用
-
如何随机选择代理ip,让使用次数较少的ip地址有更大的可能性被用到
- {“ip”:ip,“times”:0}
- [{},{},{},{},{}],对这个ip的列表进行排序,按照使用次数进行排序
- 选择使用次数较少的10个ip,从中随机选择一个
-
检查ip的可用性
- 可以使用requests添加超时参数,判断ip地址的质量
- 在线代理ip质量检测的网站
携带cookie请求
- 携带一堆cookie进行请求,把cookie组成cookie池
使用requests提供的session类来请求登陆之后的网站的思路
- 实例化session
- 先使用session发送请求,登录对网站,把cookie保存在session中
- 再使用session请求登陆之后才能访问的网站,session能够自动的携带登录成功时保存在其中的cookie,进行请求
不发送post请求,使用cookie获取登录后的页面
- cookie过期时间很长的网站
- 在cookie过期之前能够拿到所有的数据,比较麻烦
- 配合其他程序一起使用,其他程序专门获取cookie,当前程序专门请求页面
字典推导式,列表推到是
cookies = {i.split("=")[0]:i.split("=")[1] for i in cookies.split("; ")}
[self.url_temp.format(i * 50) for i in range(1000)]
获取登录后的页面的三种方式
- 实例化session,使用session发送post请求,在使用他获取登陆后的页面
- headers中添加cookie键,值为cookie字符串
- 在请求方法中添加cookies参数,接收字典形式的cookie。字典形式的cookie中的键是cookie的name对应的值,值是cookie的value对应的值
寻找登录的post地址
-
在form表单中寻找action对应的url地址
- post的数据是input标签中name的值作为键,真正的用户名密码作为值的字典,post的url地址就是action对应的url地址
-
抓包,寻找登录的url地址
- 勾选perserve log按钮,防止页面跳转找不到url
- 寻找post数据,确定参数
- 参数不会变,直接用,比如密码不是动态加密的时候
- 参数会变
- 参数在当前的响应中
- 通过js生成
定位想要的js
- 选择会触发js时间的按钮,点击event listener,找到js的位置
- 通过chrome中的search all file来搜索url中关键字
- 添加断点的方式来查看js的操作,通过python来进行同样的操作
安装第三方模块
- pip install retrying
- 下载源码解码,进入解压后的目录,
python setup.py install
***.whl
安装方法pip install ***.whl
json使用注意点
- json中的字符串都是双引号引起来的
- 如果不是双引号
- eval:能实现简单的字符串和python类型的转化
- replace:把单引号替换为双引号
- 如果不是双引号
- 往一个文件中写入多个json串,不再是一个json串,不能直接读取
- 一行写一个json串,按照行来读取
正则使用的注意点
-
re.findall("a(.*?)b","str")
,能够返回括号中的内容,括号前后的内容起到定位和过滤的效果 -
原始字符串r,待匹配字符串中有反斜杠的时候,使用r能够忽视反斜杠带来的转义的效果
-
点号默认情况匹配不到
\n
-
\s
能够匹配空白字符,不仅仅包含空格,还有\t|\r\n
xpath学习重点
-
使用xpath helper或者是chrome中的copy xpath都是从element中提取的数据,但是爬虫获取的是url对应的响应,往往和elements不一样
-
获取文本
a/text()
获取a下的文本a//text()
获取a下的所有标签的文本//a[text()='下一页']
选择文本为下一页三个字的a标签
-
@符号
a/@href
//ul[@id="detail-list"]
-
//
- 在xpath最前面表示从当前html中任意位置开始选择
li//a
表示的是li下任何一个标签
lxml使用注意点
-
lxml能够修正HTML代码,但是可能会改错了
- 使用etree.tostring观察修改之后的html的样子,根据修改之后的html字符串写xpath
-
lxml 能够接受bytes和str的字符串
-
提取页面数据的思路
- 先分组,渠道一个包含分组标签的列表
- 遍历,取其中每一组进行数据的提取,不会造成数据的对应错乱