使用Scrapy连续捕获嵌套页面中的数据

问题描述 投票:0回答:1

我正在尝试使用 Scrapy BaseSpider 抓取一个相当简单的网站,因为我事先知道我想要抓取的所有链接在哪里。

待抓取网站的基本布局是

  1. 国家列表
  2. 州内县列表
  3. 县内机构列表
  4. 有关单个机构的信息

我可以成功导航并获取所有 4 个级别的数据,但是,我的县字段未正确填充。对于给定的机构,我获取的是该机构所在州的最后一个县,而不是其实际所在的县。

示例:

  • OH - 县#3 - 机构#1(应为县#1
  • OH - 县#3 - 机构#2(应为县#2
  • OH - 县#3 - 机构#3(正确)

似乎无法弄清楚我认为相对简单的东西。

这是代码:

from scrapy.spider import BaseSpider
from scrapy.selector import Selector
from agencyspider.items import AgencyItem
from scrapy.http import Request

class BasicspiderSpider(BaseSpider):
    name = "basicSpider"
    allowed_domains = ["usacops.com"]
    start_urls = [
        'http://www.usacops.com/',
        ]

    items = {}

    def parse(self, response):
        sel = Selector(response)
        states = sel.xpath('//comment()[.=" Begin State Names "]/following::table[1]/tr/td/a')
        for s in states:
            item = AgencyItem()
            state = s.xpath('text()').extract()[0]
            url = s.xpath('@href').extract()[0]
            item['state'] = state
            item['stateUrl']= url
            yield Request(url=url,callback=self.parse_counties,meta={'item':item})


    def parse_counties(self, response):
        sel = Selector(response)
        counties = sel.xpath('//comment()[.=" Begin Counties "]/following::table[1]/tr/td/font/a | //comment()[.=" Begin Counties "]/following::table[1]/tr/td/a')
        for c in counties:
            item = response.request.meta["item"]
            county = c.xpath('text()').extract()[0]
            countyUrl = c.xpath('@href').extract()[0]
            url = item["stateUrl"] + countyUrl
            item["county"]=county
            item["countyUrl"]=url
            yield Request(url=url, callback=self.parse_agencies,meta={'item':item})

    def parse_agencies(self,response):
        sel = Selector(response)
        agencies = sel.xpath('//table[9]/tr/td/table[2]/tr/td/font/a | //table[9]/tr/td/table[2]/tr/td/a')
        for a in agencies:
            item = response.request.meta["item"]
            agency = a.xpath('text()').extract()[0]
            agencyUrl = a.xpath('@href').extract()[0]
            url =  item["stateUrl"] + agencyUrl
            item["agency"] = agency
            item["agencyUrl"] = url 
            yield Request(url=url, callback=self.parse_agencyinfo,meta={'item':item})

    def parse_agencyinfo(self,response):
        sel = Selector(response)        
        item = response.request.meta["item"]
        item["agency"]= ' '.join(sel.xpath('//comment()[.=" Begin center section "]/following::table/tr/td/strong/font[1]/text()').extract())
        item["admintype"]= ' '.join(sel.xpath('//comment()[.=" Begin center section "]/following::table/tr/td/strong/font[2]/text()').extract())
        item["adminhead"]= ' '.join(sel.xpath('//comment()[.=" Begin center section "]/following::table/tr/td/strong/font[3]/text()[1]').extract())
        item["address"]= ' '.join(sel.xpath('//comment()[.=" Begin center section "]/following::table/tr/td/strong/font[3]/text()[position()>1]').extract())
        return item
scrapy
1个回答
3
投票

嘿,问题是每次您分配

item = response.request.meta["item"]
时,您都会一遍又一遍地引用和分配相同的项目。

幸运的是,它很容易解决!只需用

response.request.meta["item"]
包裹
AgencyItem(response.request.meta["item"])
即可为每个县创建州项目的 copy

也不要忘记在其他回调中执行相同的操作,否则您将在其他字段中遇到问题。希望有帮助!

© www.soinside.com 2019 - 2024. All rights reserved.