爬虫 0030~ requests利刃出鞘

1-1 简介

requests第三方封装的模块,通过简化请求和响应数据的处理,简化繁琐的开发步骤和处理逻辑、统一不同请求的编码风格以及高效的数据处理特性等而风靡于爬虫市场。

参考官方文档:

1-2 下载安装

Python2/python3命令行安装

使用pip(python install package)命令安装

#  pip install requests

or

使用easy_install命令安装

# easy_install requests

1-3 程序中的引入使用

安装好request模块之后,在程序中就可以通过import引入并且使用了

接下来,通过一个简单的案例了解requests模块的使用,let上干货

# -*- coding:utf-8 -*-
# 引入requests模块
import requests

# 发送请求,得到服务器返回的响应对象,通过encoding设置响应中数据的编码
response = requests.get("http://www.sojson.com/open/api/weather/json.shtml?city=%E9%83%91%E5%B7%9E")
response.encoding="utf-8"

# 通过text打印响应中的文本数据
print(response.text)

得到结果如下:

{"message":"Success !","status":200,"city":"郑州","count":1,"data":{"shidu":"50%","pm25":61.0,"pm10":131.0,"quality":"良","wendu":"32","ganmao":"极少数敏感人群应减少户外活动","yesterday":{"date":"09日星期三","sunrise":"05:40","high":"高温 36.0℃","low":"低温 25.0℃","sunset":"19:21","aqi":70.0,"fx":"西风","fl":"<3级","type":"晴","notice":"lovely sunshine,尽情享受阳光的温暖吧"},"forecast":[{"date":"10日星期四","sunrise":"05:41","high":"高温 37.0℃","low":"低温 25.0℃","sunset":"19:20","aqi":95.0,"fx":"西风","fl":"<3级","type":"晴","notice":"晴空万里,去沐浴阳光吧"},{"date":"11日星期五","sunrise":"05:42","high":"高温 35.0℃","low":"低温 25.0℃","sunset":"19:19","aqi":75.0,"fx":"南风","fl":"3-4级","type":"阴","notice":"灰蒙蒙的天空就像模糊了的眼睛"},{"date":"12日星期六","sunrise":"05:42","high":"高温 31.0℃","low":"低温 23.0℃","sunset":"19:18","aqi":54.0,"fx":"东风","fl":"3-4级","type":"小雨","notice":"雾蒙蒙的雨天,最喜欢一个人听音乐"},{"date":"13日星期日","sunrise":"05:43","high":"高温 27.0℃","low":"低温 23.0℃","sunset":"19:17","aqi":55.0,"fx":"北风","fl":"<3级","type":"小雨","notice":"下雨了不要紧,撑伞挡挡就行"},{"date":"14日星期一","sunrise":"05:44","high":"高温 33.0℃","low":"低温 25.0℃","sunset":"19:16","aqi":62.0,"fx":"西风","fl":"<3级","type":"多云","notice":"悠悠的云里有淡淡的诗"}]}}

1-4 基本请求方式<所有的故事都发生在那年那月的懵懂>

常规情况下,所有类似给服务器发送的请求方式,都是参考W3C提供的标准进行制定的。

requests为爬虫开发者们提供了8种基本的请求方式,分别如下:

req = requests.request(method,url, **kw)
req = requests.post(url, **kw)
req = requests.get(url, **kw)
req = requests.delete(url, **kw)
req = requests.put(url, **kw)
req = requests.head(url, **kw)
req = requests.options(url, **kw)
req = requests.patch(url, **kw)

注意:由于在web开发过程中,大家发现对于服务器数据的处理方式没有一开始制定标准时设计的那么复杂,所以一般情况下都简化成了get/post两种常见的请求方式

以上请求方式中,request()方式是底层的请求方式,分别由get()/post()等方式进行了高级的实现,方便开发人员去更加快捷的使用了。 PS:如此懒的开发人员啊...

1-5 一个基本请求的使用方式<有了酒,就有了故事>

由于requests库的封装的使用方式非常统一,所以通过一种方式的请求,基本就能了解和学习到所有的请求方式的处理过程了。

这里主要通过post()方式的请求,来了解在发送请求过程中所有的事故处理方式,分别讲解如下几种情况:

  • 基本请求:空手套白狼,简单的一个请求就得到想到的数据
  • 附带参数的请求:去看丈母娘总得带点礼物,她老人家开心~才会把你要的姑娘给你啊
  • 附带JSON参数的请求:老岳父看中的更多的是人品,请求需要的可是JSON参数了
  • 返回的结果数据编码总是那么不可捉摸
  • 上传文件的请求:要结婚总是大件小件的搬东西,习惯就好了
  • 总有一些时刻是美好的~cookie准备好了吗
  • 千万不要持久战~那个会让你过期的timeout超时配置
  • 老人家总是会记性不大好,所以我们要保持好自己的会话状态Session
  • 有了证书,就有了阅历,关于SSL证书那点事儿
  • 你的人生得到了最终的成功,代理们开始为你工作了

1.5.1 基本请求方式

基本请求方式,通过request直接调用对应的函数/方法即可完成,多么的优雅

# 引入需要的模块
import requests

# 发送请求吧
res = requests.post(“http://www.baidu.com”)

# 通过text属性得到响应中的数据
print (res.text)

1.5.2 附带普通参数的请求

参数包含在一个字典对象中,将字典对象交给requests的函数即可

友情提示:在使用的时候最好看一下源码哦,有惊喜的

# 引入需要的模块
import requests

# 封装参数的字典
data = {“city”:”郑州”}
# get方式发送请求,包含参数
res = requests.get(http://..../json.html, params = data)
# post方式发送请求,包含参数
res = requests.post(“http://..../json.html, data = data)
.. .. ..

1.5.3 传递JSON参数

在请求的过程中,有些URL接口需要的参数数据并不是零散的数据,而是需要封装在一起的JSON数据,此时,可以通过json.dumps()函数将一个字典数据转换成json数据进行传递~就是这么easy

此时~requests符合人体工程学的操作就出现了,如果你提供的是字典数据,json模块提供了dumps()函数转换一下就OK了

# 引入需要的模块
import requests
imoprt json

# 封装参数的字典
data = {“city”:”郑州”}
# 转换参数
json_data = json.dumps(data)
# post方式发送请求,包含参数
res = requests.post(“http://..../json.html, data = json_data)
.. .. ..

当然,如果你提供的就是JSON字符串的话,那就easy了

# 引入需要的模块
import requests

# 封装参数的json字符串
json_data = ‘{“city”:”郑州”}’
# post方式发送请求,包含参数
res = requests.post(“http://..../json.html, json = json_data)
.. .. ..

1.5.4 返回的数据和它编码操作

返回的数据,可以根据数据的编码类型区分为二进制数据和文本数据,两种不同的数据通过两个不同的属性进行获取

  • response.content:获取响应中包含的二进制数据
  • response.text:获取响应中包含的文本数据

返回的数据,会根据响应的数据进行自动的编码,数据编码最常见的会是ISO-8859-1也就是西欧编码,容易看到乱码的情况,此时可以通过返回的响应对象response的一个属性encoding进行编码的获取和指定

  • response.encoding = “编码”
# 引入需要的模块
import requests

response = requests.post(“http://www.baidu.com”)
print(response.encoding)
print(response.text)
ISO-8859-1
å
³äº�ç�
response = requests.post(“http://www.baidu.com”)
response.encoding=”UTF-8”
print(response.text)
百度一下

1.5.5 文件上传操作

requests对象支持文件的数据流式处理,不需要将整个文件都加载到内存中,而是读取一部分传递一部分,将文件指定给requests请求的file参数即可

注意:文件的上传操作只能通过post()请求方式执行操作

传统方式,加载整个文件,然后进行上传操作

# 引入需要的模块
import requests

# 打开文件
f = open(“d:/test.txt”, “r”)
# 包装文件参数
file = {“file”:f}
# 传递文件
response = requests.post(http://httpbin.org/post, files=file)
# 打印结果
print (response)    

流式数据传递方式

# 引入需要的模块
import requests

# 打开文件
with open(“d:/test.txt”, “r”) as f:
    response = requests.post(http://httpbin.org/post, data=f) 

1.5.6 cookie操作

cookie操作是web开发过程中经常用到的一个功能,在爬虫操作过程中也是非常实用的个功能,可以用于进行诸如登陆状态记录、浏览记录等很多非常实用的功能

在requests模块中对cookie的操作进行了封装,可以直接通过响应对象的cookie属性进行操作

import requests

response = request(“http://www.badiu.com”)
print(response.cookies)# 获取整个cookie
print(r.cookies[“key”])# 根据key获取指定的值

1.5.7 请求超时设置

如果要求对于数据操作性能有要求的话,经常会针对请求比较慢的连接进行过滤处理,可以通过传递timeout参数数据进行超时时间的设置,超过超时时间的连接自动抛出异常

import requests

response = requests.get(“http://github.com”, timeout=0.1)
异常信息:requests.exceptions.ConnectTimeout

1.5.8 让多个请求包含在一个会话中

一般情况下,爬虫操作获取目标数据都是短连接,也就是获取数据时连接服务器,每次发起请求就是一个连接,获取到服务器的响应数据后连接自动断开,再次发起请求时又是一个新的请求对象了~ 备注:类似打开浏览器访问了一个网页,然后关闭了浏览器,再次打开浏览器访问网页,两次访问请求就不是同一个会话了

使用测试服务器进行测试,测试服务器返回的响应对象中包含了cookie数据

import requests

response = 
requests.get(“http://httpbin.org/cookies/set/key/value”)
print(response.cookies)

response = 
requests.get(“http://httpbin.org/cookies”)
print(response.cookies)
{
  "cookies": {
    "key": "value"
  }
}

{
  "cookies": {}
}

从上面的代码中可以看到,两次请求不是同一个会话进行操作的了。如果要进行多个请求包含在同一个会话中的处理的话,通过requests模块的会话对象Session()构建一个会话请求进行操作即可

import requests

req = requests.Session()

response = 
req.get(“http://httpbin.org/cookies/set/key/value”)
print(response.cookies)

response = 
req.get(“http://httpbin.org/cookies”)
print(response.cookies)
{
  "cookies": {
    "key": "value"
  }
}
{
  "cookies": {
    "key": "value"
  }
}

1.5.9 SSL证书设置

SSL证书设置,可以让爬虫程序类似浏览器一样验证https协议访问的网站,为https请求验证SSL证书。

测试一下:(某12306网站的数字证书可是无效的哦)如下图

爬虫程序爬取该网页会出现什么问题呢?

import requests

response = requests.get(“https://kyfw.12306.cn/otn”)
print(response.text)

此时,关闭掉爬虫的对HTTPS的SSL证书验证,通过设置请求参数verify=False关闭该验证

import requests

response = requests.get(“https://kyfw.12306.cn/otn”,verify=False)
print(response.text)

我们可以看到,无效SSL证书的数据也被正常的爬取下来了。

1.5.10 代理设置

和之前讲解的urllib2一样,爬虫操作过程中,代理的设置是不可避免的一种技术手段

在requests模块中,当然也是充分考虑了代理操作的可行性

通过将代理服务器端口配置在字典中,然后通过proxies参数进行设置即可

import requests

proxies = {
    "https":"122.72.32.75:80"
}
response = requests.get("http://www.baidu.com", proxies=proxies)

print (response.text)

未完待续!

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏coding for love

进程与线程,单核与多核1. 简介2. 程序3. 进程4. 线程5. 多进程与多线程的选择6. 小结参考

用户打开浏览器,其实就是打开了浏览器应用程序。那么什么是程序呢?我们常说浏览器是多线程的,JS 是单线程的,那么什么是线程呢?说到线程,和我们常说的进程有什么关...

2903
来自专栏黑白安全

PHP安全编码规范之安全配置篇

因为配置不当引发的安全问题是屡见不鲜的,通过一系列的安全配置,可以很好的解决一些安全隐患,从而为系统增加安全系数。但是在开发过程中,因为需求的改变和编程的习惯可...

2822
来自专栏ionic3+

【开发指南】(六)Ionic3从目录结构理解开发

对比目前其它流行的js框架,个人觉得其分工明确、清晰好理解,我觉得就算一开始头脑一遍空白的新手,对他讲解过一次后都能有个大致印象。

1001
来自专栏IT笔记

Nginx学习之HTTP/2.0配置

哎呀,一不小心自己的博客也是HTTP/2.0了,前段时间对网站进行了https迁移并上了CDN,最终的结果是这酱紫的(重点小绿锁,安全标示以及HTTP/2.0请...

38914
来自专栏云计算教程系列

如何使用InspIRCd 2.0和Shaltúre在Ubuntu 14.04上设置IRC服务器

本教程介绍如何在Ubuntu 14.04上安装和配置InspIRCd 2.0,一个IRC服务器。在您自己的服务器上安装可以让您灵活地管理用户,更改他们的缺口,更...

1714
来自专栏玄魂工作室

CTF实战14 任意文件上传漏洞

该培训中提及的技术只适用于合法CTF比赛和有合法授权的渗透测试,请勿用于其他非法用途,如用作其他非法用途与本文作者无关

8983
来自专栏赵俊的Java专栏

Hexo 优化 --- 支持邮件通知的评论 Valine 增强版

8892
来自专栏云计算教程系列

如何在CentOS 7上添加Swap

使服务器响应更快,并防止应用程序中出现内存不足错误的最简单方法之一是添加一些swap空间。Swap是存储驱动器上的一个区域,操作系统可以在该区域临时存储无法再保...

1762
来自专栏游戏杂谈

关于chrome插件编写的小结

其中manifest文件最为重要,它定义/指明插件应用的相关信息(权限、版本、功能说明等),点此查看Manifest的详情>>

3683
来自专栏JMCui

Linux 学习记录 二 (文件的打包压缩).

 前言:本文参考《鸟哥的Linux 私房菜》,如有说的不对的地方,还请指正!谢谢!  环境:Centos 6.4  和window不同,在Linux压缩文件需要...

3605

扫码关注云+社区

领取腾讯云代金券