zoukankan      html  css  js  c++  java
  • scrapy之源码解析

    """
    from twisted.internet import reactor #事件循环(终止条件。所有的socket都已经以移除)
    from twisted.internet import defer  #defer.Deferred特殊的socket对象(不会发请求,手动移除)
    from twisted.web.client import getPage #socket对象(自动从事件循环移除)
    """
    from scrapy.crawler import CrawlerProcess
    #scrapy源码分析
    """
    1.爬虫运行的开始,自定义命令
    
    
    2.spider_list包含爬虫的名字列表
    spider_list = self.crawler_process.spiders.list()
    
    
    3.from scrapy.crawler import CrawlerProcess
    调用CrawlerProcess父类的CrawlerRunner的crawl方法,
    返回一个Crawler类的对象
    crawler = self.create_crawler(crawler_or_spidercls)
    return Crawler(spidercls, self.settings)
    
    
    4.返回之后,调用_crawl,将对象Crawler放到_active集合,
    在defer.DeferredList(self._active)里会转为列表
    
     return self._crawl(crawler, *args, **kwargs)
     d = crawler.crawl(*args, **kwargs)
            self._active.add(d)
    
    5.此时创建了Crawler.crawl方法,有@defer.inlineCallbacks装饰器
    这个crawl就是添加事件循环,此时不会调用里面的yield,
    在Crawler类
     self.spider = self._create_spider(*args, **kwargs)
                self.engine = self._create_engine()
                start_requests = iter(self.spider.start_requests())
                yield self.engine.open_spider(self.spider, start_requests)
                yield defer.maybeDeferred(self.engine.start)
    
    
    6.在CrawlerProcess类中调用self.crawler_process.start()
    先将_active中的Crawler对象加到defer.DeferredList(self._active)
    defer.DeferredList()这个函数监听事件循环是否完成,即爬虫
    是否完成,完成后会调用dd.addBoth(done),在scrapy中用
     _close=defer.Deferred()
        yield _close
    
    _close.callback(None)
    来结束事件循环
    
    然后会调用reactor.run()开始事件循环
    
    
    7.回到5,此时会调用yield
    即yield self.engine.open_spider(self.spider, start_requests)
    
    然后加载爬虫的中间件
    start_requests = yield self.scraper.spidermw.process_start_requests(start_requests, spider)
    将爬虫放到调度器
    yield scheduler.open(spider)
    加载items
    yield self.scraper.open_spider(spider)
    
    
    取得scheduler中的请求,进入下一个事件循环
    slot.nextcall.schedule()
    
    
    
    
    
    在调用yield defer.maybeDeferred(self.engine.start)
    将defer.Deferred()加到事件循环中
    
    
    
    
    
    自定义setting
    1.SCHEDULER
    2.DOWNLOADER
    
    
    
    """

    由于本人知识有限,只看懂到这里,后续再更新。。。。。

  • 相关阅读:
    中文编解码问题
    转载:深入探讨 Java 类加载器
    转载:MAT Memory Analyzer Tool使用示例
    转载:MyEclipse安装插件的几种方法
    React组件之间通过Props传值的技巧(小案例,帮助体会理解props、state、受控组件和非受控组件等)
    ES5, ES6, ES2016, ES.Next: JavaScript 的版本是怎么回事?
    GIT,SVN,CVS的区别比较
    JS实现拖拽小案例
    JS实现时钟效果
    关于VUE的安装和一些简单属性
  • 原文地址:https://www.cnblogs.com/lujiacheng-Python/p/10222035.html
Copyright © 2011-2022 走看看