2013-04-06 123 views
7

我是Scrapy的新手,我试图使用CrawlSpider从文本文件中抓取多个站点。不过,我想限制网站的抓取深度以及再次抓取网页的总数量网站。不幸的是,当设置start_urls和allowed_domains属性时,response.meta ['depth']似乎总是为零(当我试图抓取单个站点时,这不会发生)。在设置文件中设置DEPTH_LIMIT似乎没有任何作用。 当我删除init定义,并简单地设置start_urls和allowed_domains似乎工作正常。 下面是代码(很抱歉的压痕 - 这是不是问题):使用Python Scrapy爬行多个站点,每个站点的深度有限

class DownloadSpider(CrawlSpider): 
    name = 'downloader' 
    rules = (
    Rule(SgmlLinkExtractor(), callback='parse_item', follow=True), 
    ) 
    def __init__(self, urls_file, N=10): 
     data = open(urls_file, 'r').readlines()[:N] 
     self.allowed_domains = [urlparse(i).hostname.strip() for i in data] 
     self.start_urls = ['http://' + domain for domain in self.allowed_domains] 

    def parse_start_url(self, response): 
     return self.parse_item(response) 

    def parse_item(self, response): 
     print response.url 
     print response.meta['depth'] 

这导致response.meta [“深度”]总是等于零和cralwer只抓取了第一个网站start_urls的每个元素(即它不跟随任何链接)。所以,我有两个问题 1)如何将抓取限制到一定深度每个站点在start_urls 2)如何限制每个网站抓取的总数不考虑深度

谢谢!

+0

看来,这个问题是在您将参数传递给蜘蛛的一部分。如果删除了,则DEPTH_LIMIT设置可以正常工作。然而,这使得它为喂养一组不断变化的网站抓取 – gpanterov 2013-04-06 12:39:48

回答

2

不要忘了(与super为例)调用基类的构造函数:

def __init__(self, urls_file, N=10, *a, **kw): 
    data = open(urls_file, 'r').readlines()[:N] 
    self.allowed_domains = [urlparse(i).hostname.strip() for i in data] 
    self.start_urls = ['http://' + domain for domain in self.allowed_domains] 
    super(DownloadSpider, self).__init__(*a, **kw) 

UPDATE:

当你覆盖 Python中的方法基类的方法不再调用,而是调用你的新方法,这意味着如果你想让你的新逻辑运行另外旧逻辑(即不是),那么你需要调用旧的逻辑ma nually。

这里是你缺少的不是调用CrawlSpider.__init__()(通过super(DownloadSpider, self).__init__())的逻辑:

self._compile_rules() 
+0

THanks效率非常低。这固定了它(尽管我仍然不知道为什么 - 我将继续梳理scrapy中的文档) – gpanterov 2013-04-06 17:43:15