学习2:scrapy保存数据、scrapy数据建模与请求

保存数据

在pipelines.py文件中定义对数据的操作

1、定义一个管道类
2、重写管道类的process_item方法
3、process_item 方法处理完item之后必须返回给引擎

# 管道类
class Study1Pipeline:
    def process_item(self, item, spider):
        # item 是爬虫中返回的数据,一般是一个字典
        print("itecast:",item)
        # 默认使用完管道后需要将数据返回给引擎
        return item

在settings.py中配置启用管道
在这里插入图片描述
需要注意,如果以上两个操作都完成后。但是还是没有正确打印出print("itecast:",item),是因为你的爬虫文件中最后要返回出一个字典才行
在这里插入图片描述
这样在管道中才能拿到数据

在这里插入图片描述

将数据保存到文件中

import json 
# 管道类
class Study1Pipeline:
    
    # 类的初始化方法
    def __init__(self):
        self.file = open('itcast.json','w',encoding='utf-8')
    def process_item(self, item, spider):
        # item 是爬虫中返回的数据,一般是一个字典
        print("itecast:",item)
        # 将字典数据序列号,不进行ascii编码
        json_data = json.dumps(item,ensure_ascii=False) + ",\n"
        # 写入文件
        self.file.write(json_data)
        # 默认使用完管道后需要将数据返回给引擎
        return item

    # 用于对象被销毁前,执行一些清理工作
    def __del__(self):
        # 关闭文件
        self.file.close()

在这里插入图片描述

scrapy数据建模与请求

数据建模

建模的原因

  • 定义Item即提前规划那些字段需要爬取,防止手误。在定义好后,程序会自动检查
  • 配合注释可以清晰的知道要抓取那些字段,没有定义的字段不会被抓取
  • 使用scrapy的一些特定组件需要Item的支持

建模
items.py中定义要爬取的字段,在创建爬虫项目后,会自动生成该文件。
在这里插入图片描述
使用
定义好后需要在爬虫中导入并实例化,后续的使用和使用字典相同。

from study1.items import Study1Item

# 继承自Scrapy中的scrapy.Spider基类
class ItcastSpider(scrapy.Spider):
    # 爬虫名字
    name = "itcast"
    # 指定了爬虫允许爬取的域名范围
    allowed_domains = ["itcast.cn"]
    # 爬虫启动时要首先访问的初始URL,爬虫将从这些起始URL开始抓取网页内容,并逐渐遍历其他相关链接。
    start_urls = ["http://itcast.cn/"]

    # 解析方法,response时对应的响应
    def parse(self, response):
        # 使用xpath定位要爬取的内容,爬取精品课程
        list_selector = response.xpath("//ul[@class='ulon']/li")
        print(len(list_selector))
        # 遍历课程列表,获取名称
        for li in list_selector:
            # temp = {}
            # 实例化
            item = Study1Item()
            name = li.xpath("./a/text()")
            # xpath提取数据,返回的是一个列表,使用extract_first()方法提取列表中的第一个元素
            # 如果为多个元素,使用extract()方法
            # print("name:", name,name.extract_first())
            #temp["name"] = name.extract_first()
            item['name'] = name
            # 使用yield返回数据,而不是return。yield返回数据后,程序会继续执行,直到再次遇到yield,再返回数据
            #yield temp
            yield item

需要注意返回的item不是一个字典,在管道中使用时要对其进行转换

 def process_item(self, item, spider):
     # item 是爬虫中返回的数据,一般是一个字典
     # 将item转换为字典
     item = dict(item)
     print("itecast:",item)
     # 将字典数据序列号,不进行ascii编码
     json_data = json.dumps(item,ensure_ascii=False) + ",\n"
     # 写入文件
     self.file.write(json_data)
     # 默认使用完管道后需要将数据返回给引擎
     return item

请求

以翻页请求为例
1、找到下一页的URL地址
2、构造URL地址的请求对象,传递给引擎

实现方法
1、确定url地址
2、构造请求,scrapy.Request(url,callback)callback 指定解析函数名称,表示该请求返回的响应使用哪一个函数进行解析
3、把请求交给引擎:yield scrapy.Request(url,callback)

实例
爬取字体网站的字体名称、对应的字体类型和链接地址

字体网站:https://www.font.cn/zitiku/?scdh

创建项目:scrapy startproject study2

1、在items.py 文件里进行建模

class Study2Item(scrapy.Item):
    # 定义字体的名称和类型
    fontName = scrapy.Field()
    fontType = scrapy.Field()

2、创建爬虫文件
在项目目录下运行:scrapy genspider font font.cn 其中font是爬虫名称,font.cn是网站域名
3、编写相应基础内容

# 引入建模
from study2.items import Study2Item


class FontSpider(scrapy.Spider):
    # 爬虫名称
    name = "font"
    # 允许访问的域名
    allowed_domains = ["font.cn"]
    # 起始地址,一般需要进行修改
    start_urls = ["https://www.font.cn/zitiku/"]

    def parse(self, response):
        # 1、提取数据,字体名称和类型
        # 1.1 获取所有的节点
        node_list = response.xpath("//div[@class='item_top clearfix']")
        # print("节点数量:",len(node_list))
        # 1.2 遍历节点,获取数据
        for num, node in enumerate(node_list):
            # 实例化对象
            item = Study2Item()
            # print(num,node)
            name = node.xpath(
                "./div[@class='item_top_left']/p/a/text()"
            ).extract_first()
            type = node.xpath(
                "./div[@class='item_top_right']/p/a/text()"
            ).extract_first()
            # response.urljoin 将相对路径转换为绝对路径
            url = response.urljoin(
                node.xpath("./div[@class='item_top_left']/p/a/@href").extract_first()
            )
            item["fontName"] = name
            item["fontType"] = type
            item["fontUrl"] = url
            print(item)
        # 2、模拟翻页
        # 2.1 获取下一页的链接
        pageBox = response.xpath("//div[@class='PageBox']")
        next_url = ''
        # 2.2 判断是否有下一页
        # 2.3 构建请求对象
        yield scrapy.Request(url=next,callback=self.parse)

效果图:
在这里插入图片描述
注意:
1、你在浏览器里看到的元素代码是解析后的,但是scrapy获取到的是未经解析过的代码。未经解析过的代码可以直接查看网页源代码
在写xpath时一定要比较一下网页代码是否一致,不一致以网页源代码为准
2、网页源代码中是未经过编译的,所以有些通过javascript生成的代码是拿不到的。就比如上面的分页条是动态生成的拿不到。
因此未实现翻页功能。关于如何处理动态生成的部分,后面学到相关内容后在进行补充。

ROBOTS协议

ROBOTS协议,全称为Robots Exclusion Protocol(网络爬虫排除标准),是一种由网站所有者创建的、位于网站服务器根目录下的纯文本文件,通常命名为robots.txt。这个文件作为网站和网络爬虫(包括搜索引擎爬虫和其他自动抓取工具)之间的通信手段,指示爬虫哪些页面或目录可以抓取,哪些不应被抓取。

可以在settings中设置ROBOTS协议

# False表示忽略协议,默认为True
# Obey robots.txt rules
ROBOTSTXT_OBEY = True

User-Agent

User-Agent 是 HTTP 请求头中的一个字段,用于标识发起请求的应用程序或用户代理软件的信息,包括软件的名称、版本以及其他一些相关信息。当浏览器、搜索引擎爬虫或者其他客户端向Web服务器发起请求时,会在请求头中包含 User-Agent 字段,以便于服务器识别客户端类型并做出相应的响应。

在这里插入图片描述
这一部分可以复制实际的User-Agent来进行简单的伪装
在这里插入图片描述

  • 15
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
Scrapy是一个Python编写的开源Web爬虫框架,可以用于抓取互联网上的数据或者进行数据挖掘。它的核心原理是基于Twisted异步网络框架构建的,可以同时并发抓取多个网页,从而提高数据爬取的效率。 Scrapy的核心组件包括:引擎(Engine)、调度器(Scheduler)、下载器(Downloader)、爬虫中间件(Spider Middlewares)、下载器中间件(Downloader Middlewares)和项目管道(Item Pipelines)。 引擎是Scrapy的核心组件,它负责控制整个爬虫的运行流程,并协调其他组件之间的工作。当爬虫启动时,引擎会从调度器中取出一个URL,并把它交给下载器进行下载。下载完成后,引擎会把下载器返回的响应交给爬虫解析,从而得到需要的数据。 调度器负责管理待爬取的URL队列,并根据一定的策略进行调度。当引擎需要获取新的URL时,调度器会根据策略从队列中取出一个URL,并把它交给下载器进行下载。 下载器负责从网络上下载HTML页面,并把下载的数据返回给引擎。下载器可以使用多种网络协议(如HTTP、FTP等),也可以进行异步下载,从而提高下载效率。 爬虫中间件用于处理爬虫的输入和输出,可以对请求和响应进行增强或修改。例如,可以使用中间件对请求进行代理、重定向或增加请求头信息等操作。 下载器中间件用于处理下载器的输入和输出,可以对请求和响应进行增强或修改。例如,可以使用中间件对响应进行解压缩、修改响应头信息等操作。 项目管道用于对爬虫获取的数据进行处理和存储。可以使用管道对数据进行清洗、格式化、去重等操作,并将数据存储到数据库、文件或其他存储介质中。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

无知的小菜鸡

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值