You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Scrapy多爬虫项目抽离数据处理与数据库操作的最佳实践咨询

Scrapy 多站点爬虫项目重构最佳实践

数据处理逻辑解耦方案

针对多站点规则差异大、处理函数零散的问题,采用按站点拆分独立ItemLoader的方案,完全避免所有逻辑堆积在items.py的情况:

  • 公共逻辑抽离复用
    把全项目通用的清洗规则(比如去HTML标签、去掉特殊空白符、统一日期格式化这类所有站点都会用到的逻辑)单独放到processors/common.py公共模块,所有站点都可以直接引用,无需重复开发。
  • 站点专属逻辑独立存放
    新增loaders目录,每个站点对应一个独立的Loader文件,站点专属的处理函数、字段输入输出处理器都放在对应Loader文件中,和其他站点完全隔离,修改单个站点规则不会影响其他业务。

参考目录结构:

your_project/
├── items.py # 仅存放统一的Item字段定义,不写任何处理逻辑
├── loaders/
│   ├── __init__.py
│   ├── common.py # 通用清洗函数
│   ├── taobao_loader.py # 淘宝站点专属Loader和处理函数
│   └── jd_loader.py # 京东站点专属Loader和处理函数
└── spiders/

站点专属Loader示例代码:

from scrapy.loader import ItemLoader
from itemloaders.processors import TakeFirst, MapCompose
from your_project.items import ProductItem
from your_project.loaders.common import remove_tags, trim_space

# 仅淘宝站点用到的价格处理函数,不会和其他站点逻辑混淆
def parse_taobao_price(value):
    return int(float(value.replace('¥', '').strip()) * 100)

class TaobaoProductLoader(ItemLoader):
    default_item_class = ProductItem
    default_output_processor = TakeFirst()

    title_in = MapCompose(remove_tags, trim_space)
    price_in = MapCompose(remove_tags, parse_taobao_price)

重构后爬虫代码和原有写法差异极小,只需替换对应Loader即可:

import scrapy
from your_project.loaders.taobao_loader import TaobaoProductLoader

class TaobaoSpider(scrapy.Spider):
    name = "taobao"
    start_urls = ["xxx"]

    def parse(self, response):
        loader = TaobaoProductLoader(selector=response)
        loader.add_xpath('title', "//title/text()")
        loader.add_xpath('price', "//div[@class='price']/text()")
        yield loader.load_item()

数据库操作解耦方案

直接使用Scrapy原生的Pipeline机制处理所有持久化逻辑,完全移除爬虫文件中的数据库操作:

  • 所有数据库增删改查逻辑都写到Pipeline中,爬虫只负责yield Item,不需要关心数据存储的任何细节,后续更换数据库、修改存储规则都只需要改Pipeline代码,无需调整爬虫逻辑。

Pipeline示例代码:

import pymysql
from your_project.items import ProductItem

class MySQLPipeline:
    def open_spider(self, spider):
        # 爬虫启动时初始化数据库连接
        self.conn = pymysql.connect(
            host='127.0.0.1',
            user='root',
            password='your_password',
            database='crawler',
            charset='utf8mb4'
        )
        self.cursor = self.conn.cursor()

    def process_item(self, item, spider):
        if isinstance(item, ProductItem):
            sql = "INSERT INTO product (title, price) VALUES (%s, %s)"
            self.cursor.execute(sql, (item['title'], item['price']))
            self.conn.commit()
        return item

    def close_spider(self, spider):
        # 爬虫关闭时释放连接
        self.cursor.close()
        self.conn.close()

写完后只需要在settings.py中开启该Pipeline即可生效,如需区分站点做不同的存储逻辑,只需在process_item方法中通过spider.name判断当前运行的爬虫即可。

重构后核心优势

  • 各层逻辑完全解耦:爬虫只负责页面解析取原始数据、Loader只负责数据清洗、Pipeline只负责持久化,哪部分出问题修改对应模块即可,互不影响
  • 维护成本大幅降低:站点专属逻辑独立存放,通用逻辑复用,不会出现大量零散函数堆积在同个文件的问题
  • 扩展效率高:新增站点只需要新增对应爬虫文件、专属Loader即可,公共逻辑直接复用,无需重复开发

内容的提问来源于stack exchange,提问作者Xus

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.28 06:15:04