scrapy分页抓取川大公管学院老师信息

关于任务思考:
1.确定爬虫入口:

start_urls = [
        'http://ggglxy.scu.edu.cn/index.php?c=article&a=type&tid=18&page_1_page=1',
    ]

确定爬虫入口应该是编写爬虫的第一步,但是很不幸,我在第一步就走偏了
,从公共管理学院首页进到师资队伍页面获得的网址是

http://ggglxy.scu.edu.cn/index.php?c=article&a=type&tid=18

但是从这个网址我无法获得下一页的绝对链接,在执行爬虫的过程中,我就遇上了URLERROR的错误。

  1. 爬取思路:
图片.png

从这张图,可以看出,我们可以在目录页抓取教师姓名、教师职位、教师所属专业、教师邮箱,因此我们只需要在详情页获取教师的简介就可以了。

下一页.png

从网站的目录页中,每页有八项数据,我需要拿到每一项的数据的链接,同时还需要拿到「下一页」的链接。因为下一页的结构和第一页的结构相同,所以我将下一页的连接传给pasre处理,而每一项数据的链接交给pasre_content处理。

  1. 代码实现:
    3.1 items.py文件:
class TeacherItem(scrapy.Item)
     name = scrapy.Field()    #教师姓名
     position = scrapy.Field()  #教师职位
     intro = scrapy.Field()   #教师   
     email = scrapy .Field() #教师邮箱
     major = scrapy.Field()#教师所属专业
     pass

3.2 spider代码:
处理目录页的教师信息的代码:

 def parse(self,response):
        for quote in response.css('ul.teachers_ul.mt20.cf li.fl'):
            item = TeacherItem()
            item['name'] = quote.css('div.r.fr h3.mb10::text').extract_first()#教师名字
            item['position'] = quote.css('div.r.fr p.color_main.f14::text').extract_first()#教师职位
            item['major'] = quote.css('div.r.fr div.desc p::text').extract_first()#教师所属专业
            item['email'] = response.xpath('//div[@class="r fr"]/div[@class="desc"]/p[last()]/text()').extract()#教师邮箱
            url = response.urljoin(quote.css('div.l.fl a::attr("href")').extract_first())#教师详情页链接
            request=scrapy.http.Request(url,callback=self.parse_content)#将获取的信息传给详情页处理器
            request.meta['item']=item
            yield request

处理下一页的链接的代码:

      next_page = response.xpath('//div[@class="pager cf tc pt10 pb10 mobile_dn"]/li[last()-1]/a/@href').extract_first()   #获取下一页的链接
        if next_page is not None:
            next_full_url = response.urljoin(next_page)
            yield scrapy.Request(next_full_url, callback=self.parse)  #判断是有有下一页,有的话,就将url传给自身

处理每一项数据链接的代码:

 def parse_content(self,response):
        for site in response.css('div.js_infobox.cf'):
            item = response.meta['item']#接收meta传递过来的数据,即姓名、邮箱、职位等信息
            item['intro']= site.css('div.r.fr div.desc::text').extract_first()
            yield item

在编写这个代码的过程中,我认为元素的定位是最难的,路径不对数据就爬不出。
3.3 执行爬虫
同样使用scrapy crawl quotes命令来执行爬虫,爬取之后下载文件,打开:

数据.png

由于文件默认的是unicode编码格式,所以我爬取到的数据是一堆我看不懂数据。我首先尝试了同学使用过并可行的
scrapy crawl quotes -o teacher.json -s FEED_EXPORT_ENCODING=utf-8
命令,结果生成的还是unicode编码格式的文件。
3.4 处理unicode编码问题
通过网上查找,我运用了下面的方法解决问题:
修改pipelines.py文件:

import json
import codecs


class QuotesPipeline(object):
    def __init__(self):
        self.file =codecs.open('teacher.json','wb',encoding='utf-8')
    def process_item(self, item, spider):
        line=json.dumps(dict(item))+'\n'
        self.file.write(line.decode("unicode_escape"))
        return item

在pipelines.py这个文件中,通过编写QuotesPipeline来实现对item的处理。它主要完成数据的查重、丢弃,验证item中的数据,将得到的item数据保存等工作。其中 process_item方法将得到的item实现解码,以便正常显示中文,最终保存到json文件中。
在编写完pipelines.py后,为了启动它,必须将其加入到ITEM_PIPELINES配置中:

ITEM_PIPELINES = {
    'quotes.pipelines.QuotesPipeline':300
}

修改完这些文件后,我再次执行spiders,将得到的结果保存并下载:

图片.png

这次,数据显示正常,共抓取到了128位老师的信息,其中包括了教师的姓名、职位、所属专业、邮箱与简介。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容