有鼻泡的犀牛 发表于 2018-1-14 10:26:55

浅谈python的第三方库scrapy

本帖最后由 有鼻泡的犀牛 于 2018-1-14 10:35 编辑

scrapy是一个python的爬虫框架。安装过程不再详说,这篇文章只是很肤浅的谈一下自己的理解。

首先,创建scrapy相关项目,windows中,进入 cmd ,然后进入你想创建的项目所在目录:

运行命令: scrapy startproject [项目名] ,我们就可以在相关目录下看到你所创建的项目,而我们只需要在这个项目中写代码即可。

用相关 IDE 打开项目。这里,我首先介绍一下关于 scrapy 的运行流程:

如图所示:



在这个图中,我们可以很清晰的看到数据流向,具体的工作流程大概是这样:(当然具体的数据流向更复杂,但初始这么想,也可以写出爬虫)

你:我有一个 url ,你 engine 帮我处理一下

engine:老大给我一个 url ,那个谁 , downloader 你把这个 url 的内容下一下

downloader: engine 先生,我下好了

engine:奥,行吧,那个,spider 你给我分析一下

spider: 小菜一碟。。。好了,我这里还有 url ,那就传给 engine 吧,下载下来的数据,就用 item 包装一下吧,美美哒,然后再给 pipeline

pipeline: 来了,行,我把他们存到仓库里

engine:那个 spider 小同志给了我一些 url ,那个,谁来着,奥,downloader 你把 url 的内容下一下

所以,经过上面分析,我们需要做的事为

1.传递一个初始 url

2.书写 spider ,用于分析

3.书写 item ,用于包装

4.书写 pipeline,用于对分析完的数据进行后续处理

当我们创建项目后,我们可以在setting中,发现系统已经为我们创建好相关属性,如:

BOT_NAME = 'spider_bg'

SPIDER_MODULES = ['spider_bg.spiders']
NEWSPIDER_MODULE = 'spider_bg.spiders'

大致意思就是告诉 scrapy ,这个项目名字,分析类也就是spider位于哪里

进入spiders 的 spider.py 中,我们发现相关 爬虫类 内容:

name = "girl"
    allowed_domains = ["lesmao.cc"]
    start_urls = ["http://www.lesmao.cc/forum-113-1.html"]

name : 是爬虫的名字,尤为重要,可自己单独命名 在最后,启动爬虫的时候我们需 scrapy crawl 爬虫名

allowed_domains : 是所允许爬的域名范围限制,因为一个网站可能有外链存在,如果你不加限制,可能会爬到别的网站

start_urls : 是你需要提供的第一个 url

里面有一个方法: parse()

        我们需要在里面写分析过程,告诉爬虫该怎么爬,怎么获取另外的 url ,对获取的 url 我们怎么处理,对获取的数据,我们怎么处理

当然,我们需要在 items.py 中,定义包装。其意义有很多,在此不一详述。

数据经过 item 包装后,最终会流向 pipeline 中,对于为什么最终会流向 pipeline,是因为在 setting 中的设定

ITEM_PIPELINES = {
    'spider_bg.pipelines.SpiderBgPipeline': 300,
}

这个设定就告诉 scrapy ,那个pipeline 在哪,当然我们也可以设定多个不容优先数的 line,只需要相应的添加即可。后面的优先数越小表示的优先级越大。

假设,我们有两个 line ,一个是图片处理,如 line1,优先数为10,一个为文字处理,line2,优先数为300

所以item包装后的数据流向是,先到line1,再到line2,最后返回到 spider,进行下一个包装。

再次,贴出相关代码,很简单,一读便知:

setting:


BOT_NAME = 'spider_bg'

SPIDER_MODULES = ['spider_bg.spiders']
NEWSPIDER_MODULE = 'spider_bg.spiders'

ROBOTSTXT_OBEY = False

ITEM_PIPELINES = {
    'spider_bg.pipelines.SpiderBgPipeline': 300,
}

items.py

import scrapy


class SpiderBgItem(scrapy.Item):
    # define the fields for your item here like:
    url = scrapy.Field()
    pass

spiders文件夹下的spider.py

import scrapy
from spider_bg.items import SpiderBgItem

class LiSpider(scrapy.Spider):
    name = "girl"
    allowed_domains = ["lesmao.cc"]
    start_urls = ["http://www.lesmao.cc/forum-113-1.html"]



    def parse(self, response):
      urls = response.xpath("//div[@id = 'show_right']//div[@class = 'group']//a/@href").extract()

      for url in urls:
            yield scrapy.Request(url,callback=self.parse_detail)
      next_url = response.xpath("//a[@class = 'nxt']/@href").extract()
      if next_url:
            for url in next_url:
                yield scrapy.Request(url,callback=self.parse)

    def parse_detail(self,response):
      img_urls = response.xpath("//div[@id = 'thread-pic']//img/@src").extract()
      for url in img_urls:
            item = SpiderBgItem()
            item['url'] = url
            yield item
      next_url = response.xpath("//div[@id = 'thread-page']//a[@class = 'nxt']/@href").extract()
      for url in next_url:
            if url:
                yield scrapy.Request(url,callback=self.parse_detail)


pipeline.py

import urllib.request

class SpiderBgPipeline(object):

    def process_item(self, item, spider):
      img = urllib.request.urlopen(str(item['url']))
      name = str(item['url']).split('/')[-1]
      try:
            with open('./Bololi/' + name , 'wb') as f:
                f.write(img.read())
      except:
            print(1)
      return item

再贴一下,目录结构:



谢谢大家的阅读。


有鼻泡的犀牛 发表于 2018-1-14 10:36:19

怎么也看不见图片。。。
页: [1]
查看完整版本: 浅谈python的第三方库scrapy