打开京东的数码相机页面,进行分析,右键某个商品进行检查,发现商品详情页的链接地址
可以使用XPath Helper进行验证是否获取到每个商品的详情页的链接(XPath Helper插件可以在google应用商店获取)
进入商品详情页,爬取我们需要的信息(下图是爬取商品的编号)
思路大概就是在京东商城的首页,在搜索栏输入数码相机,然后再获取每个数码相机的详情页,最后在详情页爬取我们需要的信息(编号,名称,店铺,产地,品牌,毛重,像素,某日的价格)
开始写代码
在cmd命令行输入 scrapy startproject jd
在进入创建的jd目录,输入 scrapy genspider jdspider jd.com
使用Pycharm打开我们刚才所创建的项目
在item.py中,写我们所需要爬取的信息
import scrapy
class JdItem(scrapy.Item):
# define the fields for your item here like:
# name = scrapy.Field()
#商品编号
tnumber = scrapy.Field()
#商品名称
title = scrapy.Field()
#价格
price = scrapy.Field()
#商品产地
commodity_origin = scrapy.Field()
#品牌
brand = scrapy.Field()
#商品毛重
commodity_weight = scrapy.Field()
#像素
pixel = scrapy.Field()
#店铺名
shop = scrapy.Field()
在settings.py中配置如下信息
USER_AGENT = 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/83.0.4103.116 Safari/537.36'
# Obey robots.txt rules
ROBOTSTXT_OBEY = False
发现详情页没有我们需要的价格信息,价格信息在https://p.3.cn/prices/mgets?skuIds=J_8524940网址中,
https://p.3.cn/prices/mgets?skuIds=J_+商品编号,就是每个商品的价格信息,如下图
在jdspider.py中编写如下代码
# -*- coding: utf-8 -*-
import scrapy
import re
import json
import requests
from jd.items import JdItem
class JdspiderSpider(scrapy.Spider):
name = 'jdspider'
allowed_domains = ['jd.com']
start_urls = ['https://search.jd.com/Search?keyword=%E6%95%B0%E7%A0%81%E7%9B%B8%E6%9C%BA']
# 获取100页的链接
def parse(self,response):
for i in range(1, 7):
next_url = "https://search.jd.com/Search?keyword=%E6%95%B0%E7%A0%81%E7%9B%B8%E6%9C%BA&page=" + str(i * 2 - 1)
yield scrapy.Request(next_url, callback=self.parse_link)
#获取每页详情页的链接
def parse_link(self, response):
#获取每个数码相机的url
url_lists = response.xpath("//li[@class='gl-item']//div[@class='p-img']")
for temp in url_lists:
temp_url = "https:"+temp.xpath("./a/@href").get()
yield scrapy.Request(url=temp_url, callback=self.parse_digital)
#数码相机的详情页
def parse_digital(self,response):
item = JdItem()
#获取商品编号
item['tnumber'] = response.xpath("//ul[@class='parameter2 p-parameter-list']/li[2]/@title").extract_first()
#商品名称
item['title'] = response.xpath("//ul[@class='parameter2 p-parameter-list']/li[1]/@title").extract_first()
#价格url
price_url = "https://p.3.cn/prices/mgets?skuIds=J_"+str(item['tnumber'])
res = requests.get( price_url)
#print(price_url)
ret = res.content.decode()
#print(ret)
result = json.loads(ret)
#print(res)
item['price'] = result[0]['p']
# 品牌
item['brand'] = response.xpath("//ul[@class='p-parameter-list']/li[1]/@title").extract_first()
#print(brand)
#商品产地
item['commodity_origin'] = re.findall('商品产地:([\s\S]*?)</li>\n',response.text)
#商品毛重
item['commodity_weight'] = re.findall('商品毛重:([\s\S]*?)</li>\n',response.text)
#像素
item['pixel'] = re.findall('像素:([\s\S]*?)</li>\n',response.text)
#店铺名
item['shop'] = re.findall('店铺:([\s\S]*?)</li>\n',response.text)
#列表转换成字符串
shop1 = ''.join(item['shop'])
if len(shop1)==0:
item['shop'] = shop1
if len(shop1)>0:
#将a标签去除
shop2 = shop1.split(">")
shop3 = shop2[1].split("<")
item['shop'] = shop3[0]
with open('shuma1.csv', 'a', encoding='utf-8') as f:
#f.write('编号,名称,店铺,产地,品牌,毛重,像素,2020-7-3的价格\n')
#保存数据
f.write('{},{},{},{},{},{},{},{}\n'.format(item['tnumber'], item['title'], item['shop'], item['brand'],item['commodity_origin'],item['commodity_weight'],item['pixel'],item['price']))
爬取结果(因为有些商品信息没有店铺、产地、品牌等信息,所以有些爬取的数据是空值,需要自己手动筛选,某一天的价格信息可以累加在最后一列)