scrapy抓取,如何改写非200状态码的response返回值?
发布于 作者:苏南大叔 来源:程序如此灵动~scrapy
目前是非常火热的抓取框架,苏南大叔以前更新过这个scrapy
框架的部分教程。目前,对以前的内容进行一些适当的补充。本文中,解决的问题是scrapy
抓取文件的时候,会碰到一些非200
状态码的情况,比如:500
/301
/302
之类的异常请求。
大家好,这里是苏南大叔的“程序如此灵动”博客,我是苏南大叔。本文中,苏南大叔将对scrapy
碰到的非200
情况进行处理。希望对您有所帮助。
本文测试环境:win10
,python@3.6.8
,scrapy@2.5.1
。
新建scrapy
项目
这里先回顾一下建立scrapy
的方法,scrapy
项目是使用pip
安装的。
pip install scrapy
创建一个新的项目su
,新建一个名为example
的蜘蛛,目标网站是example.com
。
scrapy startproject su
cd su
scrapy genspider example example.com
然后对su/spiders/example.py
编写实际的蜘蛛逻辑,并运行编写的蜘蛛代码。
scrapy crawl example
结果发现,在实际的批量数据抓取过程中,一些文章页面会跳转到另外的栏目,提供的并不是苏南大叔的目标数据,导致后续逻辑出错。
解决方案
新建middleware
,处理process_response
函数,对于非200
状态码的情况,模拟一个新的response
。
su/middlewares.py
:
class CheckStatus(object):
def process_response(self, response, request, spider):
if response.status != 200:
# print(response.status)
return response.replace(body="")
else:
return response
su/settings.py
:
DOWNLOADER_MIDDLEWARES = {
'su.middlewares.CheckStatus': 542,
}
这里的su.middlewares.CheckStatus
是有命名依据的,是上述捕获非200
代码处理方案的class
的名字。542
只是一个比较大的值,用于控制权重的。所以,您可以修改为您喜欢的任何合理数字。
spiders/example.py
里面不做任何的逻辑修改,当然,值得注意的是,当出现非200
的情况时,获得的html
是自己可以自定义的。上述代码里面是留空了,实际上可以替换成任何想自定义的标记。
可能的问题一
在middleware
里面,如果直接修改response
的body
,
response.body=""
会得到一个错误提示:
AttributeError: HtmlResponse.body is not modifiable, use HtmlResponse.replace() instead
这里的解决方案就是使用response.replace()
,这里不但可以替换body
,实际上还可以替换status
,url
等等。这里大家可以自行试验。
response.replace(body="")
可能的问题二
不要以为上述middleware
可以捕获所有的状态码了,您还可能会碰到如下类似提示信息:
Ignoring response <500>: HTTP status code is not handled or not allowed
解决方案是,修改settings.py
:
HTTPERROR_ALLOWED_CODES = [403,500]
当然需要您根据实际情况,修改上述数组,添加新的错误状态码。如果不做上述修改的话,scrapy
运行时如果碰到500
状态返回值,可能会意外结束运行。
相关链接
总结
scrapy
爬虫似乎很好很强大,不过对于苏南大叔来说,还是比较喜欢使用php
外加phpquery
来直接写,似乎思路会更加流畅。但是,拥抱新技术才是正确的选择。更多scrapy
的经验文字,请点击苏南大叔的博客:
本博客不欢迎:各种镜像采集行为。请尊重原创文章内容,转载请保留作者链接。