Scrapy scrapy 框架,异步爬虫框架。
同步与异步 同步:下一个方法依赖上一个方法,上一个没执行完,则下一个不会执行。
异步:下一个方法不依赖上一个方法,上一个没执行完,下一个依旧会执行。
组成:Pipeline 、Scheduler、Downloader、Spiders。以及Scrapy Engine 引擎(队列)
中间件:Spider Middlewares、Downloader Middlewares
Pipeline 主要用于处理IO 存储,写入本地获取的西悉尼
Scheduler 调度器,将所有的 url 发送给Downloader,并且去重网址,整合队列
Downloader 处理请求 requests,将 responses 返回给 Spiders
Spiders 是我们的爬虫文件
Scrapy Engine 引擎控制整个运转
spider middlewares 一般不用,爬虫将请求交给调度器时,进行处理。
Downloader Middlewares 加入请求头,加入代理 ip
初次使用 scrapy 安装 scrapy
创建项目
1 2 3 4 5 6 7 # 创建项目 > > scrapy startproject 项目名字 > > cd 项目名字 # 创建爬虫文件 > > scrapy genspider 爬虫名字 "host 地址" # 运行爬虫文件 > > scrapy crawl 爬虫名字
常用配置
1 2 3 4 5 6 7 8 9 Settings中的常用配置: USER_AGENT = "" ROBOTSTXT_OBEY = True |False DEFAULT_REQUEST_HEADERS = {} CONCURRENT_REQUESTS = 16 DOWNLOAD_DELAY = 3 SPIDER_MIDDLEWARES DOWNLOADER_MIDDLEWARES ITEM_PIPELINES
创建文件
1 > > scrapy genspider s1 "blog.csdn.net"
创建好的爬虫文件
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 import scrapyclass S1Spider (scrapy.Spider): name = 's1' allowed_domains = ['blog.csdn.net' ] start_urls = ['http://blog.csdn.net/' ] def parse (self, response ): pass
下面方法执行相当于 start_urls ,但是可以跳过限定的请求头
1 2 3 4 5 6 7 8 def start_requests (self ): yield scrapy.Request( url = 'http://edu.csdn.net' , callback = self.parse2 ) def parse2 (self, respones ): print (response.body)
爬取网页时,一般默认机器人设置为 False
加入请求头
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 class Scrapy01DownloaderMiddleware (object ): def process_request (self, request, spider ): request.headers = Headers( { 'User-Agent' : user_agent.get_user_agent_pc() } ) return None
开启这个中间件
1 2 3 4 5 DOWNLOADER_MIDDLEWARES = { 'scrapy01.middlewares.Scrapy01DownloaderMiddleware' : 543 , }
加入代理 Ip
1 2 3 4 5 6 7 def process_request (self, request, spider ): request.headers = Headers( { 'User-Agent' : user_agent.get_user_agent_pc() } ) request.meta['proxy' ] = 'http://IP:PORT' + ur.urlopen("代理 ip 接口" ).read().decode('utf-8' ).strip()
为了方便我们使用,可以增加一个 start.py
1 2 3 from scrapy import cmdlinecmdline.execute('scrapy crawl s1' .split())
保存文件,修改文件如下
1 2 3 4 5 6 7 8 def parse2 (self, response ): data = response.body.decode('utf-8' ) item = {} item['data' ] = data yield item
在 setting 中
1 2 3 4 5 ITEM_PIPELINES = { 'scrapy01.pipelines.Scrapy01Pipeline' : 300 , 'scrapy01.pipelines.Scrapy01Pipeline' : 300 , }
项目说明
关键字
说明
projectcode
项目编号
web
信息来源网站(例如:必联网)
keyword
关键字
detail_url
招标详细页网址
title
第三方网站发布标题
toptype
信息类型
province
归属省份
product
产品范畴
industry
归属行业
tendering_manner
招标方式
publicity_date
招标公示日期
expiry_date
招标截止日期
log日志 1 2 3 4 5 6 7 8 9 LOG_FILE = "日志文件地址" LOG_LEVEL = "日志级别" CRITICAL 严重错误 (critical) ERROR 一般错误(regular errors) WARNING 警告信息(warning messages) INFO 一般信息(informational messages) DEBUG 调式信息 (debugging messages)
pymysql 1 2 3 4 5 6 7 8 9 10 11 12 13 14 import pymysqlmysql_conn = pymysql.Connection( host='localhost' , port=3306 , user='root' , password="" , database='连接数据库名字' , charset='utf8' , ) cs = mysql_conn.cursor() cs.execute('SQL' ) mysql_conn.commit()
Redis的数据库结构
Redis 中有16个数据库
select [ index ] 切换数据库
类型
表示
字符串(数字属于特殊的字符串)
String
哈希(字典)
Hash
列表(有序,相当于 python 中的 list )
List
无序集合
Set
有序集合
Zset
键的操作:
操作
命令
查找
keys [ pattern ]
删除
del [ key ]
检查是否存在
exists [ key ]
查看键的类型
type [ key ]
scrapy-redis 原理 将调度器和
1 2 3 4 5 6 7 8 9 DUPEFILTER_CLASS = "scrapy_redis.dupefilter.RFPDupeFilter" SCHEDULER = "scrapy_redis.scheduler.Scheduler" SCHEDULER_PERSIST = True REDIS_URL = 'redis://127.0.0.1:6379'