scrapy框架使用-下载图片,使用urllib,使用requests,使用imagepipeline,
###
这是使用的urllib,
####
使用requests下载图片
import requests # 这是一个图片的url url = 'http://yun.itheima.com/Upload/Images/20170614/594106ee6ace5.jpg' response = requests.get(url) # 获取的文本实际上是图片的二进制文本 img = response.content # 将他拷贝到本地文件 w 写 b 二进制 wb代表写入二进制文本 with open( './a.jpg','wb' ) as f: f.write(img)
####
可见urllib,下载图片是更加的方便的,
####
使用scrapy自带的imagepipeline爬取图片
spider:
# -*- coding: utf-8 -*- import scrapy import json import re from urllib import parse from ..items import BaiduimageItem class ImagesSpider(scrapy.Spider): name = 'images' allowed_domains = ['image.baidu.com'] word_origin = input("请输入搜索关键字:") word = parse.quote(word_origin) url = "https://image.baidu.com/search/acjson?tn=resultjson_com&ipn=rj&is=&fp=result&queryWord=" + word + "&cl=2&lm=-1&ie=utf-8&oe=utf-8&adpicid=&st=-1&z=&ic=0&hd=&latest=©right=&word=" + word + "&s=&se=&tab=&width=&height=&face=0&istype=2&qc=&nc=1&fr=&expermode=&force=&pn={}&rn=30&gsm=1e&1586660816262=" def start_requests(self): #页数可调整,开始页30,每次递增30 for pn in range(30,151,30): url=self.url.format(pn) yield scrapy.Request(url=url,callback=self.parse) def parse(self, response): #正则匹配符合条件的thumbURL regex = '"thumbURL":"(.*?)"' pattern = re.compile(regex, re.S) links = pattern.findall(response.text) item=BaiduimageItem() #将搜索内容赋值给item,创建文件夹会用到 item["word"]=self.word_origin for i in links: item["link"]=i yield item
###
这一步要注意的,
1,url的编码问题,
2,正则匹配到所有的图片url,
pipelines.py
from scrapy.pipelines.images import ImagesPipeline import scrapy import hashlib from scrapy.utils.python import to_bytes class BaiduimagePipeline(ImagesPipeline): word="" # 重写ImagesPipeline里的get_media_requests函数 # 原函数的请求不适应与本程序 def get_media_requests(self, item, info): self.word=item['word'] yield scrapy.Request(url=item['link']) # 重写ImagesPipeline里的file_path函数 # 原函数return 'full/%s.jpg' % (image_guid) # 我们将其改为自己想存放的路径地址 def file_path(self, request, response=None, info=None): image_guid = hashlib.sha1(to_bytes(request.url)).hexdigest()
####
需要重写两个函数,
此处class BaiduimagePipeline继承了scrapy给我们提供的ImagesPipeline图片处理管道,为了让这个模块适应我们的程序,需要重写两个函数。
这里我将item中的word参数复制给了一个全局变量,目的是传递给file_path。也可以使用scrapy.Request(meta={})去传递
settings.py
ITEM_PIPELINES = { 'baiduimage.pipelines.BaiduimagePipeline': 300, } IMAGES_STORE= 'D:\\图片\\'
在settings.py里IMAGES_STORE是图片存储的路径
ImagesPipeline中的from_setting会调用 IMAGES_STORE,store_uri=settings['IMAGES_STORE']
#####
item
import scrapy class BaiduimageItem(scrapy.Item): # define the fields for your item here like: # name = scrapy.Field() link=scrapy.Field() word=scrapy.Field() pass
####
#####
####
技术改变命运