【问题标题】:How to force Scrapy to scrape corresponding comments webpage after scraping article webpage?抓取文章网页后如何强制 Scrapy 抓取相应的评论网页?
【发布时间】:2016-10-22 22:40:01
【问题描述】:

我正在尝试使用 scrapy 抓取新闻文章及其 cmets。在我的例子中,新闻文章及其 cmets 位于不同的网页上,如下例所示。

(1) 文章链接。 http://www.theglobeandmail.com/opinion/editorials/if-britain-leaves-the-eu-will-scotland-leave-britain/article32480429/

(2) 与文章相关的 cmets 的链接。 http://www.theglobeandmail.com/opinion/editorials/if-britain-leaves-the-eu-will-scotland-leave-britain/article32480429/comments/

我希望我的程序了解 (1) 和 (2) 是相关的。另外,我想确保 (2) 在 (1) 之后被抓取,而不是在中间抓取其他网页。我使用以下规则来抓取新闻文章网页和 cmets 网页。

rules = (
         Rule(LinkExtractor(allow = r'\/article\d+\/$'),   callback="parse_articles"),
        Rule(LinkExtractor(allow = r'\/article\d+\/comments\/$'), callback="parse_comments")
)

我尝试在文章的解析函数中使用显式请求调用,如下所示:

comments_url = response.url + 'comments/'
print('comments url: ', comments_url)
return Request(comments_url, callback=self.parse_comments)

但它没有用。如何让爬虫在抓取文章网页后立即抓取 cmets 网页?

【问题讨论】:

    标签: python scrapy web-crawler


    【解决方案1】:

    您需要手动设置对 cme​​ts 页面的请求。
    您的爬虫发现的每个文章页面都应该在某处有一个 cmets 页面 url,对吗?
    在这种情况下,您可以简单地在 parse_article() 方法中链接评论页面请求。

    from scrapy import Request
    from scrapy.spiders import CrawlSpider
    class MySpider(CrawlSpider):
    
        rules = (
            Rule(LinkExtractor(allow = r'\/article\d+\/$'),   callback="parse_articles"),
        )
        comments_le = LinkExtractor(allow = r'\/article\d+\/comments\/$')
    
        def parse_article(self, response):
            item = dict()
            # fill up your item
            ...
            # find comments url
            comments_link  = comments_le.extract_links()[0].link
            if comments_link:
                # yield request and carry over your half-complete item there too
                yield Request(comments_link, self.parse_comments,
                              meta={'item':item})
            else:
                yield item 
    
        def parse_comments(self, response):
            # retrieve your half-complete item
            item = response.meta['item']
            # add some things to your item
            ...
            yield item
    

    【讨论】:

    • 感谢您的回复!它会转到相应的 cmets 链接,但它仍然不会在文章页面之后立即抓取 cmets 页面。它会在两者之间刮掉其他文章。
    • @user7009553 是的,因为scrapy 是异步的,它并行抓取多个链。因此,它可能会刮掉文章并安排对 cme​​ts 的请求,同时刮掉其他一些文章 - 但是您的连锁店不会失去订单。在这种情况下,您的链是 parse_article->parse_cmets->yield 项,因此您应该得到预期的结果。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-06-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多