python3 爬虫库的基本使用

发布时间丨2023-02-25 11:32:27作者丨zhaomeng浏览丨0


爬虫获取数据的本质是网络请求,那么每个语言都有其获取网络请求的方法及对应的库。那么python3最为火爆的网络爬虫库有哪些呢?博主结合自己的使用经验,列出部分使用的频率比较高的python库。

一、网络请求库

常见的网络请求库requests 、aiohttp等等

# 安装
pip install requests
pip install selenium
pip install aiohttp

二、具体使用方式

网络请求库requests

requests库的常见使用方法如下:

方法有两种一种是GET请求,参数有如下几个:

res = requests.get(url,headers=headers,params,timeout,proxies)

GET请求的参数解释:

参数 解释
url 请求的目标链接
headers 请求携带的headers头
params 请求所需要的参数
timeout 请求超时时间
proxies 请求所需要的代理

resp响应对象的方法:

参数 解释
resp.url 请求的url
resp.status_code 响应返回的状态码
resp.content 获取返回的二进制数据,一般下载图片的时候使用
resp.text 获取返回的页面源代码及html
resp.headers 获取响应后的请求头
resp.json() 获取返回数据为json格式的源码
resp.encoding 获取返回的源码的编码

使用GET方法获取源代码及带有参数payload

import requests

# 获取网站的源代码
url = 'http://zhaomeng.net.cn/'
res=requests.get(url=url)
print(res.text)


#获取带有参数playload的请求,获取博文翻页第二页
url = http://zhaomeng.net.cn/
param={'page":2}
resp = requests.get(url=url,param=param)
print(resp.text)

另一种方法是POST请求:参数如下

res = requests.post(url,headers=headers,data/json,timeout,proxies)

POST参数解释:

参数 解释
url 请求的目标链接
headers 请求携带的headers头
data 请求所需要的form参数或者payload参数
timeout 请求超时时间
proxies 请求所需要的代理
json 请求所需要的form参数

resp响应的结果:

参数 解释
resp.url 请求的url
resp.status_code 响应返回的状态码
resp.content 获取返回的二进制数据,一般下载图片的时候使用
resp.text 获取返回的页面源代码及html
resp.headers 获取响应后的请求头
resp.json() 获取返回数据为json格式的源码
resp.encoding 获取返回的源码的编码

在HTTP协议中,post提交的数据必须放在消息主体中,但是协议中并没有规定必须使用什么编码方式,从而导致了提交方式的不同。服务端根据请求头中的Content-Type字段来获知请求中的消息主体是用何种方式进行编码,再对消息主体进行解析。具体的编码方式包括如下:

  • application/x-www-form-urlencoded   :如果是通过页面表单方式提交,那就是”application/x-www-form-urlencoded”,以form表单形式提交数据,最常见也是大家最熟悉的

          对于”application/x-www-form-urlencoded”,其参数组织形式,是键值对,类似于get方式的参数形式:name=张三&sex=男&tel=5354169,而json大家都知道,是这样的:
          

{
name:”张三”,
sex:”男”,
tel:”5354169”,
}

          所以,如果你传递的参数是json,而你声明的header是”application/x-www-form-urlencoded”,或者没有声明这个”Content-Type”(似乎默认就是”application/x-www-form-urlencoded”),则服务器拿不到提交的数据。数据是传过去了,但读不出来。

  • multipart/form-data :爬虫中很少用,一般用于上传文件
  • application/json  :如果是json(要反序列化成字符串),那就是”application/json”,以json串提交数据
  • text/xml :爬虫中很少用,它是一种使用 HTTP 作为传输协议,XML 作为编码方式的远程调用规范

POST使用方法如下:

提交Form表单

requests提交Form表单,一般存在于网站的登录,用来提交用户名和密码。以http://httpbin.org/post 为例,在requests中,以form表单形式发送post请求,只需要将请求的参数构造成一个字典,然后传给requests.post()的data参数即可。

#默认是application/x-www-form-urlencoded
url = 'http://httpbin.org/post'
d = {'key1': 'value1', 'key2': 'value2'}
resp = requests.post(url, data=d,headers={'Content-Type':'application/x-www-form-urlencoded'})
print(resp.text)

对于提交json串,主要是用于发送ajax请求中,动态加载数据

url = 'http://httpbin.org/post'
data = {'key1': 'value1', 'key2': 'value2'}
resp = requests.post(url, data=data,headers={'Content-Type':'application/json; charset=UTF-8'})
print(resp.text)

三、常见错误

常见请求头错误如下:

如果requests发送post请求:返回下面的错误信息:{"success":false,"errorCode":4000000,"errorMsg":"System Error","result":null}

但明明headers的Content-Type:application/json; charset=UTF-8都加上了,为什么会出错呀?

原因在于,你的请求实体的格式错了,目标服务端无法解码。

解决方法一:正确代码是把data进行json.dumps.编码,再发送。代码如下:

resp = requests.post(url=url,data =json.dumps(data),headers=headers)

现在就可以返回正确信息了。

解决方法二:    除了将data主动编码为json字符串发送之外,requests还提供了一个json参数,自动使用json方式发送,而且在请求头中也不用显示声明’Content-Type’:’application/json; charset=UTF-8’。完整代码如下:

resp = requests.post(url=url,json=data,headers=headers)

url = 'http://httpbin.org/post'
data = {'key1': 'value1', 'key2': 'value2'}
headers={}
resp = requests.post(url=url,json=data,headers=headers)
print(resp.text)

四、异步请求

网络请求库异步请求aiohttp

aiohttp 是使用 asyncio 作为基础库的 Python HTTP 客户端和服务器端。它支持异步 I/O,使得执行网络请求时不会阻塞主线程,从而提升应用程序的性能。以下是 aiohttp 异步请求的示例代码:

import aiohttp
import asyncio

async def fetch(session, url):
    async with session.get(url) as response:
        return await response.text()

async def main():
    async with aiohttp.ClientSession() as session:
        html = await fetch(session, 'https://www.example.com')
        print(html)

loop = asyncio.get_event_loop()
loop.run_until_complete(main())

以上代码中包含两个异步函数,一个是 fetch 用来发送 HTTP 请求并返回响应结果,另一个是 main 相当于控制器,调用 fetch 函数获取响应结果。在 main 函数中,使用 aiohttp.ClientSession() 创建一个异步 HTTP 客户端,并在其中调用异步函数 fetch 发送 GET 请求,参数为要请求的 URL 地址。

Python 的 async with 语句上下文管理器实现了对异步资源的自动释放,这样可以自动关闭协程函数打开的所有 socket 连接,并回收资源。函数执行完毕后,将结果通过 print() 输出到控制台。

当然,还有其他方法也可以实现 aiohttp 异步请求。例如,可以结合 asyncio 的 run_in_executor() 方法将同步操作转化为异步操作,或者利用回调函数和事件循环等实现异步请求。不论哪种方法,应该根据具体的任务需求选择最为合适的方式来实现。

需要注意的是,在使用 aiohttp 执行网络请求时,需要对异步任务加锁进行同步操作,避免因为并发导致数据错误或程序崩溃。此外,在实际的爬虫开发过程中,还需要注意遵守相关法律法规和道德准则,避免违反相关规定。