首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何抓取子页面并将其与页面信息合并?

如何抓取子页面并将其与页面信息合并?
EN

Stack Overflow用户
提问于 2021-05-26 22:57:13
回答 1查看 54关注 0票数 0

我使用scrapy来解析页面。该页面具有子页面(类别),我还需要从这些子页面获取信息并将其组合到一个元素中(可能会将来自其他页面的信息保存为json),并将其添加到csv中。我尝试过不同的选项,例如:

代码语言:javascript
复制
requests = scrapy.Request(url, meta={'meta_item': item}, callback=self.parse_category)

代码语言:javascript
复制
yield scrapy.Request(url, meta={'meta_item': item}, callback=self.parse_category)

但是,这两种方法都不能按我希望的方式工作。

例如,我从https://www.webscorer.com/findraces?pg=results (示例:https://www.webscorer.com/seriesresult?seriesid=211565 )获取页面,并从该页面获取信息。之后,我需要从category (例如:https://www.webscorer.com/seriesresult?seriesid=211565&gender=F ):example中获取其他信息,并将它们全部放入csv中。现在是我的代码:

代码语言:javascript
复制
class WebscorerSpider(scrapy.Spider):
name = 'webscorer'
allowed_domains = ['webscorer.com']

def start_requests(self):
    url = f'https://www.webscorer.com/findraces?pg=results'
    yield scrapy.Request(url, callback=self.parse_page)

def parse_page(self, response, **kwargs):
    for href in response.css('table.results-table tbody tr a::attr("href")').extract():
        url = response.urljoin(href)
        url = 'https://www.webscorer.com/seriesresult?seriesid=211565'
        yield scrapy.Request(url, callback=self.parse)

def parse(self, response: Response, **kwargs):
    latlong_match = re.search('lat=(.*)&lng=(.*)', response.css('span#FSrc::text').get())
    item = dict()

    for href in response.css('table.category-table .category-name').css('a::attr("href")').extract():
        url = response.urljoin(href)

        # requests = scrapy.Request(url, meta={'meta_item': item}, callback=self.parse_category)

        yield scrapy.Request(url, meta={'meta_item': item}, callback=self.parse_category)

    yield WebscorerEvent(name=response.css('h1.race-name::text').get(),
                         source_url=response.request.url,
                         sport_discipline=response.css('td.spec+td').css('strong::text').get(),
                         description=response.css('span.regnotes span::text').get(),
                         hero_image=response.css('p.associated-race-pic img::attr(src)').get(),
                         start_date=parse_webscorer_date(response.css('p.race-date::text').get()),
                         location={
                              "link": f"https://www.google.com/maps/search/?api=1&query={latlong_match.group(1)},{latlong_match.group(2)}",
                              "description": response.css('td.spec:contains("Location:")+td strong::text').get()})

def parse_category(self, response, **kwargs):
    item = response.meta['meta_item']
    # print(item)
    item['winner'] = response.css('table.results-table .r-racername span::text').get()

    return item
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2021-05-30 01:01:11

您使用了yield WebscorerEvent,所以在获取下一页所需的数据之前,您已经“丢弃”了该项。

你可以这样做:

代码语言:javascript
复制
def parse(self, response: Response, **kwargs):
    latlong_match = re.search('lat=(.*)&lng=(.*)', response.css('span#FSrc::text').get())
    item = {
        "name": response.css('h1.race-name::text').get(),
        "source_url": response.request.url,
        "sport_discipline": response.css('td.spec+td').css('strong::text').get(),
        "description": response.css('span.regnotes span::text').get(),
        "hero_image": response.css('p.associated-race-pic img::attr(src)').get(),
        "start_date": parse_webscorer_date(response.css('p.race-date::text').get()),
        "location": {
            "link": f"https://www.google.com/maps/search/?api=1&query={latlong_match.group(1)},{latlong_match.group(2)}",
            "description": response.css('td.spec:contains("Location:")+td strong::text').get()
        }
    }

    for href in response.css('table.category-table .category-name').css('a::attr("href")').extract():
        url = response.urljoin(href)

        yield scrapy.Request(url, meta={'meta_item': item}, callback=self.parse_category)

def parse_category(self, response, **kwargs):
    item = response.meta['meta_item']
    item['winner'] = response.css('table.results-table .r-racername span::text').get()

    yield WebscorerEvent(item)

因此,通过这种方式,您最终只需对项目执行yield操作,并包含所需的所有数据。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/67707525

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档