【Python3 爬虫学习笔记】pyspider框架的使用 2

本文介绍如何使用Pyspider爬取去哪儿网的旅游攻略,包括启动Pyspider、创建项目、编写代码、调试及运行爬虫的全过程。重点讲解了如何配置爬虫、解析页面、提取所需信息,并将其存储到MongoDB中。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

pyspider的基本使用

计划爬取去哪儿网的旅游攻略,链接为http://travel.qunar.com/travelbook/list.htm,要将所有攻略的作者、标题、出发日期、人均费用、攻略正文等保存下来,存储到MongoDB中。

启动pyspider

执行如下命令启动pyspider:

pyspider all

运行结果如下:
在这里插入图片描述
这样可以启动pyspider的所有组件,包括PhantomJS、ResultWorker、Processer、Fetcher、Scheduler、WebUI,这些都是pyspider运行必备的组件。最后一行输出提示WebUI运行在5000端口上。可以打开浏览器,输入链接http://localhost:5000,这时打开浏览器,可以看到:
在这里插入图片描述
此页面便是pyspider的WebUI,我们可以用它来管理项目、编写代码、在线调试、监控任务等。

创建项目

在WebUI中,点击右侧的Create按钮,在弹出的浮窗里输入项目的名称和爬取的链接,再点击Create按钮,这样就成功创建一个项目。接下来会看到pyspider的项目遍及和调试页面,如图所示:
在这里插入图片描述
左侧就是代码的调试页面,点击左侧右上角的run单步调试爬虫程序,在左侧下半部分可以预览当前的爬取页面。右侧是代码编辑页面,我们可以直接编辑代码和保存代码,不需要借助IDE。
注意右侧,pyspider已经帮我们生成了一段代码,代码如下所示:

from pyspider.libs.base_handler import *


class Handler(BaseHandler):
    crawl_config = {
    }

    @every(minutes=24 * 60)
    def on_start(self):
        self.crawl('http://travel.qunar.com/travelbook/list.htm', callback=self.index_page)

    @config(age=10 * 24 * 60 * 60)
    def index_page(self, response):
        for each in response.doc('a[href^="http"]').items():
            self.crawl(each.attr.href, callback=self.detail_page)

    @config(priority=2)
    def detail_page(self, response):
        return {
            "url": response.url,
            "title": response.doc('title').text(),
        }

这里的Handler就是pyspider爬虫的主类,我们可以在此处定义爬取、解析、存储的逻辑。整个爬虫的功能只需要一个Handler即可完成。
接下来我们可以看到一个crawl_fonfig属性。我们可以将本项目的所有爬取配置统一定义到这里,如定义Headers、设置代理等,配置之后全局生效。
然后,on_start()方法是爬取入口,初始的爬取请求会在这里产生,该方法通过调用crawl()方法即可新建一个爬取请求,第一个参数是爬取的URL,这里自动替换成我们所定义的URL。crawl()方法还有一个参数callback,它指定了这个页面爬取成功后用哪个方法进行解析,代码中指定为index_page()方法,即如果这个URL对应的页面爬取成功了,那Response将交给index_page()方法解析。
index_page()方法恰好接收这个Response参数,Response对接了pyquery。我们直接调用doc()方法传入相应的CSS选择器,就可以像pyquery一样解析此页面,代码中默认是a[href^=“http”],也就是说该方法解析了页面的所有链接,然后将链接遍历,再次调用了crawl()方法生成了新的爬取请求,同时再指定了callback为detail_page,意思是说这些页面爬取成功了就调用detail_page()方法解析。这里,index_page()实现了两个功能,一是将爬取的结果进行解析,二是生成新的爬取请求。
detail_page()同样接收Response作为参数。detail_page()抓取的就是详情页的信息,就不会生成新的请求,只对Response对象做解析,解析之后将结果以字典形式返回。当然我们也可以进行后续处理,如将结果保存到数据库。

爬取首页

点击左栏右上角的run按钮,即可看到页面下方follow便会出现一个标注,其中包含数字1,这代表有新的爬取请求产生,如图所示:
在这里插入图片描述
左栏左上角会出现当前run的配置文件,这里有一个callback为on_start,这说明点击run之后实际是执行了on_start()方法。在on_start()方法中,我们利用crawl()方法生成一个爬取请求,那下方follows部分的数字1就代表了这一个爬取请求。
点击下方的follows按钮,即可看到生成的爬取请求的链接。每个链接的右侧还有一个箭头按钮,如图所示。点击该箭头,我们就可以对此链接进行爬取,也就是爬取攻略的首页内容。
在这里插入图片描述
点击下方的follows按钮,即可看到生成的爬取请求的链接。每个链接的右侧还有一个箭头按钮,点击该箭头,我们就可以对此链接进行爬取,也就是爬取攻略的首页内容,如上图所示。
上方的callback已经变成了index_page,这就代表当前运行了index_page()方法。index_page()接收到的response参数就是刚才生成的第一个爬取请求的Response对象。index_page()方法通过调用doc()方法,传入提取所有a节点的CSS选择器,然后获取a节点的属性href,这样实际上就是获取了第一个爬取页面中的所有链接。然后再index_page()方法里遍历了所有链接,同时调用crawl()方法,就把这一个个的链接构造成新的爬取请求了。所以最下方follows按钮部分有229的数字标记,这代表新生成了229个爬取请求,同时这些请求的URL都呈现在当前页面了。
再点击下方的web按钮,即可预览当前爬取结果的页面。点击html按钮即可查看当前页面的源代码,如果需要分析代码的结构,我们可以直接参考页面源码。
我们刚才在index_page()方法中提取了所有的链接并生成了新的爬取请求。但是很明显要爬取的肯定不是所有链接,只需要攻略详情的页面链接就够了,所以我们要修改一下当前index_page()里提取链接时的CSS选择器。
接下来需要另外一个工具。首先切换到Web页面,找到攻略的标题,点击下方的enable css selector helper,点击标题。这时候我们看到标题外多了一个红框,上方出现了一个CSS选择器,这就是当前标题对应的CSS选择器。
在右侧代码选中要更改的区域,点击左栏的右箭头,此时在上方出现的标题的CSS选择器会被替换到右侧代码中:
在这里插入图片描述
这样就成功完成了CSS选择器的替换,非常便捷。
重新点击左栏右上角的run按钮,即可重新执行index_page()方法。此时的follows就变成了10个,也就是说我们提取的只有当前页面的10个攻略。
我们现在抓取的只是第一页的内容,还需要抓取后续页面,所以还需要一个爬取链接,即爬取下一页的攻略列表页面。我们再利用crawl()方法添加下一页的爬取请求,在index_page()方法里面添加如下代码,然后点击save保存:

next = response.doc('.next').attr.href
self.crawl(next, callback=self.index_page)

利用CSS选择器选中下一页的链接,获取它的href属性,也就获取了页面的URL。然后将该URL传给crawl()方法,同时指定回调函数,注意这里回调函数仍然指定为index_page()方法,因为下一页的结构与此页相同。
重新点击run按钮,这时就可以看到11个爬取请求。follows按钮会显示11,这就代表我们成功添加了下一页的爬取请求。
现在,索引列表页的解析过程我们就完成了。

爬取详情页

任意选取一个详情页进入,点击前10个爬取请求中的任意一个的右箭头,执行详情页的爬取。
切换到Web页面预览效果,页面下拉之后,头图正文中的一些图片一直显示加载中。查看源代码,我们没有看到img节点。出现此现象的原因是pyspider默认发送HTTP请求,请求的HTML文档本身就不包含img节点。但是在浏览器中我们看到了图片,这时因为这张图片时后期经过JavaScript出现的。
我们将index_page()中生成抓取详细页的请求方法添加一个参数fetch_type,改写的index_page()变为如下内容:

def index_page(self, response):
	for each in response.doc('li > .tit > a').items():
		self.crawl(each.attr.href, callback=self.detail_page, fetch_type='js')
	next = response.doc('.next').attr.href
	self.crawl(next, callback=self.index_page)

重新抓取,可以发现页面中的图片被正常加载了,这就是启用了PhantomJS渲染后的结果。只需要添加一个fetch_type参数即可。
最后就是将详情页中需要的信息提取出来。
在这里插入图片描述
(运行过程中,出现过一个问题,就是获取信息部位,出现了HTTP 501 错误,查询之后发现,原来在使用PhantomJS后,PhantomJS未加入PATH,安装好后便能正常运行了。)
左栏中输出了最终构造的字典信息,这就是一篇攻略的抓取结果。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值