2012-07-05 65 views
2

我对scrapy工作,被刮取的网站,并获取所有如何动态创建一个CSV文件与scrapy蟒蛇蜘蛛名

其实我有3个蜘蛛不同的数据信息,我创造了这3个蜘蛛同一文件夹 结构如下

scrapy.cfg 
myproject/ 
    __init__.py 
    items.py 
    pipelines.py 
    settings.py 
    spiders/ 
     __init__.py 
      spider1.py 
      spider2.py 
      spider3.py 

现在,当我们运行特定的蜘蛛,我需要创建通过与蜘蛛的名字管道csv文件,例如

spider1.csv,spider2.csv,spider3.csv and so on(S根据蜘蛛和蜘蛛名称的数量我想创建csv文件

在这里,我们是否可以在pipeline.py中创建多个管道?也如何动态创建蜘蛛名称的csv文件如果不止一个蜘蛛存在

在这里我有3个蜘蛛,我想一次运行所有3个蜘蛛(通过使用scrapyd),当我运行所有3个蜘蛛应该创建3个带有蜘蛛名字的csv文件。 我想安排这个蜘蛛每6小时运行一次。 如果我的解释中有什么错误,请纠正我,让我知道如何做到这一点。

在此先感谢

编辑代码: 比如我贴我的代码只spider1.py

代码spider1.py

class firstspider(BaseSpider): 
    name = "spider1" 
    domain_name = "www.example.com" 
    start_urls = [ 
        "www.example.com/headers/page-value" 
       ] 
def parse(self, response): 
    hxs = HtmlXPathSelector(response) 
      ........ 
      ....... 
      item = Spider1Item() 
      item['field1'] = some_result 
      item['field2'] = some_result 
      ..... 
      ..... 
      return item 

管道.py代码:

import csv 
from csv import DictWriter 

class firstspider_pipeline(object): 

def __init__(self): 
    self.brandCategoryCsv = csv.writer(open('../%s.csv' % (spider.name), 'wb'), 
    delimiter=',', quoting=csv.QUOTE_MINIMAL) 
    self.brandCategoryCsv.writerow(['field1', 'field2','field3','field4']) 



def process_item(self, item, spider): 
    self.brandCategoryCsv.writerow([item['field1'], 
           item['field2'], 
           item['field3'], 
           item['field4']) 
    return item 

至于我,当我运行与蜘蛛名以上蜘蛛如前所述,与蜘蛛名CSV文件将被动态地创建..... 但现在当我办剩下的蜘蛛像spider2,spider3,spider3下,CSV文件及其相应的蜘蛛名称应该生成。

  1. 上述代码是否足以满足上述功能?

  2. 我们是否需要创建另一个管道类来创建另一个csv文件?(是否有可能在一个单一的pipeline.py文件创建多个管道类?)

  3. 如果我们创建多个管道类在一个pipeline.py文件,如何在特定的蜘蛛匹配其相关管道类

我想保存到数据库时,实现相同的功能,我的意思是,当我运行spider1 spider1的所有数据应保存到数据库到具有相关蜘蛛名称的表格中。 这里每个蜘蛛我有不同的SQL查询(所以需要编写不同的管道类)

  1. 这里的内涵是,当我们同时运行多个蜘蛛所有(使用scrapyd),多个CSV文件应与蜘蛛产生名称和多个表应与蜘蛛名称创建(当保存到数据库)

对不起,如果我错了任何地方,我希望它很好的解释,如果没有请让我知道。

+0

向我们展示一些代码,你已经尝试过了什么?或者向我们展示至少您对于您所想到的界面/ API的想法。 – 2012-07-05 13:00:24

+0

@Don问题:我已经更新了我的代码,请解释我该怎么做 – 2012-07-06 06:00:04

回答

3

你一般是在正确的轨道上。

但有几点我可以立刻指出:

  1. 你可能并不需要(=不宜用)的一类! Python不是Java。如果你的课程只包含2个方法,第一个方法是__init__-方法,你几乎肯定不需要一个类,但一个函数可以做得很好。少混乱=更好的代码!

  2. SO不适合进行一般的代码审查。改为尝试codereview。 SO-useres是一个友好的(主要)和有帮助的一群,但他们不喜欢写你的代码。他们喜欢解释,建议和正确。 因此,尽量实施你的申请,如果你遇到麻烦,你不能解决自己,再回来,并寻求建议。如上所述,您在概念上处于正确的轨道上,只是尝试实施它。

  3. 您似乎对班级概念有误解。至少只要它是蟒蛇类:

    1. 就我所见,您不需要BaseSpider类。基类和子类之间有什么区别?派生类不会让你的程序OO,或者更好,或者其他什么。搜索Liskovs principle以获得有关子类在python中何时适用的一般理解。 (这是一种反向逻辑,但它是查看是否应该继承或改变方法的最快方法之一。)

    2. python类变量在类声明后立即声明,在__init__方法中初始化的实例变量。类变量是一个类的所有实例之间的SHARED,其中实例变量对于各个实例是私有的。你几乎从不想使用类变量,它是一个Singleton-Pattern,这在大多数情况下是你想避免的,因为它在调试时会引起头痛和委屈。

因此我会修改你的Spider -class这样的:

class Spider(object): 
    def __init__(self, name, url=None): 
     self.name = name 
     self.domain_name = url 
     self.start_urls = [url] 
     ... 

crawlers = [Spider('spider %s' %i) for i in xrange(4)] #creates a list of 4 spiders 

但是,也许你正在使用一个声明元类的方法,但我不能看到您发布的代码。

如果您想并行运行抓取工具,则应考虑threading模块。它意味着连续的I/O操作,与multiprocessing模块相反,它是用于并行计算的。

您在正确的轨道上是概念性的。每当你遇到错误时,将你的项目分成小块并返回。

只是不期望得到一个完整的答案就像这样的问题:“我不想重新创建谷歌,我怎么能以最好的方式和最短的时间做到这一点!” ;-)