本文基于scrapy框架,获取链家网楼盘信息。
安装python3
- 下载python3,并安装。
- 配置环境变量:
- 添加系统变量
PYTHON_HOME
值为 python目录,比如我的为:D:\Program Files\Python\Python36
- 添加path:
%PYTHON_HOME%
和%PYTHON_HOME%\Scripts
- 添加系统变量
安装scrapy
-
安装scrapy命令:
pip install scrapy
-
Twisted等包可能会安装失败,根据提示,对于安装失败的可以到这里下载对应平台的whl文件。再本地安装。
本地安装命令:
pip install {whl文件绝对路径}
制作scrapy爬虫
创建项目
创建scrapy项目命令:scrapy startproject lianjiaSpider
其中 mySpider是项目名称。创建后目录结构如图
确定爬虫目标信息
如下图,打算爬取列表实体中9个信息点。
image.png
- 打开打开lianjiaSpider>目录下的items.py
- 创建scrapy.Item 的子类 HouseItem。内容如下
class HouseItem(scrapy.Item):
name = scrapy.Field()
house_type = scrapy.Field()
sale_status = scrapy.Field()
location_1 = scrapy.Field()
location_2 = scrapy.Field()
location_3 = scrapy.Field()
area = scrapy.Field()
price = scrapy.Field()
price_unit = scrapy.Field()
制作爬虫
新建文件spiders/lianjia_spider.py,lianjia_spider.py
源码如下:
import scrapy
from lianjiaSpider.items import HouseItem
class lianjiaSpider(scrapy.Spider):
# 爬虫的识别名称,必须唯一.
name = 'lianjia_spider'
# 限制爬虫只爬取这个域名下的网页
allowed_domains = ['lianjia.com']
# 爬虫的起始页
start_urls = ['https://gz.fang.lianjia.com/loupan/pg{}/'.format(i) for i in range(2, 5)]
def parse(self, response):
items_li = response.xpath("//ul[@class='resblock-list-wrapper']//li[@class='resblock-list']")
for item_li in items_li:
# 根据xpath获取目标元素信息
name = item_li.xpath("div//a[@class='name']/text()").extract_first()
house_type = item_li.xpath("div//span[@class='resblock-type']/text()").extract_first()
sale_status = item_li.xpath("div//span[@class='sale-status']/text()").extract_first()
location_1 = item_li.xpath("div//div[@class='resblock-location']//span[position()=1]/text()").extract_first()
location_2 = item_li.xpath("div//div[@class='resblock-location']//span[position()=2]/text()").extract_first()
location_3 = item_li.xpath("div//div[@class='resblock-location']//a[last()]/text()").extract_first()
area = item_li.xpath("div//div[@class='resblock-area']/span/text()").extract_first()
price = item_li.xpath("div//div[@class='main-price']/span[position()=1]/text()").extract_first()
price_unit = item_li.xpath("div//div[@class='main-price']/span[position()=2]/text()").extract_first()
item = HouseItem()
item['name'] = name
item['house_type'] = house_type
item['sale_status'] = sale_status
item['location_1'] = location_1
item['location_2'] = location_2
item['location_3'] = location_3
item['area'] = area
item['price'] = price
item['price_unit'] = price_unit.strip()
yield item
处理item: 编写pipeline
注意:
- 笔者这里是将信息保存到mysql 数据库,所以依赖PyMySQL包,没有安装的可以通过命令
pip3 install PyMySQL
安装。 - 为做演示,mysql只创建了三个字段。实体信息获取较多,但是只使用了三个字段。
mysql 建表语句:
CREATE TABLE `t_house` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`NAME` varchar(200) DEFAULT NULL,
`location_3` varchar(300) DEFAULT NULL,
`price` int(11) NOT NULL,
PRIMARY KEY (`id`)
);
pipeline.py
中创建item 通道。内如如下:
from lianjiaSpider.items import HouseItem
import pymysql
class LianjiaspiderPipeline(object):
def __init__(self):
self.db = pymysql.connect("localhost", "loginName", "passworld", "test01")
self.cursor = self.db.cursor()
def process_item(self, item, spider):
if isinstance(item, HouseItem):
sql = "insert into t_house(name ,location_3,price) value('%s','%s','%s')" % (item['name'], item['location_3'], int(item['price']))
self.cursor.execute(sql)
return item
def close_spider(self, spider):
self.db.commit()
self.db.close()
settings.py
中开启通道配置
ITEM_PIPELINES = {
'lianjiaSpider.pipelines.LianjiaspiderPipeline': 300,
}
取消Robots协议(settings.py配置
)。
ROBOTSTXT_OBEY = False
启动scrapy 爬虫
回到主目录,执行命令 scrapy crawl lianjia_spider
执行成功后,查看mysql,数据如下
到此为止,爬虫从爬取数据到入库,一个基本的过程就结束了。
很多网站会有反爬虫,scrapy对这方面也有处理,主要的就是更换User-Agent和代理IP。这个以后做相关演示。
总的一个感慨就是,py很简洁,功能确很强大。一点代码量就可以完成java需要很多代码才能完成的事。
网友评论