什么触发了from_crawler类方法?

时间:2018-04-02 00:57:55

标签: python scrapy

我正在使用scrapy,我有以下功能管道类:

class DynamicSQLlitePipeline(object):

@classmethod
def from_crawler(cls, crawler):
    # Here, you get whatever value was passed through the "table" parameter
    docket = getattr(crawler.spider, "docket")
    return cls(docket)

def __init__(self,docket):
    try:
        db_path = "sqlite:///"+settings.SETTINGS_PATH+"\\data.db"
        db = dataset.connect(db_path)
        table_name = docket[0:3]  # FIRST 3 LETTERS
        self.my_table = db[table_name]


    except Exception:
        # traceback.exec_print()
        pass

def process_item(self, item, spider):

    try:
        test = dict(item)
        self.my_table.insert(test)
        print('INSERTED')
    except IntegrityError:
            print('THIS IS A DUP')

我的蜘蛛中有:

custom_settings = {
    'ITEM_PIPELINES': {

        'myproject.pipelines.DynamicSQLlitePipeline': 600,
    }
}

从最近的一个问题我被指出What is the 'cls' variable used for in Python classes?

如果我正确理解为了实例化管道对象(使用init函数),它需要一个案卷号。只有运行from_crawler类方法后才能使用文档编号。但是什么触发了from_crawler方法。代码再次起作用。

1 个答案:

答案 0 :(得分:2)

classmethod的调用者必须拥有该类的实例。他们可能只是通过名称访问它,如下所示:

DynamicSQLlitePipeline.from_crawler(crawler)

......或:

sqlitepipeline.DynamicSQLlitePipeline.from_crawler(crawler)

或许您可以将类对象传递给某人,然后将它们存储起来并在以后使用它:

pipelines[i].from_crawler(crawler)

在Scrapy中,根据the docs,使用框架注册一组管道的常用方法是这样的:

ITEM_PIPELINES = {
    'myproject.pipelines.PricePipeline': 300,
    'myproject.pipelines.JsonWriterPipeline': 800,
}

(另请参阅Extensions user guide,其中说明了这适用于scrapy项目。)

据推测,你已经在代码中做了类似的事情,你没有向我们展示过,把'sqlscraper.pipelines.DynamicSQLlitePipeline'放在那个字典中。在某些时候,Scrapy会通过该dict,按值按顺序对其进行排序,并实例化每个管道。 (因为它具有类的名称,作为字符串,而不是类对象,这有点棘手,但这里的细节实际上并不相关。)