python scrapy框架爬取80s保存mysql
写在前面
学习了scrapy框架,把前面写的resquest + gevent协程 爬取的方式改进一下。相较之前文章:https://blog.csdn.net/mozixigg/article/details/107325429用到辣么多的库(gevent分配任务,request获取数据,bs4解析数据都要手写),scrapy框架就要简单很多,正如书中所言,scrapy就是一辆汽车,不用我们再造轮子。可以直接开车!
scrapy项目创建流程
第一步:创建一个项目(开发商拍到地了,立项)
scrapy startproject movies
第二步:开始项目(审批通过,开始奠基)
cd movies
scrapy genspider movie www.y80s.com
第三步:提取的item(设计图纸,购买材料)
import scrapy
class MoviesItem(scrapy.Item):
film_name = scrapy.Field()
#定义电影名字名数据属性
film_story = scrapy.Field()
#定义剧情介绍数据属性
film_score = scrapy.Field()
#定义豆瓣分数据属性
film_play_url = scrapy.Field()
#定义播放url数据属性
xldown_url = scrapy.Field()
#定义迅雷地址数据属性
第四步:编写spider(开始建设)
#该文件执行scrapy genspider movie www.y80s.com 后会自动创建
import scrapy
import bs4#导入bs4解析网页
from ..items import MoviesItem
#导入项目中items中MoviesItem对象,固定导入方式
#执行scrapy genspider movie www.y80s.com 后会自动创建此爬虫类
class MovieSpider(scrapy.Spider):
name = 'movie'#爬虫名字
allowed_domains = ['www.y80s.com']#允许爬取的域名
start_urls = []#定义起始爬取的网址
for i in range(5):#爬5页
url = 'http://www.y80s.com/movie/list/----g-p'+str(i)
start_urls.append(url)#加入起始地址列表,相当于要爬取的地址为这5个地址
# parse是默认处理response的方法
def parse(self,response):
bs = bs4.BeautifulSoup(response.text,'html.parser')#解析网页
page_film = bs.findAll(class_='h3')#获取每部电影的短地址
for film in page_film:
film_url = 'http://www.y80s.com'+ (film.find('a')['href']).strip()#拼接成每部电影实际地址
print('正在获取电影详情页链接:'+ film_url)
#用yield语句把构造好的request对象传递给引擎。用scrapy.Request构造request对象。callback参数设置调用parse_page方法
yield scrapy.Request(film_url,callback=self.parse_page)
# 解析和提取每部电影信息的数据
def parse_page(self,response):
bs = bs4.BeautifulSoup(response.text,'html.parser')
item = MoviesItem()# 实例化MoviesItem这个类
#下面几行获取相关数据
item['film_name'] = bs.find('h1',class_='font14w').text.strip().replace(' ','')
item['film_story'] = bs.find(id='movie_content').text[:-12]
item['film_score'] = bs.find('div',style='float:left; margin-right:10px;').text.strip()[-3:]
item['film_play_url'] = 'http://www.y80s.com'+ bs.find('div',class_='info').findAll('a')[-1]['href']
item['xldown_url'] = bs.find(class_='xunlei dlbutton1').find('a')['href']
yield item
# 用yield语句把item传递给引擎
第五步:Item Pipeline(交房)
from itemadapter import ItemAdapter
import mysql.connector
# 定义一个MoviesPipeline类,负责处理item
class MoviesPipeline(object):
# 初始化函数 当类实例化时这个方法会自启动
def __init__(self):
# 创建数据库连接
self.db = mysql.connector.connect(user='root',passwd='huantian',db='learn')
# 创建游标
self.cursor = self.db.cursor()
# process_item是默认的处理item的方法,就像parse是默认处理response的方法
def process_item(self, item, spider):
# 创建插入语句
sql_insert = "INSERT INTO `movie`(`name`, `story`, `score`,`play_url`, `down_url`)VALUE\
S('{}','{}','{}','{}','{}')".format(item['film_name'],item['film_story'],item['film_score'],item['film_play_url'],item['xldown_url'])
# 执行插入语句
self.cursor.execute(sql_insert)
# 提交数据库
self.db.commit()
# close_spider是当爬虫结束运行时,这个方法就会执行(仅执行一次)#
# 对应的还有open_spider方法开始运行时执行,可以用来创建保存文件时候打开文件等操作。
def close_spider(self,spider):
print('爬虫结束!')
self.cursor.close()
self.db.close()
结语
知识是海洋,越学习只会发现海洋的辽阔。
While True:learn()
加油吧,骚年~