application实现网页计数_Python爬虫:模拟浏览器访问实现http报文体压缩传输

一、 引言
在《第14.6节 Python模拟浏览器访问网页的实现代码》介绍了使用urllib包的request模块访问网页的方法。但上节特别说明http报文头Accept-Encoding最好不设置,否则服务端会根据该字段及服务端的情况采用对应方式压缩http报文体,如果爬虫应用没有解压支持会导致应用无法识别收到的响应报文体。本节简单介绍一下怎么处理响应报文体的压缩。
在爬虫爬取网页时,如果在请求头中传递了“‘Accept-Encoding’:‘gzip’”信息则服务器会采用gzip压缩报文,此时客户端必须支持对报文解压缩才能识别报文。解gzip压缩需要安装gzip模块,并在服务器返回http应答报文时判断服务端是否压缩了报文,如果压缩了就进行解压处理,否则直接读取。

57ec3aec18f3a7710c7be061ac1ec951.png

二、 对HTTP响应报文的报文体支持压缩处理的爬虫处理步骤
要进行响应HTTP报文体的压缩,爬虫应用需要进行如下处理:
1、 在请求报文的http报文头中的Accept-Encoding中设置能支持的压缩格式;
2、 读取响应报文后要判断响应报文头中的Content-Encoding的返回值的压缩格式;
3、 调用对应的解压方法进行报文体解压。

5256de8b9e2c001803c67102962c32ce.png

三、 案例
1、 导入相关模块:
import urllib.request
from io import BytesIO
import gzip

2、 构造支持压缩的请求报文头
本节在《第14.5节 利用浏览器获取的http信息构造Python网页访问的http请求头》的mkhead函数的基础上,增加一个参数来确认是否需要处理压缩报文,如果是则通过http报文头的Accept-Encoding参数向服务器告知支持的压缩格式,否则不设置压缩格式支持的请求报文头Accept-Encoding参数,代码如下:

  def mkhead(NeedEncoding=False):    if NeedEncoding:        header = {'Accept':'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3',        'Accept-Encoding':'gzip',        'Accept-Language':'zh-CN,zh;q=0.9',        'Connection':'keep-alive',        'Cookie':'uuid_tt_dd=10_35489889920-1563497330616-876822;......',        'User-Agent':'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.100 Safari/537.36'}    else:        header = {'Accept':'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3',        'Accept-Language':'zh-CN,zh;q=0.9',        'Connection':'keep-alive',        'Cookie':'uuid_tt_dd=10_35489889920-1563497330616-876822;......',        'User-Agent':'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.100 Safari/537.36'}            return header

3、 读取响应报文后取响应报文头中的Content-Encoding的返回值的压缩格式

8f4f548c5f49dcc75b6d2dd226a4de7c.png
 req = urllib.request.Request(url=site,headers=header)   sitersp = urllib.request.urlopen(req)   Encoding = sitersp.info().get('Content-Encoding')  #取响应报文体的压缩格式123

4、 根据压缩对应情况进行处理后返回报文体的内容,如果是gzip压缩就调用gzip解压,如果未压缩就不进行解压处理,否则报错返回:

 if  Encoding== 'gzip':  #判断压缩格式是否gzip格式        print(" Encoding== 'gzip'")        buf = BytesIO(sitersp.read())        fzip = gzip.GzipFile(fileobj=buf)        return fzip.read().decode()    elif not Encoding:  #是否没有压缩报文体        print(" Encoding==None")        return sitersp.read().decode()    else:        print(f"Content-Encoding={Encoding},can't unzip")        return None        123456789101112

四、 案例完整代码

#读取压缩http响应报文import urllib.requestfrom io import BytesIOimport gzip   def mkhead(NeedEncoding=False):    if NeedEncoding:        header = {'Accept':'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3',        'Accept-Encoding':'gzip',        'Accept-Language':'zh-CN,zh;q=0.9',        'Connection':'keep-alive',        'Cookie':'uuid_tt_dd=10_35489889920-1563497330616-876822;...... ',        'User-Agent':'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.100 Safari/537.36'}    else:        header = {'Accept':'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3',        'Accept-Language':'zh-CN,zh;q=0.9',        'Connection':'keep-alive',        'Cookie':'uuid_tt_dd=10_35489889920-1563497330616-876822;......',        'User-Agent':'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.100 Safari/537.36'}            return header def readweb(site):    header = mkhead(True)    try:        req = urllib.request.Request(url=site,headers=header)        sitersp = urllib.request.urlopen(req)    except Exception as e:        print(e)        return None    Encoding = sitersp.info().get('Content-Encoding')    if  Encoding== 'gzip':        print(" Encoding== 'gzip'")        buf = BytesIO(sitersp.read())        fzip = gzip.GzipFile(fileobj=buf)        return fzip.read().decode()    elif not Encoding:        print(" Encoding==None")        return sitersp.read().decode()    else:        print(f"Content-Encoding={Encoding},can't unzip")        return None       readweb(r'https://blog.csdn.net/LaoYuanPython/article/details/100585881 ')[0:100]

执行结果:

>>> readweb(r'https://blog.csdn.net/LaoYuanPython/article/details/100585881 ')[0:100] Encoding== 'gzip''    >>

注意:代码中的cookie设置可以不要,那就是匿名爬取网页,如果需要非匿名则需要根据自己浏览器的cookie来设置。

本节介绍了使用urllib包的request模块读取网页并支持解压的实现过程,以支持网页内容的压缩传输。

关于原文链接

本文在CSDN的“老猿Python”首发,头条号、微信公众号和百家号“老猿Python”转载,由于这些平台对外部链接的限制,文中不能包含外部链接。如果是头条请点击文章底部最下方的“了解更多”跳转CSDN阅读原文,如果是微信公众号请点击文章底部最下方的“阅读原文”跳转CSDN阅读原文,否则请在百度搜索或CSDN搜索中输入"CSDN老猿Python”加文章标题关键字搜寻本文

c049650a800e47cca94039301759b74e.png
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值