【爬虫】从零开始使用 Scrapy

一. 概述

最近有一个爬虫相关的需求,需要使用 scrapy 框架来爬取数据,所以学习了一下这个非常强大的爬虫框架,这里将自己的学习过程记录下来,希望对有同样需求的小伙伴提供一些帮助。

本文主要从下面几个方面进行介绍:

  • 我的学习过程
  • 需求分析
  • 搭建项目
  • 编写代码实现需求
  • 部署爬虫项目到 SpiderKeeper

二. 我的学习过程

学习一个新的技术,首先就是去阅读它的官方文档,因为官方文档写的是比较全面的而且权威。

scrapy 官方文档地址https://docs.scrapy.org/en/latest/

上面是 scrapy 的官方文档地址,文档是英文的,如果英文比较好建议直接看英文文档,其实自己的英语也不是很好,但是一直强迫自己看英文文档,遇到不认识的单词,就是用 chrome 的 一个叫做 沙拉查词 的插件翻译,翻译完就记下这些单词,慢慢的读这些英文技术文档就没有太大问题了。

如果学习的时间比较充足,可以看完整个文档再进行实践开发,如果需要快速上手,可以看文档中的快速开始。因为自己在开发需求之前有空闲的时间,所以把它的文档看了七七八八。

Scrapy 简介

下面根据自己阅读官方文档的过程做一个总结:

Scrapy 是一个快速强大的高级 web 抓取框架,用于抓取网站和从网页中提取结构化数据,它可以用于从数据挖掘到监控和自动化测试等广泛的用途。

Scrapy 提供了许多强大的功能来使抓取变得简单高效,例如:

  • 内置支持使用扩展的 CSS 选择器和 XPath 表达式从 HTML/XML 源中选择和提取数据,以及使用正则表达式提取的辅助方法。
  • 一个交互式 shell 控制台(IPython 感知),用于尝试使用 CSSXPath 表达式来抓取数据,在编写或调试时非常有用。
  • 内置支持以多种格式(JSON、CSV、XML生成提要导出并将它们存储在多个后端(FTP、S3、本地文件系统)
  • 强大的编码支持和自动检测,用于处理外部、非标准和损坏的编码声明。
  • 强大的可扩展性支持,允许您使用signals和定义良好的 API(中间件、扩展 pipeline )插入自己的功能。
  • 一个Telnet 控制台,用于连接到在 Scrapy 进程中运行的 Python 控制台,以检查和调试您的爬虫
  • 可重复使用的spider从站点地图XML/CSV 提要中抓取站点、用于自动下载与抓取的项目相关联的图像(或任何其他媒体)的媒体 pipeline 、缓存 DNS 解析器等等!
  • 用于处理的各种内置扩展和中间件:
    • cookie 和会话处理
    • HTTP 功能,如压缩、身份验证、缓存
    • 用户代理欺骗
    • robots.txt
    • 爬行深度限制

从前面的介绍可以看出 scrapy 的功能非常强大,如果要掌握全部功能,需要花费大量的时间,并且也没有那个必要,只是需要的时候再去查阅官方文档即可。对于一般的网站都没有特别的反爬虫措施,除非一些数据比较敏感的网站,可能需要输入图形验证码之类的,个人觉得对于一般的网站,在抓取网页的过程中合理设置请求头,控制爬取的速度都能够将网页抓取下来。获取到网页内容之后,我们开发的内容就是根据需求解析出需要的结构化数据,所以重点是掌握 scrapy 的选择器。

Scrapy 选择器

scrapy 使用的选择器包括如下:

  • css 选择器
  • xpath 选择器
  • 正则表达式提取

XPath 表达式非常强大,是 Scrapy 选择器的基础,事实上,CSS 选择器在后台被转换为 XPath。虽然可能不如 CSS 选择器流行,但 XPath 表达式提供了更强大的功能,因为除了导航结构之外,它还可以查看内容。使用 XPath 您可以选择以下内容:选择包含文本“下一页”的链接,这使得 XPath 非常适合抓取任务。

XPath 常用规则

表达式 描述
nodename 选取此节点的所有子节点
/ 从当前节点选区直接子节点
// 从当前节点选取子孙节点
. 选取当前节点
.. 选取当前节点的父节点
@ 选取属性
text() 获取节点中的文本

三. 需求分析

通过前面的介绍我们大概了解了 Scrapy 的特性,接下来,自己模拟一个实际的需求,该需求是在网上找的,只是用来学习 Scrapy 的一个 demo,需求如下:

目标网站:站长之家 https://top.chinaz.com/

需求:在站长之家的网站排行板块中,提供了行业排名、地区排名等多种分类网站排行数据。现在请你任选一种感兴趣的排名方式,摘取其中的数据。

image-20220107145943621

字段要求,一共5个字段,分别是:

  • 网站名称:web_name
  • 网站域名:domain
  • 排名:rank
  • 得分:score
  • 网站简介:abstract

技术要求:使用 scrapy 编写爬虫,最终将提取到的数据存到 mongodb 中;

四. 搭建项目

前面已经介绍了需求,现在我们开始从零搭建一个 scrapy 的项目,因为 scrapy 是使用 python 开发的,所以需要提前安装 python 的环境,推荐使用 Anaconda,关于 Anaconda 的安装可以查阅其官方文档,这里默认已经安装好了。

1. 安装 scrapy

CMD 控制台使用如下命令安装 scrapy :

pip install scrapy

安装完成后输入 scrapy 可以看到如下输出:

D:\my-projects>scrapy
Scrapy 2.5.1 - no active project

Usage:
  scrapy <command> [options] [args]

Available commands:
  bench         Run quick benchmark test
  check         Check spider contracts
  commands
  crawl         Run a spider
  edit          Edit spider
  fetch         Fetch a URL using the Scrapy downloader
  genspider     Generate new spider using pre-defined templates
  list          List available spiders
  parse         Parse URL (using its spider) and print the results
  runspider     Run a self-contained spider (without creating a project)
  settings      Get settings values
  shell         Interactive scraping console
  startproject  Create new project
  version       Print Scrapy version
  view          Open URL in browser, as seen by Scrapy

Use "scrapy <command> -h" to see more info about a command

2. 创建项目

语法:scrapy startproject <project_name> [project_dir]

project_dir 目录下创建一个名为 <project_name> 的新 Scrapy 项目,如果 project_dir 未指定,表示当前目录。

项目名只能使用数字、字母、下划线组成

使用如下命令创建一个叫做 scrapy_demo 的项目:

scrapy startproject scrapy_demo

输出内容如下:

D:\my-projects>scrapy startproject scrapy_demo
New Scrapy project 'scrapy_demo', using template directory 'e:\anaconda3\lib\site-packages\scrapy\templates\project', created in:
    D:\my-projects\scrapy_demo

You can start your first spider with:
    cd scrapy_demo
    scrapy genspider example example.com

自动生成的项目目录结构如下:

scrapy_demo
├── scrapy_demo
│   ├── items.py       # 数据模型文件
│   ├── middlewares.py # 中间件文件,配置所有中间件
│   ├── pipelines.py   #  pipeline 文件,用于存放自定义pipeline的处理逻辑,比如配置保存数据库的逻辑
│   ├── settings.py    # 项目的配置文件,自定义的外部配置都可以放在这里
│   └── spiders        # Spider类文件夹,我们编写的解析代码均存放在这里
└── scrapy.cfg         # 项目的部署配置文件

3. 生成 spider 文件

语法:scrapy genspider [-t template] <name> <domain>

如果在 scrapy 项目中调用,将在当前项目的 spiders 文件夹中创建一个新的 spider 文件,该<name>参数设置为 spider 的name,而<domain>用于生成allowed_domains start_urls 的属性值。

执行下面的命令,生成 spider 文件:

scrapy genspider tech_web top.chinaz.com

输出内容如下:

D:\my-projects\scrapy_demo>scrapy genspider tech_web top.chinaz.com
Created spider 'tech_web' using template 'basic' in module:
  scrapy_demo.spiders.tech_web

生成的 spider 文件内容如下图所示:

image-20220107155030530

五. 代码实现

按照前面的步骤,我们已经完成项目的搭建,接下来开始正式实现需求。

1. 在 items.py 文件中定义采集的字段

前面已经知道要采集的字段,所以我们需要在 items.py 文件中定义采集的字段以及一些其他需要的字段,如下所示:

# Define here the models for your scraped items
#
# See documentation in:
# https://docs.scrapy.org/en/latest/topics/items.html

import scrapy


class ScrapyDemoItem(scrapy.Item):
    # define the fields for your item here like:
    # name = scrapy.Field()
    _id = scrapy.Field()  # 保存到 mongodb 中的 _id
    web_name = scrapy.Field()  # 网站名称
    domain = scrapy.Field()  # 网站域名
    rank = scrapy.Field()  # 排名
    score = scrapy.Field()  # 得分
    abstract = scrapy.Field()  # 摘要
    create_time = scrapy.Field()  # 创建时间
    update_time = scrapy.Field()  # 更新时间

2. 在 spider 文件中编写采集逻辑

我们这里打算采集网络科技网站排行榜,它的地址为:https://top.chinaz.com/hangye/index_wangluo.html,在正式编写代码之前,我们可以使用 scrapy 提供的 shell 工具进行测试,通过交互式的方式解析需要的字段,使用方式如下:

语法: scrapy shell [url]

scrapy shell https://top.chinaz.com/hangye/index_wangluo.html --nolog

如果使用上面的命令输出如下:

D:\my-projects\scrapy_demo>scrapy shell https://top.chinaz.com/hangye/index_wangluo.html --nolog
[s] Available Scrapy objects:
[s]   scrapy     scrapy module (contains scrapy.Request, scrapy.Selector, etc)
[s]   crawler    <scrapy.crawler.Crawler object at 0x0000011BEAE84748>
[s]   item       {}
[s]   request    <GET https://top.chinaz.com/hangye/index_wangluo.html>
[s]   response   <200 https://top.chinaz.com/hangye/index_wangluo.html>
[s]   settings   <scrapy.settings.Settings object at 0x0000011BEB0F1B88>
[s]   spider     <TechWebSpider 'tech_web' at 0x11beb538488>
[s] Useful shortcuts:
[s]   fetch(url[, redirect=True]) Fetch URL and update local objects (by default, redirects are followed)
[s]   fetch(req)                  Fetch a scrapy.Request and update local objects
[s]   shelp()           Shell help (print this help)
[s]   view(response)    View response in a browser
In [1]: 
 

此时你可以使用 response.text 来检查我们是否获取了整个页面的源码,scrapy的所有资源解析操作都被集成在了response这个对象中,使用 Tab 建可以提示补全相关的内容。

接下来我们可以在浏览器中分析需要抓取的页面的信息

image-20220107163221087

解析网页的 spider 代码如下:

import datetime
from hashlib import md5
import scrapy
from scrapy_demo.items import ScrapyDemoItem


class TechWebSpider(scrapy.Spider):
    name = 'tech_web'
    allowed_domains = ['top.chinaz.com']
    url = 'https://top.chinaz.com/hangye/index_wangluo_{}.html'
    pagesize = 1
    start_urls = ['https://top.chinaz.com/hangye/index_wangluo.html']

    def parse(self, response):
        li_list = response.xpath('//ul[@class="listCentent"]/li')
        for li in li_list:
            web_name = li.xpath('.//h3/a/text()').get()
            domain = li.xpath('.//h3/span/text()').get()
            abstract = li.xpath('.//div[@class="CentTxt"]/p/text()').get(default='')
            rank = li.xpath('.//div[@class="RtCRateCent"]/strong/text()').get(default='')
            score = li.xpath('.//div[@class="RtCRateCent"]/span/text()').get(default='')
            # 封装数据
            item = ScrapyDemoItem()
            date = datetime.datetime.now()
            item['_id'] = md5(str(web_name).encode('utf-8')).hexdigest()
            item['web_name'] = web_name
            item['domain'] = domain
            item['abstract'] = abstract
            item['rank'] = rank
            item['score'] = score
            item['create_time'] = date
            item['update_time'] = date
            yield item
        # 构造下一页的请求
        self.pagesize = self.pagesize + 1
        url = self.url.format(self.pagesize)
        if len(li_list) > 0:
            yield scrapy.Request(url=url, callback=self.parse)

Spider parse方法:所有的parse方法都必须返回 Item 对象(目前可以理解为数据项)或者 Request 对象(下一条请求)。这里所有的parse的意思是不是特指Spider类中生成的parse方法,而是所有具备解析功能的函数都应该返回 Item 或者 Request。

启动 spider :

语法:scrapy crawl <spider>

其中的 <spider> 是我们 spider 文件中 name 属性的值,我们在 scrapy 项目中可以通过 scrapy list 命令查看,如下所示:

D:\my-projects\scrapy_demo>scrapy list
tech_web

所以我们可以使用下面的命令启动我们创建的这个 spider :

scrapy crawl tech_web

那么现在有一个问题是我需要将数据保存应该如何做呢?

Scrapy 提供了许多Feed exports的方法,可以将输出数据保存为json, json lines, csv, xml

在启动命令后面加 -o xx.json 就可以将文件保存为json格式。

例如使用如下命令将抓取的数据保存到一个 json 文件中:

scrapy crawl tech_web -o result.json

打开保存的 json 文件,发现出现了乱码,出于历史原因,JSON 输出使用安全数字编码(\uXXXX序列),如果想要 UTF-8 用于 JSON,请使用 FEED_EXPORT_ENCODING = 'utf-8'。官方文档对该字段的说明如下:

image-20220107174023299

3. 保存数据到 mongodb

前面我们介绍了如何将采集的结构化数据保存到 json 文件中,下面将介绍如何将采集的数据保存到 mongodb 中,保存到其他数据库也是类似的。

首先由于我们需要保存数据到 mongodb 中,所以这里先用 docker 部署一个 mongodb 数据库,如果已经有了 mongodb 数据库,就不需要这个操作。

docker 部署 mongodb 地址:https://hub.docker.com/r/bitnami/mongodb

使用下面的命令启动一个 mongodb 数据库:

docker run --name mongodb  -e MONGODB_ROOT_PASSWORD=password123 -p 27017:27017  bitnami/mongodb:latest

其次需要介绍一下 scrapypipeline ,在每一个item 被抓取之后,都会被发送到 pipeline 中,每个 pipeline 都是一个实现简单方法的 python 类,

它们接收一个 item 并对其执行操作,同时决定该 item 是应该继续进入下一个 pipeline 还是被丢弃不再处理。

pipeline 的典型用途如下:

  • 清洗 HTML 数据
  • 验证抓取的数据(检查项目是否包含某些字段)
  • 检查重复项(并删除它们)
  • 将抓取的项目存储在数据库中

编写自己的 pipeline

每个 pipeline 组件都是一个必须实现 process_item 方法的 Python 类:

此外,它们还可以实现以下方法:

  • open_spider(self,spider)

    这个方法在 spider 打开时被调用。参数spider– 打开的 spider

  • close_spider(self,spider)

    当 spider 关闭时调用此方法。参数 spider – 关闭的spider

  • from_crawler ( cls , crawler )

    如果存在,必须返回 pipeline 的新实例,通常在这个方法中传入一些外部配置,构造一个新的 pipeline 实例。Crawler 对象提供对所有 Scrapy 核心组件的访问,如 settings 和 signals ;这是 pipeline 访问它们并将其功能挂钩到 Scrapy 的一种方式。参数crawler ( Crawlerobject) – 使用这个 pipeline 的爬虫。

知道了 pipeline 的作用和定义方法后,我们定义一个保存数据到 mongodbpipeline ,如下所示:

# Define your item pipelines here
#
# Don't forget to add your pipeline to the ITEM_PIPELINES setting
# See: https://docs.scrapy.org/en/latest/topics/item-pipeline.html


# useful for handling different item types with a single interface
from itemadapter import ItemAdapter
import pymongo


class ScrapyDemoPipeline:
    def process_item(self, item, spider):
        return item


class SaveToMongoPipeline:
    
    def __init__(self, mongo_uri, mongo_db, collection):
        self.mongo_uri = mongo_uri
        self.mongo_db = mongo_db
        self.collection = collection

    @classmethod
    def from_crawler(cls, crawler):
        # 从 settings.py 文件中读取对应的配置
        env = crawler.settings.get('ENV', 'local')
        config = crawler.settings.get('CONFIG')
        config = config[env]
        mongo_uri = config.MONGO_URI
        mongo_db = config.MONGODB_DB
        collection = config.COLLECTION_NAME
        # 返回当前 pipeline 的实例,传入从 settings 中读取的配置
        return cls(
            mongo_uri=mongo_uri,
            mongo_db=mongo_db,
            collection=collection,
        )

    def open_spider(self, spider):
        """
        打开 spider 的时候调用一次,可以在这里创建数据的连接
        """
        self.client = pymongo.MongoClient(self.mongo_uri)
        self.db = self.client[self.mongo_db]

    def process_item(self, item, spider):
        """
        每一个 item 都会调用这个方法,可以在这里清洗数据,并保存到数据库
        """
        adapter = ItemAdapter(item)
        coll = self.db[self.collection]
        # 使用 ItemAdapter 的 asdict() 方法可以处理嵌套的 item 格式,获取 json 字符串
        doc = adapter.asdict()
        count = coll.find({'_id': doc.get('_id')}).count()
        if count == 0:
            coll.insert_one(doc)
        else:
            del doc['create_time']
            coll.update_one({"_id": doc.get('_id')}, {'$set': doc})
        return item

    def close_spider(self, spider):
        """
        spider 关闭的时候调用一次,可以在这里关闭数据库连接,释放资源
        """
        self.client.close()

如果要让自己的 pipeline 生效, 需要配置在 settings.py 文件中,如下所示:

# Configure item pipelines
# See https://docs.scrapy.org/en/latest/topics/item-pipeline.html
ITEM_PIPELINES = {
   'scrapy_demo.pipelines.ScrapyDemoPipeline': 300,
   'scrapy_demo.pipelines.SaveToMongoPipeline': 400,
}

ITEM_PIPELINES 是一个字典,它的 keypipeline 的类路径,它的值是一个数字, 这个数字决定了 pipeline 的执行顺序,它的执行顺序为从低到高,数字越大越后执行,自定义的数字范围为 0 - 1000

上述的pipeline 中的 from_crawler 方法使用了 settings 中配置的 mongodb 的地址,settings.py 文件的配置如下所示:

# Scrapy settings for scrapy_demo project
#
# For simplicity, this file contains only settings considered important or
# commonly used. You can find more settings consulting the documentation:
#
#     https://docs.scrapy.org/en/latest/topics/settings.html
#     https://docs.scrapy.org/en/latest/topics/downloader-middleware.html
#     https://docs.scrapy.org/en/latest/topics/spider-middleware.html

BOT_NAME = 'scrapy_demo'

SPIDER_MODULES = ['scrapy_demo.spiders']
NEWSPIDER_MODULE = 'scrapy_demo.spiders'

FEED_EXPORT_ENCODING = 'utf-8'

# Crawl responsibly by identifying yourself (and your website) on the user-agent
USER_AGENT = 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/96.0.4664.45 Safari/537.36'

# Obey robots.txt rules
ROBOTSTXT_OBEY = False

# Override the default request headers:
DEFAULT_REQUEST_HEADERS = {
    'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9',
    'Accept-Encoding': 'gzip, deflate, br',
    'Accept-Language': 'zh-CN,zh;q=0.9,en;q=0.8',
    'Connection': 'keep-alive',
    'User-Agent': USER_AGENT
}

# Configure item pipelines
# See https://docs.scrapy.org/en/latest/topics/item-pipeline.html
ITEM_PIPELINES = {
    'scrapy_demo.pipelines.ScrapyDemoPipeline': 300,
    'scrapy_demo.pipelines.SaveToMongoPipeline': 400,
}


class LocalConfig:
    # 本地环境mongeDB地址
    MONGODB_HOST = 'localhost:27017'
    MONGODB_USERNAME = 'root'
    MONGODB_PASSWORD = 'password123'
    MONGODB_DB = 'admin'
    COLLECTION_NAME = 'tech_web'
    MONGO_URI = "mongodb://{username}:{password}@{server}/{database}". \
        format(username=MONGODB_USERNAME, password=MONGODB_PASSWORD, server=MONGODB_HOST, database=MONGODB_DB)


class DevelopmentConfig:
    # 开发环境mongeDB地址
    MONGODB_HOST = 'localhost:27017'
    MONGODB_USERNAME = 'root'
    MONGODB_PASSWORD = 'password123'
    MONGODB_DB = 'admin'
    COLLECTION_NAME = 'tech_web'
    MONGO_URI = "mongodb://{username}:{password}@{server}/{database}". \
        format(username=MONGODB_USERNAME, password=MONGODB_PASSWORD, server=MONGODB_HOST, database=MONGODB_DB)


CONFIG = {
    'local': LocalConfig,
    'dev': DevelopmentConfig,
}

ENV = 'local'

编写完成后运行下面的命令就可以启动 spider:

scrapy crawl tech_web

可以看到数据保存到 mongodb 中了:

image-20220107201532414

六. 部署爬虫项目到 SpiderKeeper

前面介绍了使用命令 scrapy crawl <name> 来运行 spider ,如果我们想要定时运行这些爬虫任务应该怎么做呢?

  • 如果运行在Linux系统中,可以使用 crontab 来执行定时任务
  • 可以使用 python 的定时库 apscheduler ,通过手动编程的方式执行定时任务
  • 使用 scrapy 的可视化管理工具 SpiderKeeper

接下来将介绍部署 scrapy 项目到 SpiderKeeper,部署 scrapy 项目到 SpiderKeeper 需要安装两个 python 库:

  • spiderkeeper
  • scrapyd

1. SpiderKeeper 简介

SpiderKeeper 的源码地址:https://github.com/DormyMo/SpiderKeeper

SpiderKeeperspider 服务的可扩展管理 ui,包括如下功能:

  • 从仪表板管理 spider ,并且调度它们自动运行

  • 只需单击一次,即可部署 scrapy 项目

  • 显示 spider 运行统计信息

  • 提供 api

spiderkeeper 目前只支持 scrapyd 方式运行的 scrapy 项目的管理,所以在安装 spiderkeeper 之前需要先安装 scrapyd

2. Scrapyd 简介

Scrapyd 的源码地址:https://github.com/scrapy/scrapyd

Scrapyd 是运行 scrapy 项目的一个守护服务,它允许你部署 scrapy 项目,并且可以使用 http json api 的方式控制 scrapyspider

3. 安装 spiderkeeper

使用下面的命令安装 scrapyd

pip install scrapyd

使用下面的命令启动 scrapydscrapyd 默认运行在 6800 端口,如下所示:

>scrapyd
2022-01-09T10:24:19+0800 [-] Loading e:\anaconda3\lib\site-packages\scrapyd\txapp.py...
2022-01-09T10:24:20+0800 [-] Scrapyd web console available at http://127.0.0.1:6800/
2022-01-09T10:24:20+0800 [-] Loaded.
2022-01-09T10:24:20+0800 [twisted.application.app.AppLogger#info] twistd 21.7.0 (e:\anaconda3\python.exe 3.7.6) starting up.
2022-01-09T10:24:20+0800 [twisted.application.app.AppLogger#info] reactor class: twisted.internet.selectreactor.SelectReactor.
2022-01-09T10:24:20+0800 [-] Site starting on 6800
2022-01-09T10:24:20+0800 [twisted.web.server.Site#info] Starting factory <twisted.web.server.Site object at 0x000001DA664F3C88>
2022-01-09T10:24:20+0800 [Launcher] Scrapyd 1.2.1 started: max_proc=16, runner='scrapyd.runner'

使用下面的命令安装 spiderkeeper

pip install spiderkeeper

使用下面的命令启动 spiderkeeper,默认运行在 5000 端口,如下所示:

>spiderkeeper
--------------------------------------------------------------------------------
INFO in run [e:\anaconda3\lib\site-packages\SpiderKeeper\run.py:22]:
SpiderKeeper startd on 0.0.0.0:5000 username:admin/password:admin with scrapyd servers:http://localhost:6800
--------------------------------------------------------------------------------
2022-01-09 10:27:24,828 - SpiderKeeper.app - INFO - SpiderKeeper startd on 0.0.0.0:5000 username:admin/password:admin with scrapyd servers:http://localhost:6800

spiderkeeper 的其他配置说明如下:


spiderkeeper [options]

Options:

  -h, --help            show this help message and exit
  --host=HOST           host, default:0.0.0.0
  --port=PORT           port, default:5000
  --username=USERNAME   basic auth username ,default: admin
  --password=PASSWORD   basic auth password ,default: admin
  --type=SERVER_TYPE    access spider server type, default: scrapyd
  --server=SERVERS      servers, default: 'http://localhost:6800'
  --database-url=DATABASE_URL
                        SpiderKeeper metadata database default: sqlite:////home/souche/SpiderKeeper.db
  --no-auth             disable basic auth
  -v, --verbose         log level
  

example:

spiderkeeper --server=http://localhost:6800

启动完成 spiderkeeper 后,在浏览器访问:http://localhost:5000,可以看到如下所示页面:

默认用户名和密码都为:admin

image-20220109103152935

登录成功后可以看到如下所示页面:

image-20220109103307504

点击创建一个项目:

image-20220109103406400

可以看到如下部署页面:

image-20220109103452704

scrapy 项目中使用命令 scrapyd-deploy --build-egg output.egg 生成部署文件,并上传,即可完成 scrapy 项目的部署。

使用下面的命令生成部署文件:

>scrapyd-deploy --build-egg output.egg
Writing egg to output.egg

将前面的 scrapy 项目生成的 output.egg 上传到 spiderkeeper 中:

image-20220109103902307

点击 Dashboard --> 点击 Run --> 选择需要运行的 spiderspiderkeeper 会自动识别 spider 中 name 的名称:

image-20220109104314079

如果要创建定时任务,如下图所示:

image-20220109104510161

七. 总结

这篇文章简单记录自己学习 scrapy 的过程,包括从创建项目到部署项目的完整流程,很多细节并没有详细介绍,更多内容可以查看文章中列出的官方文档。

本文作者:blogwd

本文链接:https://www.cnblogs.com/blogwd/p/15780478.html

版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。

posted @   blogwd  阅读(455)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· DeepSeek “源神”启动!「GitHub 热点速览」
· 微软正式发布.NET 10 Preview 1:开启下一代开发框架新篇章
· C# 集成 DeepSeek 模型实现 AI 私有化(本地部署与 API 调用教程)
· DeepSeek R1 简明指南:架构、训练、本地部署及硬件要求
· 2 本地部署DeepSeek模型构建本地知识库+联网搜索详细步骤
点击右上角即可分享
微信分享提示
💬
评论
📌
收藏
💗
关注
👍
推荐
🚀
回顶
收起
  1. 1 不要说话 REOL
  2. 2 这世界那么多人 REOL
  3. 3 盛夏的果实 REOL
这世界那么多人 - REOL
00:00 / 00:00
An audio error has occurred, player will skip forward in 2 seconds.

作词 : 王海涛

作曲 : Akiyama Sayuri

编曲 : 彭飞

制作人 : 荒井十一/彭飞

这世界有那么多人

人群里 敞着一扇门

我迷朦的眼睛里长存

初见你 蓝色清晨

这世界有那么多人

多幸运 我有个我们

这悠长命运中的晨昏

常让我 望远方出神

灰树叶飘转在池塘

看飞机轰的一声去远乡

光阴的长廊 脚步声叫嚷

灯一亮 无人的空荡

晚风中闪过 几帧从前啊

飞驰中旋转 已不见了吗

远光中走来 你一身晴朗

身旁那么多人 可世界不声 不响

这世界有那么多人

多幸运 我有个我们

这悠长命运中的晨昏

常让我 望远方出神

灰树叶飘转在池塘

看飞机轰的一声去远乡

光阴的长廊 脚步声叫嚷

灯一亮 无人的空荡

晚风中闪过 几帧从前啊

飞驰中旋转 已不见了吗

远光中走来 你一身晴朗

身旁那么多人 可世界不声 不响

笑声中浮过 几张旧模样

留在梦田里 永远不散场

暖光中醒来 好多话要讲

世界那么多人 可是它不声 不响

这世界有那么个人

活在我 飞扬的青春

在泪水里浸湿过的长吻

常让我 想啊想出神

弦乐 : 彭飞

吉他 : 胡洋

曼陀林 : 彭飞

鼓 : 荒井十一

录音室 : Studio 21A

录音师 : 倪涵文

混音室 : Studio 21A

混音师 : 周天澈

母带工程师 : 周天澈