scrapy实现数据持久化、数据库连接、图片文件下载及settings.py配置
数据持久化的两种方式:(1)基于终端指令的持久化存储;(2)基于管道的持久化存储
基于终端指令的持久化存储
在爬虫文件的parse方法中必须要return可迭代对象类型(通常为列表或字典等)的返回值,该返回值作为基于终端指令持久化指定文件的输出内容。
执行输出指定格式进行存储-------将爬取到的数据写入不同格式的文件中进行存储,存储格式有限:
scrapy crawl 爬虫文件 -o xxx.json
scrapy crawl 爬虫文件 -o xxx.xml
scrapy crawl 爬虫文件 -o xxx.csv
基于管道的持久化存储
(1)编写爬虫文件进行数据解析
(2)在items.py中定义相关字段(用于存储解析的数据)
(3)在爬虫文件中将解析到的数据封装在实例化的item对象中
(4)通过yield将item对象提交到pipelines.py中的管道
(5)在管道中进行任意方式的数据持久化(数据库持久化需要重写两个方法open_spider和close_spider)
(6)在settings.py配置文件中开启管道(ITEM_PIPELINES ,同时处理ROBOTSTXT_OBEY协议、USER_AGENT 伪装和LOG_LEVEL='ERROR'日志输出等级)
(7)启动爬虫:scrapy crawl 爬虫文件
百度首页超链接数据解析与持久化存储
1.编写爬虫文件firstPro.py
# -*- coding: utf-8 -*-
import scrapy
from firstPro.items import FirstproItem class FirstbaiduSpider(scrapy.Spider):
name = 'firstBaidu' # 爬虫文件(应用)名
# allowed_domains = ['https://www.baidu.com/']#域名限定,一般直接注释
start_urls = ['https://www.baidu.com//'] # 起始url,创建应用时指定的,可修改 def parse(self, response): # 自动访问起始URL并获取结果后的回调函数,参数respons为起始请求的响应对象,可以直接调用封装好的xpath解析 # print(response.text)#获取字符串类型的响应内容
# print(response.body)#获取字节类型的相应内容 # 进行数据解析
a_list = response.xpath('//p[@id="nv"]/a') # 注意页面解析标签定位!!!浏览器看到的标签位置和实际爬去的页面内容位置可能不一样
for a in a_list:
# scrapy自带xpath解析获取文本或属性需要使用extract()或extract_first()
title = a.xpath('./text()').extract_first().replace('\xa0','') # extract_first()从结果列表获取第一个值
url = a.xpath('./@href')[0].extract() # extract()从解析结果中取出所有制,结果只有一个就是字符串,多个就是列表
# print(title, url) # 解析后的数据需要进行持久化存储:
# (1)items.py中定义相关存储字段;
item = FirstproItem()
# (2)实例化item对象将解析的数据进行封装;
item['title'] = title
item['url'] = url
# (3)使用yield将item对象提交给管道处理
yield item pass
爬虫文件firstPro.py
2.自定义items.py中的类字段
# -*- coding: utf-8 -*- # Define here the models for your scraped items
#
# See documentation in:
# https://docs.scrapy.org/en/latest/topics/items.html import scrapy class FirstproItem(scrapy.Item):
# define the fields for your item here like:
# name = scrapy.Field()
title=scrapy.Field()#存储标题
url=scrapy.Field()#存储连接
pass
items.py中类字段定义
3.管道pipilines.py处理类定义
注意:
(1)要想使用管道进行数据持久化,必须在settings.py中进行开启配置;
(2)可以定义多个管道类进行处理,但是在每个process_item函数中必须return item 传递给其它管道使用;
(3)process_item参数item只接受爬虫文件提交来的item对象,参数spider是爬虫文件中类的实例化对象,可以进行数据传递;
(4)如果要对数九持久化写入到数据库,需要在管道类中重写open_spider和close_spider方法,这两个方法只会被执行一次;
(5)对于图片类(视频、音频等二进制)数据的下载有可以定义新的管道继承相关类既可以直接实现图片的下载,注意要在settings.py中指定存储路径IMAGES_STORE=path
# 注意:
# (1)要想使用管道进行数据持久化,必须在settings.py中进行开启配置
# (2)可以定义多个管道类进行处理,但是在每个process_item函数中必须return item 传递给其它管道使用
# (3)process_item参数item只接受爬虫文件提交来的item对象,参数spider是爬虫文件中类的实例化对象,可以进行数据传递;
# (4)如果要对数九持久化写入到数据库,需要在管道类中重写open_spider和close_spider方法,这两个方法只会被执行一次;
# (5)对于图片类(视频、音频等二进制)数据的下载有可以定义新的管道继承相关类既可以直接实现图片的下载 # 默认管道处理
class FirstproPipeline(object):
# item对象处理函数
def process_item(self, item, spider):
print(item)
return item
管道处理注意事项
# (1)自定义的文件持久化管道
class TofilePipeline(object):
# 构造方法初始化一个属性文件句柄,也可以定义一个类变量:fp=None
def __init__(self):
self.fp = None # 打开文件句柄
def open_spider(self, spider):
print('开始写入数据...')
self.fp = open('a.text', 'w', encoding='utf-8') # 关闭文件进行系统资源回收
def close_spider(self, spider):
self.fp.close()
print('数据下载成功,爬虫结束!') def process_item(self, item, spider):
self.fp.write(f'{item["title"]}:{item["url"]}\n')
return item
(1)自定义的文件持久化管道
# (2)自定义的基于mysql数据库持久化管道
import pymysql
class ToMysqlPipeline(object):
conn = None
cursor = None # 建立数据库连接
def open_spider(self, spider):
print('建立数据库连接...')
self.conn = pymysql.connect(host='127.0.0.1', port=3306, user='root', password='', db='spider') # 关闭数据库连接
def close_spider(self, spider):
self.cursor.close() # conn断开时也会自动断开
self.conn.close()
print('成功写入数据库!') def process_item(self, item, spider):
sql = f'insert into table1 values ({item["title"]},{item["url"]})'
self.cursor = self.conn.cursor() # 数据库事务操作
try:
self.cursor.execute(sql)
self.conn.commit()
except Exception as e:
print(e)
self.conn.rollback() return item
(2)自定义的基于mysql数据库持久化管道
# (3)自定义的基于redis数据库持久化管道
import redis
class ToRedisPipeline(object):
conn = None # 建立数据库连接
def open_spider(self, spider):
print('建立数据库连接...')
self.conn = redis.Redis(host='127.0.0.1', port=6379) def process_item(self, item, spider):
self.conn.lpush('data', dict(item)) # 将item对象以字典形式存储在redis列表结构中
return item
(3)自定义的基于redis数据库持久化管道
# (4)自定义的基于mongodb数据库持久化管道
import pymongo
class ToMongoDBPipeline(object):
conn = None # 建立数据库连接
def open_spider(self, spider):
print('建立数据库连接...')
self.conn = pymongo.MongoClient(host='127.0.0.1', port=27017) # 关闭数据库连接(可以不写)
def close_spider(self, spider):
self.conn.close()
print('成功写入数据库!') def process_item(self, item, spider):
self.conn.Spider.col.insert_one({item["title"]:item["url"]}) #将title:url存入mongodb的Spider数据库中col集合(表)中
return item
(4)自定义的基于MongoDB数据库持久化管道
# (5)自定义图片等文件的下载管道
#IMAGES_STORE='filepath'在settings设置文件中指定存储图片的下载路径
import os
import scrapy
from scrapy.pipelines.images import ImagesPipeline class ImageDownloadPipeline(ImagesPipeline):
#接收item且将item中存储的url进行请求发送
def get_media_requests(self, item, info): # 下载图片
url=item["url"]
yield scrapy.Request(url, meta={'item': item}) # 指定下载路径
def file_path(self, request, response=None, info=None):
item = request.meta['item']
img_name = request.url.split('/')[-1]
path='图片'#自动会创建文件夹,同时存放在settings.py中指定的IMAGES_STORE配置路径下
filename = os.path.join(path, img_name)
print(f'正在下载------{filename}...')
return filename # 将item传递给下一个即将被执行的管道类
def item_completed(self, result, item, info):
return item
(5)自定义图片等文件的下载管道
4.settings.py配置文件
# Crawl responsibly by identifying yourself (and your website) on the user-agent
# USER_AGENT = 'firstPro (+http://www.yourdomain.com)'
# (1)UA伪造
USER_AGENT = 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/75.0.3770.100 Safari/537.36' # Obey robots.txt rules
# ROBOTSTXT_OBEY = True
# (2)不遵守robots协议
ROBOTSTXT_OBEY = False # (3)设置日志输出等级
LOG_LEVEL = 'ERROR' # Configure item pipelines
# See https://docs.scrapy.org/en/latest/topics/item-pipeline.html
# 取消注释,开启管道,数字代表优先级,越小级别越高,按需要开启
ITEM_PIPELINES = {
'firstPro.pipelines.FirstproPipeline': 300,
'firstPro.pipelines.TofilePipeline': 200,
# 'firstPro.pipelines.ToMysqlPipeline': 600,
'firstPro.pipelines.ToRedisPipeline': 100,
# 'firstPro.pipelines.ToMongoDBPipeline': 400,
# 'firstPro.pipelines.ImageDownloadPipeline': 200,
} #如果开启图片下载管道,需要指定下载目录
# IMAGES_STORE='./images'
5.启动爬虫程序
scrapy crawl firstPro
scrapy实现数据持久化、数据库连接、图片文件下载及settings.py配置的更多相关文章
- Docker namespace,cgroup,镜像构建,数据持久化及Harbor安装、高可用配置
1.Docker namespace 1.1 namespace介绍 namespace是Linux提供的用于分离进程树.网络接口.挂载点以及进程间通信等资源的方法.可以使运行在同一台机器上的不同服务 ...
- 论Scrapy中的数据持久化
引入 Scrapy的数据持久化,主要包括存储到数据库.文件以及内置数据存储. 那我们今天就来讲讲如何把Scrapy中的数据存储到数据库和文件当中. 终端指令存储 保证爬虫文件的parse方法中有可迭代 ...
- Scrapy 框架,持久化文件相关
持久化相关 相关文件 items.py 数据结构模板文件.定义数据属性. pipelines.py 管道文件.接收数据(items),进行持久化操作. 持久化流程 1.爬虫文件爬取到数据后,需要将数据 ...
- scrapy架构与目录介绍、scrapy解析数据、配置相关、全站爬取cnblogs数据、存储数据、爬虫中间件、加代理、加header、集成selenium
今日内容概要 scrapy架构和目录介绍 scrapy解析数据 setting中相关配置 全站爬取cnblgos文章 存储数据 爬虫中间件和下载中间件 加代理,加header,集成selenium 内 ...
- 第三百六十七节,Python分布式爬虫打造搜索引擎Scrapy精讲—elasticsearch(搜索引擎)scrapy写入数据到elasticsearch中
第三百六十七节,Python分布式爬虫打造搜索引擎Scrapy精讲—elasticsearch(搜索引擎)scrapy写入数据到elasticsearch中 前面我们讲到的elasticsearch( ...
- 四十六 Python分布式爬虫打造搜索引擎Scrapy精讲—elasticsearch(搜索引擎)scrapy写入数据到elasticsearch中
前面我们讲到的elasticsearch(搜索引擎)操作,如:增.删.改.查等操作都是用的elasticsearch的语言命令,就像sql命令一样,当然elasticsearch官方也提供了一个pyt ...
- scrapy 学习笔记2 数据持久化
前情提要:校花网爬取,并进行数据持久化 数据持久化操作 --编码流程: 1:数据解析 2:封装item 类 3: 将解析的数据存储到实例化好的item 对象中 4:提交item 5:管道接收item然 ...
- iOS 数据持久化(扩展知识:模糊背景效果和密码保护功能)
本篇随笔除了介绍 iOS 数据持久化知识之外,还贯穿了以下内容: (1)自定义 TableView,结合 block 从 ViewController 中分离出 View,轻 ViewControll ...
- scrapy框架的持久化存储
一 . 基于终端指令的持久化存储 保证爬虫文件的parse方法中有可迭代类型对象(通常为列表or字典)的返回,该返回值可以通过终端指令的形式写入指定格式的文件中进行持久化操作. 执行输出指定格式进行存 ...
随机推荐
- java list随机截取(洗牌)
public void solution(){ List<Integer> givenList = Arrays.asList(1, 2, 3,4,5,6); Collections.sh ...
- 虚拟化KVM之优化(三)
KVM的优化 1.1 cpu的优化 inter的cpu的运行级别,(Ring2和Ring1暂时没什么用)Ring3为用户态,Ring0为内核态 Ring3的用户态是没有权限管理硬件的,需要切换到内核态 ...
- Spring Boot JPA中关联表的使用
文章目录 添加依赖 构建Entity 构建Repository 构建初始数据 测试 Spring Boot JPA中关联表的使用 本文中,我们会将会通过一个Book和Category的关联关系,来讲解 ...
- 标准库 xml
xml处理模块 xml是实现不同语言或程序之间进行数据交换的协议,跟json差不多,但json使用起来更简单,不过,古时候,在json还没诞生的黑暗年代,大家只能选择用xml呀,至今很多传统公司如金融 ...
- 【Linux常见命令】tee命令
tee - read from standard input and write to standard output and files tee命令用于读取标准输入的数据,并将其内容输出成文件. t ...
- 《Cisco防火墙》一2.4 总结
本节书摘来自异步社区<Cisco防火墙>一书中的第2章,第2.4节,作者 [巴西]Alexandre M.S.P. Moraes,更多章节内容可以访问云栖社区"异步社区" ...
- SaltStack数据系统之Grains、Pillar
SaltStack数据系统之Grains.Pillar 1.什么是Grains? Grains是saltstack的组件,用于收集salt-minion在启动时候的信息,又称为静态信息.Grains是 ...
- 图论--2-SAT--HDU/HDOJ 1814 Peaceful Commission
Peaceful Commission Time Limit: 10000/5000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Oth ...
- JAVA大数几算--HDU 2054 A == B ?
Problem Description Give you two numbers A and B, if A is equal to B, you should print "YES&quo ...
- [bzoj2088]P3505 [POI2010]TEL-Teleportation
洛谷 bzoj 用了分层图的思想 题意 给一张图,要求你再尽可能的多连边,使得从1到2至少要经过5条边 没啥复杂的公式,讲解都在注释里 #include<cstdio> #include& ...