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

Scrapy爬取谷歌专利数据时如何将重复化学品的专利号追加到MongoDB数组

解决方案

问题原因

你当前的Pipeline逻辑是每爬取一页搜索结果就直接向MongoDB插入一条新记录,所以同一化学品多页结果会生成多条chemical字段重复的记录,每页仅存储对应当页的公开号。

修改方案

仅需要调整pipelines.py中的process_item方法,使用MongoDB的upsert(存在则更新,不存在则插入)操作即可实现需求,同时还可自动对公开号去重:

修改后的pipelines.py代码

import pymongo
from itemadapter import ItemAdapter

class PattentsPipeline(object):
    collection_name = 'items'

    def __init__(self, mongo_uri, mongo_db):
        self.mongo_uri = mongo_uri
        self.mongo_db = mongo_db

    @classmethod
    def from_crawler(cls, crawler):
        return cls(
            mongo_uri=crawler.settings.get('MONGO_URI'),
            mongo_db=crawler.settings.get('MONGO_DATABASE', 'items')
        )

    def open_spider(self, spider):
        self.client = pymongo.MongoClient(self.mongo_uri)
        self.db = self.client[self.mongo_db]
        # 可选优化:给chemical字段加唯一索引,避免并发场景下重复插入
        self.db[self.collection_name].create_index('chemical', unique=True)

    def close_spider(self, spider):
        self.client.close()

    def process_item(self, item, spider):
        item_data = ItemAdapter(item).asdict()
        self.db[self.collection_name].update_one(
            # 查询条件:匹配相同化学品的记录
            {'chemical': item_data['chemical']},
            # 更新操作:往publication_number数组追加新公开号,自动去重
            {
                '$addToSet': {
                    'publication_number': {
                        '$each': item_data['publication_number']
                    }
                }
            },
            # 没有匹配记录时自动插入新记录
            upsert=True
        )
        return item

操作说明

  • $addToSet:MongoDB内置操作符,往数组中添加元素时自动跳过已存在的元素,避免公开号重复
  • $each:支持一次性传入数组批量添加多个元素,适配单页返回多个公开号的场景
  • upsert=True:开启更新插入模式,完全匹配“存在则追加、不存在则新增”的需求

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.06 22:27:04