Python网络爬虫与信息提取学习记录(四)

『第四周』Scrapy框架

Scrapy框架

Scrapy是一个快速功能强大的网络爬虫框架

官网:https://scrapy.org/

帮助文档:https://scrapy-chs.readthedocs.io/zh_CN/1.0/index.html

—什么是爬虫框架?

—爬虫框架是实现爬虫功能的一个软件结构和功能组件集合。
—爬虫框架是一个半成品,能够帮助用户实现专业网络爬虫。

架构

在这里插入图片描述

组件(5+2结构:5个主体和2个中间键)

  • Scrapy Engine
    控制所有模块之间的数据流;根据条件触发事件。(无需修改)

  • 调度器(Scheduler)
    对所有爬取请求进行调度管理。(无需修改)

  • 下载器(Downloader)
    根据请求下载网页。(无需修改)

  • Spiders
    向整个框架提供了最初始的访问链接,同时对每次爬取回来的内容进行解析,再次产生新的爬取请求,并且从内容中分析出提取出相关的数据。

  • Item Pipeline
    以流水线方式处理Spider产生的爬取项。
    由一组操作顺序组成,类似流水线,每个操作是一个Item Pipeline类型。
    可能操作包括:清理、检验和查重爬取项中的HTML数据、将数据存储到数据库。

  • 下载器中间件(Downloader middlewares)
    目的:实施Engine、Scheduler和Downloader之间进行用户可配置的控制。
    功能:修改、丢弃、新增请求或响应。

  • Spider中间件(Spider middlewares)
    目的:对请求和爬取项的再处理。
    功能:修改、丢弃、新增请求或爬取项。

在这5个模块之间,数据包括用户提交的网络爬虫请求,以及从网络上获取的相关内容,在这些结构之间进行流动,形成数据流。

三条主要的数据流路径

第一条:

在这里插入图片描述

SpidersEngineScheduler

  1. 引擎打开一个网站(open a domain),找到处理该网站的Spider并向该spider请求第一个要爬取的URL(s)。

  2. 引擎从Spider中获取到第一个要爬取的URL并在调度器(Scheduler)以Request调度。

第二条:

在这里插入图片描述

SchedulerEngineDownloaderSpiders

  1. 引擎向调度器请求下一个要爬取的URL。

  2. 调度器返回下一个要爬取的URL给引擎,引擎将URL通过下载中间件(请求(request)方向)转发给下载器(Downloader)。

  3. 一旦页面下载完毕,下载器生成一个该页面的Response,并将其通过下载中间件(返回(response)方向)发送给引擎。

  4. 引擎从下载器中接收到Response并通过Spider中间件(输入方向)发送给Spider处理。

第三条:

在这里插入图片描述

SpidersEngineItem Pipeline

  1. Spider处理Response并返回爬取到的Item及(跟进的)新的Request给引擎。

  2. 引擎将(Spider返回的)爬取到的Item给Item Pipeline,将(Spider返回的)Request给调度器。

  3. (从第二步)重复直到调度器中没有更多地request,引擎关闭该网站。

从前到后,这个框架的入口是Spiders,出口是Item Pipeline

其中Scheduler/Engine/Downloader 都是已有的功能实现

Spiders /Item Pipeline 需要用户去配置

Request库和Scrapy框架比较

相同点:

  • 两者都可以进行页面请求和肥取,Python爬虫的两个重要技术路线。

  • 两者可用性都好,文档丰富,入门简单。

  • 两者都没有处理js、提交表单、应对验证码等功能(可扩展)。

不同点:

RequestsScrapy
页面级爬虫网站级爬虫
功能库框架
并发性考虑不足,性能较差并发性好,性能较高
重点在于页面下载重点在于爬虫结构
定制灵活一般定制灵活,深度定制困难
上手十分简单入门稍难

Scrapy爬虫的常用命令

Scrapy命令行格式

scrapy [options] [args]
Scrapy命令 ↑

命令说明格式
startproject创建一个新工程scrapy startproject [dir]
genspider创建一个爬虫scrapy genspider [options]
settings获得爬虫配置信息scrapy settings [options]
crawl运行一个爬虫scrapy crawl
list列出工程中所有爬虫scrapy list
shell启动URL调试命令行scrapy shell [url]

Scrapy爬虫的命令行逻辑

为什么 Scrapy采用命令行创建和运行爬虫?

  • 命令行(不是图形界面)更容易自动化,适合脚本控制。

  • 本质上,Scrapy是给程序员用的,功能(而不是界面)更重要。

Scrapy爬虫的第一个实例

演示HTML页面地址:http://python123.io/ws/demo.html
文件名称:demo.html

步骤1:建立一个Scrapy爬虫工程

在选定的一个目录中打开cmd,输入scrapy startproject python123demo

在这里插入图片描述

会生成一个目录

在这里插入图片描述

└─python123demo                →    外层目录
    │  scrapy.cfg              →    部署[^1]Scrapy爬虫的配置文件
    │
    └─python123demo            →    Scrapy框架的用户自定义Python代码
        │  items.py            →    Items代码模板(继承类)
        │  middlewares.py      →    Middlewares代码模板(继承类)
        │  pipelines.py        →    Pipelines代码模板(继承类)
        │  settings.py         →    Scrapy爬虫的配置文件
        │  __init__.py         →    初始化脚本
        │
        └─spiders              →    Spiders代码模板目录(继承类)
                __init__.py    →    初始文件,无需修改
                __pycache__/   →    缓存目录,无需修改(我生成的没有该文件)

1:部署:将这样的爬虫放在特定的服务器上,并且在服务器配置好相关的操作接口。

生成文件夹目录结构可以在cmd中进入要生成目录的文件夹路径下,输入tree /f
详细参照:https://blog.csdn.net/weixin_43723625/article/details/106172273

步骤2:在工程中产生一个Scrapy爬虫

然后输入

cd python123demo
scrapy genspider demo python123.io

生成一个名称为demo的spider,然后会发现在spiders目录下会生成demo.py文件

这里是使用命令来生成demo.py,实际上可以手动生成该文件

import scrapy


class DemoSpider(scrapy.Spider):
    name = 'demo'
    allowed_domains = ['python123.io']
    start_urls = ['http://python123.io/']

    def parse(self, response):
        pass

由于爬虫名称为demo,所以类名和name变量中出现demo。很神奇的是当我输入scrapy genspider 123python123.io 时,文件和类名称会自动在'123'前加'a'

name爬虫名称
allowed_domains命令行用户提交的域名,指的是这个爬虫在爬取网站的时候,它只能爬取这个域名以下的相关链接
start_urlsScrapy框架所要爬取页面的初始页面
def parse解析页面的空的方法
parse()用于处理响应,解析内容形成字典,发现新的URL爬取请求。

步骤3:配置产生的spider爬虫

allowed_domains 这一行不需要,可以注释掉

start_urls修改为http://python123.io/ws/demo.html

然后更改爬取方法的具体功能

爬取方法有两个参数:

  • self: 面向对象类所属关系的标记

  • response: 从网络中返回内容所存取的内容或对象

这里把response中的内容保存到html文件中

def parse(self, response):
    fname = response.url.split('/')[-1]    # 从url最后一部分提取文件名
    with open(fname, 'wb') as f:
        f.write(response.body)
    self.log('Saved file %s.' % name)
    pass

步骤4:运行爬虫,获取网页

在cmd中输入scrapy crawl demo

在目录下会产生demo.html文件

在这里插入图片描述

上面的代码是Scrapy框架提供的简化版的代码

下面展示完整版代码

import scrapy

class DemoSpider(scrapy.Spider):
    name = 'demo'
    
    def start_requests(self):
      urls = [
                'http://python123.io/ws/demo.html'
             ]
      for url in urls:
        yield scrapy.Request(url=url, callback=self.parse)
    
    def parse(self, response):
        fname = response.url.split('/')[-1]    # 从url最后一部分提取文件名
        with open(fname, 'wb') as f:
            f.write(response.body)
        self.log('Saved file %s.' % name)
        pass

在这里插入图片描述

由命令生成的简化版demo.py文件,它通过 start urls这个列表来给出初始的url链接。

但Scrapy框架支持另一种使用start_requests 的等价方法。首先定义一个urls列表,并且通过对列表中每一个元素通过yield scrapy.Requestengine提出了url访问请求

yield

生成器(generator)

  • 生成器是一个不断产生值的函数

  • 包含yield语句的函数是一个生成器

  • 生成器每次产生一个值(yield语句),函数被冻结,被唤醒后再产生一个值。

一个函数执行到某一个位置产生了一个值,然后被冻结,再次唤醒后还是从这个位置继续去执行。

可参照:https://blog.csdn.net/mieleizhi0522/article/details/82142856/

为何要有生成器?

生成器相比一次列出所有内容的优势:

  • 更节省存储空间

  • 响应更迅速

  • 使用更灵活

例如在普通写法中要存储100万,生成器写法只需1。

在规模很大的时候,生成器有很大的存储空间节省优势

Scrapy爬虫的基本使用

Request类

class scrapy.http.Request()

  • Request对象表示一个HTTP请求。

  • 由Spider生成,由Downloader执行。

属性或方法说明
.urlRequest对应的请求URL地址
.method对应的请求方法,‘GET’ 'POST’等
.headers字典类型风格的请求头
.body请求内容主体,字符串类型
.meta用户添加的扩展信息,在Scrapy内部模块间传递信息使用
.copy()复制该请求

Response类

class scrapy.http.Response()

  • Response对象表示一个HTTP响应。

  • 由Downloader生成,由Spider处理。

属性或方法说明
.urlResponse对应的URL地址
.statusHTTP状态码,默认是200
.headersResponse对应的头部信息
.bodyResponse对应的内容信息,字符串类型
.flags一组标记
.request产生Response类型对应的Request对象
.copy()复制该响应

Item类

class scrapy.item.Item()

  • Item对象表示一个从HTML页面中提取的信息内容。

  • 由Spider生成,由Item Pipeline处理。

  • Item类似字典类型,可以按照字典类型操作。

Scrapy爬虫提取信息的方法

Scrapy爬虫支持多种HTML信息提取方法

  • Beautiful Soup

  • lxml

  • re

  • XPath Selector

  • CSS Selector

CSS Selector的基本使用

<HTML>.css('a::attr(href) ').extract()
# a为标签名称
# href为标签属性

CSS Selector由W3C组织维护并规范

Scrapy性能优化

配置并发连接选项-settings.py文件

选项说明
CONCURRENT_REQUESTSDownloader最大并发请求下载数量,默认32
CONCURRENT_ITEMSItem Pipeline最大并发ITEM处理数量,默认100
CONCURRENT_REQUESTS_PER_DOMAIN每个目标域名最大的并发请求数量,默认8
CONCURRENT_REQUESTS_PER_IP毎个目标IP最大的并发请求数量,默认0,非0有效

更多方法可查询Scrapy文档中有关settings.py的内容


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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值