我有一个 Django 网站,当用户请求时会发生抓取,并且我的代码在新进程中启动 Scrapy 蜘蛛独立脚本。当然,这对于用户的增加来说是行不通的。
像这样的事情:
class StandAloneSpider(Spider):
#a regular spider
settings.overrides['LOG_ENABLED'] = True
#more settings can be changed...
crawler = CrawlerProcess( settings )
crawler.install()
crawler.configure()
spider = StandAloneSpider()
crawler.crawl( spider )
crawler.start()
我决定使用 Celery 并使用工作人员对抓取请求进行排队。
然而,我遇到了龙卷风反应堆无法重新启动的问题。第一个和第二个蜘蛛运行成功,但后续蜘蛛将抛出 ReactorNotRestartable 错误。
任何人都可以分享在 Celery 框架内运行 Spider 的任何技巧吗?
好的,这就是我如何让 Scrapy 与我的 Django 项目一起工作,该项目使用 Celery 对要抓取的内容进行排队。实际的解决方法主要来自 joehillen 的代码位于此处http://snippets.scrapy.org/snippets/13/ http://snippets.scrapy.org/snippets/13/
首先是tasks.py
file
from celery import task
@task()
def crawl_domain(domain_pk):
from crawl import domain_crawl
return domain_crawl(domain_pk)
然后crawl.py
file
from multiprocessing import Process
from scrapy.crawler import CrawlerProcess
from scrapy.conf import settings
from spider import DomainSpider
from models import Domain
class DomainCrawlerScript():
def __init__(self):
self.crawler = CrawlerProcess(settings)
self.crawler.install()
self.crawler.configure()
def _crawl(self, domain_pk):
domain = Domain.objects.get(
pk = domain_pk,
)
urls = []
for page in domain.pages.all():
urls.append(page.url())
self.crawler.crawl(DomainSpider(urls))
self.crawler.start()
self.crawler.stop()
def crawl(self, domain_pk):
p = Process(target=self._crawl, args=[domain_pk])
p.start()
p.join()
crawler = DomainCrawlerScript()
def domain_crawl(domain_pk):
crawler.crawl(domain_pk)
这里的技巧是“from multiprocessing import Process”,它绕过了 Twisted 框架中的“ReactorNotRestartable”问题。因此,基本上,Celery 任务调用“domain_crawl”函数,该函数一遍又一遍地重用“DomainCrawlerScript”对象来与 Scrapy 蜘蛛交互。 (我知道我的示例有点多余,但我在使用多个版本的 python 设置时这样做是有原因的 [我的 django Web 服务器实际上使用 python2.4,我的工作服务器使用 python2.7])
在我的示例中,“DomainSpider”只是一个修改后的 Scrapy Spider,它获取 url 列表,然后将它们设置为“start_urls”。
希望这可以帮助!
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)