Requests 基础
Requests 入门
问题:为什么要学习 requests,而不是 urllib?
Requests 的底层实现就是 urlib
Requests 在 python2 和 python3 中通用,方法完全一样
Requests 简单易用
Requests 能够自动帮助我们解压(gzip 压缩的等)网页内容
安装模块
使用 pip install
pip --version 查看当前 pip 是 Python 2 的,还是 Python 3 的
注:直接输入工具名回车,一般都是帮助信息
下载压缩包,解压,使用 Python 运行 setup.py
HTTP 请求方法:
get、post、put、delete、option
1 | response = requests.get('https://www.baidu.com') |
返回一个 response 对象,通过 response 对象的方法,我们可以处理响应内容。
属性与方法
区分属性与方法:
属性是名词,是对象固有的属性
方法是动词,是对象可以做的事情
response.text
类型:str
解码类型:根据 HTTP 头部对响应的编码作出有根据的推测,推测的文本编码
如何修改编码方式:response.encoding=”gbk”
Requests 会自动对响应正文进行解码:如果 Response.encoding 为空,那么 requests 根据 header 来确定响应的编码方式,然后进行解码。如果你可以确定响应的编码方式,也可以先对 Response.encoding 进行设置,然后再通过 Response.text 获取响应正文。
response.content
类型:bytes
解码类型:没有指定
如何修改编码方式:response.content.deocde(“utf8")
如果你想取文本,可以通过 r.text。 如果想取图片,文件,则可以通过 r.content。 ( resp.json() 返回的是 json 格式数据)
当然,由于二进制是最原始的数据,我们方便对他进行任意操作,于是常用且推荐使用: response.content.decode()
requests 中解决编解码问题:
- response.content.decode() 默认使用 utf8
- response.content.decode('gbk')
- response.text
response.status_code 状态码
当状态码为 200 时,只能说请求某个 URL 成功了,但是不一定是我们传入的参数 URL 地址。
比如:我们现在请求一个登陆之后才能访问的页面,服务器会将我们重定向到登录页面,而我们成功访问登录页面,于是返回 200.
区分 4xx or 5xx 与 200
直接使用
response.status_code
或者assert resposne.status_code == 200
(需要 try except)response.raise_for_status()
raise an exception for error codes (4xx or 5xx),
很多时候我们需要请求很多网页,那么我们需要定义一个方法,专门发送请求获得相应响应,并进行异常处理。然后再在别的方法中进行处理。
response.header 响应头
响应头,一般只关注 Set-Cookie 字段
当我们关注网站如何设置 cookie 的时候,不应该只管响应头的 Set-Cookie 字段,因为也可以通过 JS 设置 cookie 到本地,所以也要关注一下 JS。
response.request 中有着关于请求报文的信息,可以通过对应的方法获得。
response.request.header 请求头、response.request.method 请求方法
注意:
- 如果遇到重定向,请求和响应的 URL 就会不一样。
- requests 模块默认的 User-Agent 为 python-requests/2.22.0(版本号可略有不同),所以我们要使用它时,要单独设置 UA,否则会被立即识别为爬虫,然后返回一个与浏览器的页面不一定相同的页面。
发送带 header 请求
我们只需要传递一个字典形式的 header 参数即可,注意:header 需要是键值对的形式,不要只写值,不写名
1 | headers = {"User-Agent":"Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/77.0.3865.75 Safari/537.36"} |
此处,我们发送带 header 请求是为了模拟浏览器,防止被识别为爬虫。如果有一天我们单单带上 UA,还是会被识别为爬虫,那么我们就要考虑带上 headers 中别的字段值了。如果还不行,我们可以考虑 带上 cookie
发送带参数的请求
比如以下 URL 中 ?后面便是参数的键值对
1 | https://www.google.com/search?q=python |
参数形式:字典
注意:有的参数对请求内容来说是没有用的,我们要测试出那些重要的参数。
两种方式:
requests 提供的方式
比如:https://xxx.com/search.php?key=Python&time=2018
url = 'https://xxx.com/search.php' # 注意:带不带问号均可,requests 会判断有无问号,然后帮我们调整,使其有一个问号。
keyword={‘key’:'Python', 'time':2018}
requests.get(url, params=keyword)
拼接字符串
3.6 及以上建议使用:f -string,采用直接在字符串中内嵌变量的方式进行字符串格式化操作
1
2
3
4param1 = 'Python'
param2 = 2018
url =f"https://xxx.com/search.php?key={param1}&time={param2}"
requests.get(url)当然,老式的方法我们也要能看懂:
1
2url ="https://xxx.com/search.php?key={}&time={}".format(param1,param2)
url ="https://xxx.com/search.php?key=%s&time=%d" % (param1, param2)注意:编码问题
如果使用 w 模式打开文件写入报错,那在打开文件时,添加 encoding 字段
使用 ‘wb’ 模式打开文件写入没有问题
1
2
3
4f = open('liyiba-'+str(i+1)+'.html','w',encoding='utf-8')
f.write(response.content.decode())
或
with open(file_path, 'w', encoding='utf-8') as f:类的每个方法的第一个参数为指向实例的引用。在类的方法中使用类的成员或方法也要在前面加上 self.
Post 请求
哪些地方我们会用到 POST 请求:
- 登录注册(POST 比 GET 更安全)
- 需要传输大文本内容的时候(POST 请求对数据长度没有要求) 所以同样的,我们的爬虫也需要在这两个地方去模拟浏览器发送 post 请求
发送 POST 请求用法:
1 | response=requests.post("http://www.baidu.com/", data=data, headers=headers) |