Python 运行爬行爬行器的多个实例

Python 运行爬行爬行器的多个实例,python,web-scraping,scrapy,Python,Web Scraping,Scrapy,我刚刚开始使用scrapy,我想做以下几点 Have a list of n domains i=0 loop for i to n Use a (mostly) generic CrawlSpider to get all links (a href) of domain[i] Save results as json lines 为此,爬行器需要接收它必须爬网的域作为参数 我已成功创建爬行蜘蛛: from scrapy.linkextractors import LinkExtractor

我刚刚开始使用scrapy,我想做以下几点

Have a list of n domains
i=0
loop for i to n
Use a (mostly) generic CrawlSpider to get all links (a href) of domain[i]
Save results as json lines
为此,爬行器需要接收它必须爬网的域作为参数

我已成功创建爬行蜘蛛:

from scrapy.linkextractors import LinkExtractor
from scrapy.spiders import CrawlSpider, Rule
from scrapy.item import Item, Field
from scrapy.crawler import CrawlerProcess

class MyItem(Item):
    #MyItem Fields


class SubsiteSpider(CrawlSpider):
    name = "subsites"
    start_urls = []
    allowed_domains = []
    rules = (Rule(LinkExtractor(), callback='parse_obj', follow=True),)

    def __init__(self, starturl, allowed, *args, **kwargs):
        print(args)
        self.start_urls.append(starturl)
        self.allowed_domains.append(allowed)
        super().__init__(**kwargs)

    def parse_obj(self, response):
        item = MyItem()
        #fill Item Fields
        return item


process = CrawlerProcess({'USER_AGENT': 'Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1)'})
process.crawl(SubsiteSpider)
process.start()
如果我用
scrapy crawl子网站来称呼它-一个starturl=http://example.com -a allowed=example.com-o output.jl
结果正是我想要的,所以这部分已经很好了

我没有做的是创建多个
subitespider
实例,每个实例都有一个不同的域作为参数

我试过(在SpiderRunner.py中)

变体:

from scrapy.crawler import CrawlerProcess
from scrapy.utils.project import get_project_settings

process = CrawlerProcess(get_project_settings())

allowed = ["example.com"]
start = ["https://example.com"]
process.crawl('subsites', start, allowed)
process.start()
但是我想我会遇到一个错误,因为参数没有正确地传递给
\uuuuu init\uuuu
,例如
TypeError:\uuuu init\uuuu()缺少1个必需的位置参数:'allowed'
TypeError:\uuu init\uuuu()缺少2个必需的位置参数:'starturl'和'allowed'
(循环尚未实现)

因此,以下是我的问题: 1) 如果我不是从scrapy shell开始爬行,而是从python代码内部爬行,那么将参数传递到init的正确方法是什么? 2) 如何传递-o output.jl参数?(或者,使用允许的参数作为文件名?) 3) 我可以一个接一个地运行每只蜘蛛——这样做是否仍然是最佳/良好的实践?你能指出一个更广泛的关于“用不同的参数(=目标域)反复运行同一个spider,可选并行”的教程吗

提前非常感谢大家!
如果有任何拼写错误(不是以英语为母语的人),或者问题/详细信息不够准确,请告诉我如何更正这些错误。

您的代码有一些问题:

  • start\u URL
    allowed\u domains
    是类属性,您可以在
    \uuuu init\uuuu()中修改它们,使它们在类的所有实例中共享。
    您应该做的是使它们成为实例属性:

    class SubsiteSpider(CrawlSpider):
        name = "subsites"
        rules = (Rule(LinkExtractor(), callback='parse_obj', follow=True),)
    
        def __init__(self, starturl, allowed, *args, **kwargs):
            self.start_urls = [starturl]
            self.allowed_domains = [allowed]
            super().__init__(*args, **kwargs)
    
  • 最后3行不应该在spider类的文件中,因为您可能不希望每次导入spider时都运行该代码

  • 你的电话有点错。您可以这样使用它,以与将参数传递给spider类“
    \uuu init\uuu()
    相同的方式传递参数

  • 如何传递-o output.jl参数?(或者,使用允许的参数作为文件名


    你可以使用,给每个实例一个不同的
    FEED\u URI
    设置来达到相同的效果。

    非常感谢你,stranac。所有3个建议都是正确的,改进了我的代码/解决了问题。你的所有建议对我也有效,但我没有办法使用网站列表进行爬网,你能解释一下吗感谢答案中的最后一个片段展示了如何为单个网站执行此操作。对于它们的列表,只需在for循环中执行相同的操作。
    class SubsiteSpider(CrawlSpider):
        name = "subsites"
        rules = (Rule(LinkExtractor(), callback='parse_obj', follow=True),)
    
        def __init__(self, starturl, allowed, *args, **kwargs):
            self.start_urls = [starturl]
            self.allowed_domains = [allowed]
            super().__init__(*args, **kwargs)
    
    process = CrawlerProcess(get_project_settings())
    process.crawl('subsites', 'https://example.com', 'example.com')
    process.start()