淘宝增加爬虫并分析
This commit is contained in:
@@ -56,21 +56,31 @@
|
||||
|
||||
## show
|
||||
|
||||
- bilibili自动登录测试正常,成功率98%
|
||||
### bilibili自动登录测试正常,成功率98%
|
||||
|
||||

|
||||
|
||||
- web微信
|
||||
### web微信
|
||||
|
||||
|
||||

|
||||
|
||||
- 图虫爬虫
|
||||
### 图虫爬虫
|
||||
|
||||

|
||||
|
||||

|
||||
|
||||
### 淘宝 - 淘宝网
|
||||
- taobao.py 为模拟登录
|
||||
- 剩下的为爬虫
|
||||
|
||||
```
|
||||
1. 爬取淘宝各子标签,按销量排名商品信息,按分类保存至MongoDB
|
||||
2. 通过pandas进行数据分析
|
||||
3. 将商品在各省分布、销量排行、地图分布等通过matplotlib绘图显示
|
||||
```
|
||||
|
||||
## tips of pull request
|
||||
|
||||
- 欢迎大家一起来 pull request
|
||||
|
||||
Vendored
BIN
Binary file not shown.
@@ -0,0 +1,11 @@
|
||||
# Automatically created by: scrapy startproject
|
||||
#
|
||||
# For more information about the [deploy] section see:
|
||||
# https://scrapyd.readthedocs.io/en/latest/deploy.html
|
||||
|
||||
[settings]
|
||||
default = taobao.settings
|
||||
|
||||
[deploy]
|
||||
#url = http://localhost:6800/
|
||||
project = taobao
|
||||
@@ -0,0 +1,21 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# Define here the models for your scraped items
|
||||
#
|
||||
# See documentation in:
|
||||
# https://doc.scrapy.org/en/latest/topics/items.html
|
||||
|
||||
import scrapy
|
||||
|
||||
|
||||
class TaobaoItem(scrapy.Item):
|
||||
# define the fields for your item here like:
|
||||
# name = scrapy.Field()
|
||||
goods_url=scrapy.Field()
|
||||
title=scrapy.Field()
|
||||
price=scrapy.Field()
|
||||
sell_count =scrapy.Field()
|
||||
goods_class=scrapy.Field()
|
||||
seller=scrapy.Field()
|
||||
area=scrapy.Field()
|
||||
|
||||
@@ -0,0 +1,103 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# Define here the models for your spider middleware
|
||||
#
|
||||
# See documentation in:
|
||||
# https://doc.scrapy.org/en/latest/topics/spider-middleware.html
|
||||
|
||||
from scrapy import signals
|
||||
|
||||
|
||||
class TaobaoSpiderMiddleware(object):
|
||||
# Not all methods need to be defined. If a method is not defined,
|
||||
# scrapy acts as if the spider middleware does not modify the
|
||||
# passed objects.
|
||||
|
||||
@classmethod
|
||||
def from_crawler(cls, crawler):
|
||||
# This method is used by Scrapy to create your spiders.
|
||||
s = cls()
|
||||
crawler.signals.connect(s.spider_opened, signal=signals.spider_opened)
|
||||
return s
|
||||
|
||||
def process_spider_input(self, response, spider):
|
||||
# Called for each response that goes through the spider
|
||||
# middleware and into the spider.
|
||||
|
||||
# Should return None or raise an exception.
|
||||
return None
|
||||
|
||||
def process_spider_output(self, response, result, spider):
|
||||
# Called with the results returned from the Spider, after
|
||||
# it has processed the response.
|
||||
|
||||
# Must return an iterable of Request, dict or Item objects.
|
||||
for i in result:
|
||||
yield i
|
||||
|
||||
def process_spider_exception(self, response, exception, spider):
|
||||
# Called when a spider or process_spider_input() method
|
||||
# (from other spider middleware) raises an exception.
|
||||
|
||||
# Should return either None or an iterable of Response, dict
|
||||
# or Item objects.
|
||||
pass
|
||||
|
||||
def process_start_requests(self, start_requests, spider):
|
||||
# Called with the start requests of the spider, and works
|
||||
# similarly to the process_spider_output() method, except
|
||||
# that it doesn’t have a response associated.
|
||||
|
||||
# Must return only requests (not items).
|
||||
for r in start_requests:
|
||||
yield r
|
||||
|
||||
def spider_opened(self, spider):
|
||||
spider.logger.info('Spider opened: %s' % spider.name)
|
||||
|
||||
|
||||
class TaobaoDownloaderMiddleware(object):
|
||||
# Not all methods need to be defined. If a method is not defined,
|
||||
# scrapy acts as if the downloader middleware does not modify the
|
||||
# passed objects.
|
||||
|
||||
@classmethod
|
||||
def from_crawler(cls, crawler):
|
||||
# This method is used by Scrapy to create your spiders.
|
||||
s = cls()
|
||||
crawler.signals.connect(s.spider_opened, signal=signals.spider_opened)
|
||||
return s
|
||||
|
||||
def process_request(self, request, spider):
|
||||
# Called for each request that goes through the downloader
|
||||
# middleware.
|
||||
|
||||
# Must either:
|
||||
# - return None: continue processing this request
|
||||
# - or return a Response object
|
||||
# - or return a Request object
|
||||
# - or raise IgnoreRequest: process_exception() methods of
|
||||
# installed downloader middleware will be called
|
||||
return None
|
||||
|
||||
def process_response(self, request, response, spider):
|
||||
# Called with the response returned from the downloader.
|
||||
|
||||
# Must either;
|
||||
# - return a Response object
|
||||
# - return a Request object
|
||||
# - or raise IgnoreRequest
|
||||
return response
|
||||
|
||||
def process_exception(self, request, exception, spider):
|
||||
# Called when a download handler or a process_request()
|
||||
# (from other downloader middleware) raises an exception.
|
||||
|
||||
# Must either:
|
||||
# - return None: continue processing this exception
|
||||
# - return a Response object: stops process_exception() chain
|
||||
# - return a Request object: stops process_exception() chain
|
||||
pass
|
||||
|
||||
def spider_opened(self, spider):
|
||||
spider.logger.info('Spider opened: %s' % spider.name)
|
||||
@@ -0,0 +1,32 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# Define your item pipelines here
|
||||
#
|
||||
# Don't forget to add your pipeline to the ITEM_PIPELINES setting
|
||||
# See: https://doc.scrapy.org/en/latest/topics/item-pipeline.html
|
||||
import pymongo
|
||||
|
||||
class TaobaoPipeline(object):
|
||||
def __init__(self,mongo_url,mongo_db):
|
||||
self.mongo_url=mongo_url
|
||||
self.mongo_db=mongo_db
|
||||
@classmethod
|
||||
def from_crawler(cls,crawler):
|
||||
return cls(
|
||||
mongo_url=crawler.settings.get("MONGO_URL"),
|
||||
mongo_db=crawler.settings.get("MONGO_DB")
|
||||
)
|
||||
|
||||
def open_spider(self, spider):
|
||||
self.client = pymongo.MongoClient(self.mongo_url)
|
||||
self.db = self.client[self.mongo_db]
|
||||
|
||||
def process_item(self, item, spider):
|
||||
sheet = self.db[item['goods_class']]
|
||||
if sheet.find_one({'goods_url':item['goods_url']}):
|
||||
print('数据已存在')
|
||||
else:
|
||||
sheet.insert(dict(item))
|
||||
|
||||
return item
|
||||
|
||||
@@ -0,0 +1,106 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# Scrapy settings for taobao project
|
||||
#
|
||||
# For simplicity, this file contains only settings considered important or
|
||||
# commonly used. You can find more settings consulting the documentation:
|
||||
#
|
||||
# https://doc.scrapy.org/en/latest/topics/settings.html
|
||||
# https://doc.scrapy.org/en/latest/topics/downloader-middleware.html
|
||||
# https://doc.scrapy.org/en/latest/topics/spider-middleware.html
|
||||
|
||||
BOT_NAME = 'taobao'
|
||||
|
||||
SPIDER_MODULES = ['taobao.spiders']
|
||||
NEWSPIDER_MODULE = 'taobao.spiders'
|
||||
|
||||
|
||||
# Crawl responsibly by identifying yourself (and your website) on the user-agent
|
||||
#USER_AGENT = 'taobao (+http://www.yourdomain.com)'
|
||||
|
||||
# Obey robots.txt rules
|
||||
ROBOTSTXT_OBEY = False
|
||||
|
||||
# Configure maximum concurrent requests performed by Scrapy (default: 16)
|
||||
#CONCURRENT_REQUESTS = 32
|
||||
|
||||
# Configure a delay for requests for the same website (default: 0)
|
||||
# See https://doc.scrapy.org/en/latest/topics/settings.html#download-delay
|
||||
# See also autothrottle settings and docs
|
||||
DOWNLOAD_DELAY = 3
|
||||
# The download delay setting will honor only one of:
|
||||
#CONCURRENT_REQUESTS_PER_DOMAIN = 16
|
||||
#CONCURRENT_REQUESTS_PER_IP = 16
|
||||
|
||||
# Disable cookies (enabled by default)
|
||||
COOKIES_ENABLED = False
|
||||
|
||||
# Disable Telnet Console (enabled by default)
|
||||
#TELNETCONSOLE_ENABLED = False
|
||||
|
||||
# Override the default request headers:
|
||||
#DEFAULT_REQUEST_HEADERS = {
|
||||
# 'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
|
||||
# 'Accept-Language': 'en',
|
||||
#}
|
||||
|
||||
# Enable or disable spider middlewares
|
||||
# See https://doc.scrapy.org/en/latest/topics/spider-middleware.html
|
||||
SPIDER_MIDDLEWARES = {
|
||||
# 'taobao.middlewares.TaobaoSpiderMiddleware': 543,
|
||||
'scrapy_splash.SplashDeduplicateArgsMiddleware': 100,
|
||||
|
||||
}
|
||||
|
||||
# Enable or disable downloader middlewares
|
||||
# See https://doc.scrapy.org/en/latest/topics/downloader-middleware.html
|
||||
DOWNLOADER_MIDDLEWARES = {
|
||||
# 'taobao.middlewares.TaobaoDownloaderMiddleware': 543,
|
||||
'scrapy_splash.SplashCookiesMiddleware': 723,
|
||||
'scrapy_splash.SplashMiddleware': 725,
|
||||
'scrapy.downloadermiddlewares.httpcompression.HttpCompressionMiddleware': 810,
|
||||
}
|
||||
|
||||
# Enable or disable extensions
|
||||
# See https://doc.scrapy.org/en/latest/topics/extensions.html
|
||||
#EXTENSIONS = {
|
||||
# 'scrapy.extensions.telnet.TelnetConsole': None,
|
||||
#}
|
||||
|
||||
# Configure item pipelines
|
||||
# See https://doc.scrapy.org/en/latest/topics/item-pipeline.html
|
||||
ITEM_PIPELINES = {
|
||||
'taobao.pipelines.TaobaoPipeline': 300,
|
||||
}
|
||||
|
||||
# Enable and configure the AutoThrottle extension (disabled by default)
|
||||
# See https://doc.scrapy.org/en/latest/topics/autothrottle.html
|
||||
#AUTOTHROTTLE_ENABLED = True
|
||||
# The initial download delay
|
||||
#AUTOTHROTTLE_START_DELAY = 5
|
||||
# The maximum download delay to be set in case of high latencies
|
||||
#AUTOTHROTTLE_MAX_DELAY = 60
|
||||
# The average number of requests Scrapy should be sending in parallel to
|
||||
# each remote server
|
||||
#AUTOTHROTTLE_TARGET_CONCURRENCY = 1.0
|
||||
# Enable showing throttling stats for every response received:
|
||||
#AUTOTHROTTLE_DEBUG = False
|
||||
|
||||
# Enable and configure HTTP caching (disabled by default)
|
||||
# See https://doc.scrapy.org/en/latest/topics/downloader-middleware.html#httpcache-middleware-settings
|
||||
#HTTPCACHE_ENABLED = True
|
||||
#HTTPCACHE_EXPIRATION_SECS = 0
|
||||
#HTTPCACHE_DIR = 'httpcache'
|
||||
#HTTPCACHE_IGNORE_HTTP_CODES = []
|
||||
HTTPCACHE_STORAGE = 'scrapy_splash.SplashAwareFSCacheStorage'
|
||||
DUPEFILTER_CLASS = 'scrapy_splash.SplashAwareDupeFilter'
|
||||
|
||||
# REDIRECT_ENABLED = False
|
||||
SPLASH_URL='http://localhost:8050'
|
||||
|
||||
# REDIS_URL='redis://:zkyr1006@localhost:6379/1'
|
||||
MONGO_URL = 'mongodb://admin:zkyr1006@localhost:28018'
|
||||
MONGO_DB='taobao'
|
||||
|
||||
# 遇到502,504,重复请求
|
||||
RETRY_HTTP_CODES = [502, 504]
|
||||
@@ -0,0 +1,4 @@
|
||||
# This package will contain the spiders of your Scrapy project
|
||||
#
|
||||
# Please refer to the documentation for information on how to create and manage
|
||||
# your spiders.
|
||||
@@ -0,0 +1,216 @@
|
||||
#!/home/zkfr/.local/share/virtualenvs/xf-5EfV3Nly/bin/python
|
||||
#-*- coding:utf-8 -*-
|
||||
# @author : MaLei
|
||||
# @datetime : 2018-10-06 12:50
|
||||
# @file : analysis.py
|
||||
# @software : PyCharm
|
||||
import numpy as np
|
||||
from pymongo import MongoClient
|
||||
from matplotlib import pyplot as plt
|
||||
import re,json,jieba,pandas
|
||||
from collections import Counter
|
||||
from wordcloud import WordCloud
|
||||
import seaborn as sns
|
||||
# matprotlib显示中文
|
||||
from pylab import *
|
||||
mpl.rcParams['font.sans-serif'] = ['SimHei']
|
||||
|
||||
# 从mongodb中获取数据
|
||||
def data_analysis(parameter):
|
||||
client = MongoClient('mongodb://admin:zkyr1006@localhost:28018')
|
||||
db = client.taobao
|
||||
colls = [db.内搭, db.外套, db.牛仔裤, db.秋季套装]
|
||||
data=[]
|
||||
for coll in colls:
|
||||
list_data=coll.aggregate([{'$group': {'_id': 0, parameter: {'$push': '$'+parameter}}}]).next()[parameter]
|
||||
data+=list_data
|
||||
return data
|
||||
# print(provience)
|
||||
|
||||
# 商品所属省份分布柱状图
|
||||
def provience():
|
||||
data=[]
|
||||
provs=data_analysis('area')
|
||||
# print(provience)
|
||||
for each in provs:
|
||||
prov = (each.split())[0]
|
||||
data.append(prov)
|
||||
count={}
|
||||
for i in data:
|
||||
count[i]=data.count(i)
|
||||
# print(count)
|
||||
prov=list(count.keys())
|
||||
nums=list(count.values())
|
||||
return prov,nums
|
||||
|
||||
def prov_plt():
|
||||
prov, nums = provience()
|
||||
plt.figure(figsize=(8, 4))
|
||||
plt.xticks(rotation=0)
|
||||
plt.bar(prov, nums, color='g')
|
||||
plt.xlabel('省份')
|
||||
plt.ylabel('数量')
|
||||
plt.title('不同省份数量分布图')
|
||||
plt.legend()
|
||||
plt.show()
|
||||
|
||||
# 词云及根据词云数据进行分析的柱状图
|
||||
def cloud_plt():
|
||||
def cloud_data():
|
||||
title=data_analysis('title')
|
||||
titles=[]
|
||||
# 对每个标题进行分词
|
||||
for each in title:
|
||||
title_cut=jieba.lcut(each)
|
||||
titles.append(title_cut)
|
||||
|
||||
# 剔除不需要的词语
|
||||
title_del=[]
|
||||
for line in titles:
|
||||
line_del=[]
|
||||
for word in line:
|
||||
if word not in ['2018','妈妈','❤','】','【',' ','Chinism','工作室','倔强']:
|
||||
line_del.append(word)
|
||||
title_del.append(line_del)
|
||||
# print(title_del)
|
||||
|
||||
# 元素去重,每个标题中不含重复元素
|
||||
title_clean=[]
|
||||
for each in title_del:
|
||||
line_dist=[]
|
||||
for word in each:
|
||||
if word not in line_dist:
|
||||
line_dist.append(word)
|
||||
title_clean.append(line_dist)
|
||||
|
||||
# 将所有词语转为一个list
|
||||
allwords_dist=[]
|
||||
for line in title_clean:
|
||||
for word in line:
|
||||
allwords_dist.append(word)
|
||||
# 把列表转为数据框
|
||||
allwords_dist=pandas.DataFrame({'allwords':allwords_dist})
|
||||
# 对词语进行分类汇总
|
||||
word_count=allwords_dist.allwords.value_counts().reset_index()
|
||||
# 添加列名
|
||||
word_count.columns=['word','count']
|
||||
# print(allwords_dist)
|
||||
return word_count,title_clean
|
||||
|
||||
def cloud_data_count():
|
||||
# 获取商品销量数据
|
||||
sell_count = data_analysis('sell_count')
|
||||
word_count, title_clean = cloud_data()
|
||||
ws_count = []
|
||||
# 商品中包含统计的词时,将其销量加入list
|
||||
for each in word_count.word:
|
||||
i = 0
|
||||
s_list = []
|
||||
for t in title_clean:
|
||||
if each in t:
|
||||
s_list.append(int(sell_count[i]))
|
||||
# print(s_list)
|
||||
i += 1
|
||||
# 统计一个关键词所包含商品的销量总数
|
||||
ws_count.append(sum(s_list))
|
||||
# 把列表转为数据框
|
||||
ws_count = pandas.DataFrame({'ws_count': ws_count})
|
||||
# 把word_count, ws_count合并为一个表
|
||||
word_count = pandas.concat([word_count, ws_count], axis=1, ignore_index=True)
|
||||
word_count.columns = ['word', 'count', 'ws_count']
|
||||
# 升序排列
|
||||
word_count.sort_values('ws_count', inplace=True, ascending=True)
|
||||
# 取最大30行数据
|
||||
df_ws = word_count.tail(30)
|
||||
return df_ws
|
||||
|
||||
# 图云部分
|
||||
word_count=cloud_data()[0]
|
||||
# 设置字体,背景颜色,字体最大号,
|
||||
w_c=WordCloud(font_path='/usr/local/lib/python3.6/dist-packages/matplotlib/mpl-data/fonts/ttf/simhei.ttf',
|
||||
background_color='white',
|
||||
max_font_size=60,
|
||||
margin=1)
|
||||
# 取前400个词进行可视化
|
||||
wc=w_c.fit_words({x[0]:x[1] for x in word_count.head(1000).values})
|
||||
# 设置图优化
|
||||
plt.imshow(wc,interpolation='bilinear')
|
||||
# 去除边框
|
||||
plt.axis('off')
|
||||
plt.show()
|
||||
|
||||
# 统计分析柱状图部分
|
||||
data = cloud_data_count()
|
||||
index = np.arange(data.word.size)
|
||||
# plt.figure(figsize=(6,12))
|
||||
plt.barh(index, data.ws_count, align='center', alpha=0.8)
|
||||
plt.yticks(index, data.word)
|
||||
# 添加数据标签
|
||||
for y, x in zip(index, data.ws_count):
|
||||
plt.text(x, y, '%.0f' % x, ha='left', va='center')
|
||||
plt.show()
|
||||
|
||||
|
||||
def impact_analysis():
|
||||
sell_count=pandas.DataFrame({'sell_count': data_analysis('sell_count')})
|
||||
price=[]
|
||||
for i in data_analysis('price'):
|
||||
p=i.split('-')
|
||||
p_i=p[0].split('.')
|
||||
price.append(p_i[0])
|
||||
price=pandas.DataFrame({'price':price})
|
||||
infos=pandas.concat([sell_count, price], axis=1, ignore_index=True)
|
||||
infos.columns = ['sell_count', 'price'] #一定注意定义到columns
|
||||
infos['sell_count']=infos.sell_count.astype('int')
|
||||
infos['price']=infos.sell_count.astype('int')
|
||||
infos['GMV']=infos['sell_count']*infos['price']
|
||||
# print(infos.GMV.dtype)
|
||||
sns.regplot(x='price',y='GMV',data=infos)
|
||||
# sns.lmplot(x='price',y='GMV',data=infos,x_jitter=.05)
|
||||
plt.show()
|
||||
|
||||
def mean_sale():
|
||||
prov,nums=provience()
|
||||
sell_count = data_analysis('sell_count')
|
||||
areas=[]
|
||||
count=[]
|
||||
for i in data_analysis('area'):
|
||||
areas.append((i.split(' '))[0])
|
||||
for each in prov:
|
||||
counts=[]
|
||||
for i in range(0,len(areas)):
|
||||
if each==areas[i]:
|
||||
counts.append(int(sell_count[i]))
|
||||
count.append(sum(counts))
|
||||
# print(count)
|
||||
count=pandas.DataFrame({'count':count})
|
||||
prov=pandas.DataFrame({'prov':prov})
|
||||
nums=pandas.DataFrame({'nums':nums})
|
||||
data = pandas.concat([nums,count], axis=1, ignore_index=True)
|
||||
data.columns = ['nums','count']
|
||||
data['nums']=data.nums.astype('int')
|
||||
m_l=data['count']/data['nums']
|
||||
mean_list=[]
|
||||
for each in m_l:
|
||||
each=str(each).split('.')
|
||||
mean_list.append(each[0])
|
||||
mean_list=pandas.DataFrame({'mean_list':mean_list},dtype=np.int)
|
||||
infos = pandas.concat([prov,mean_list], axis=1, ignore_index=True)
|
||||
infos.columns = ['prov','mean_list']
|
||||
infos['mean_list']=infos.mean_list.astype('int')
|
||||
infos.sort_values('mean_list',inplace=True,ascending=False)
|
||||
infos=infos.reset_index()
|
||||
index=np.arange(infos.mean_list.size)
|
||||
print(infos)
|
||||
plt.figure(figsize=(8,4))
|
||||
plt.bar(index,infos.mean_list,color='purple')
|
||||
plt.xticks(index,infos.prov,rotation=0)
|
||||
plt.xlabel('省份')
|
||||
plt.ylabel('平均销量')
|
||||
plt.title('不同省份销量分布')
|
||||
plt.show()
|
||||
|
||||
mean_sale()
|
||||
|
||||
# def hot_map():
|
||||
|
||||
@@ -0,0 +1,132 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
import scrapy,numpy
|
||||
from scrapy import Selector
|
||||
from taobao.items import TaobaoItem
|
||||
from scrapy.spiders import CrawlSpider, Rule
|
||||
from bs4 import BeautifulSoup
|
||||
import requests,re
|
||||
from scrapy_splash import SplashRequest
|
||||
from urllib.parse import urlencode
|
||||
|
||||
|
||||
class comicspider(scrapy.Spider):
|
||||
name = 'tb'
|
||||
allowed_domains=['www.taobao.com']
|
||||
start_urls=['https://www.taobao.com']
|
||||
|
||||
headers1 = {
|
||||
'Connection': 'keep-alive',
|
||||
'Host': 'www.taobao.com',
|
||||
'Accept-Encoding':'gzip, deflate, br',
|
||||
'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
|
||||
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:58.0) Gecko/20100101 Firefox/58.0'
|
||||
}
|
||||
|
||||
def start_requests(self):
|
||||
yield scrapy.Request(url=self.start_urls[0],callback=self.sub_nav,headers=self.headers1)
|
||||
|
||||
def sub_nav(self, response):
|
||||
page=Selector(response)
|
||||
# 女装、男装、内衣
|
||||
# sub_navs1=page.xpath('//ul[@class="service-bd"]/li[position()<2]/a/text()').extract()
|
||||
# print(sub_navs1)
|
||||
sub_urls1=page.xpath('//ul[@class="service-bd"]/li[position()<2]/a/@href').extract()
|
||||
# print(sub_urls1)
|
||||
for sub_url in sub_urls1:
|
||||
yield scrapy.Request(url=sub_url,callback=self.parse0,headers=self.headers1,dont_filter=True)
|
||||
|
||||
def parse0(self, response):
|
||||
headers2 = {
|
||||
'Connection': 'keep-alive',
|
||||
'Host': 's.taobao.com',
|
||||
'Accept-Encoding': 'gzip, deflate, br',
|
||||
'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
|
||||
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:58.0) Gecko/20100101 Firefox/58.0'
|
||||
}
|
||||
page=Selector(response)
|
||||
# 连衣裙、毛衫/内搭、秋外套……
|
||||
sub_navs11=page.xpath('//dl[@class="theme-bd-level2"]/dt/div/a/text()').extract()
|
||||
del sub_navs11[-1]
|
||||
sub_urls11=page.xpath('//dl[@class="theme-bd-level2"]/dt/div/a/@href').extract()
|
||||
del sub_urls11[-1]
|
||||
for i in range(0,len(sub_urls11)):
|
||||
page_urls=[]
|
||||
page_urls.append(sub_urls11[i]+'&sort=sale-desc')
|
||||
s=0
|
||||
sub_nav=sub_navs11[i]
|
||||
for j in range(1,20):
|
||||
# for j in range(0, 1):
|
||||
senddata = {
|
||||
'sort':'sale-desc',
|
||||
'bcoffset': '0',
|
||||
's': s
|
||||
}
|
||||
page_url=sub_urls11[i]+'&'+ urlencode(senddata)
|
||||
page_urls.append(page_url)
|
||||
s+=60
|
||||
# print(page_urls)
|
||||
|
||||
for page_url in page_urls:
|
||||
yield SplashRequest(page_url,self.parse1,args={'wait':0.5},splash_headers=headers2,dont_filter=True,meta={'sub_nav':sub_nav})
|
||||
# yield scrapy.Request(page_url,callback=self.parse1,headers=headers2,dont_filter=True,meta={'sub_nav':sub_nav})
|
||||
|
||||
def parse1(self, response):
|
||||
headers3 = {
|
||||
'Connection': 'keep-alive',
|
||||
'Host': 'item.taobao.com',
|
||||
'Accept-Encoding': 'gzip, deflate, br',
|
||||
'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
|
||||
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:58.0) Gecko/20100101 Firefox/58.0'
|
||||
}
|
||||
page=Selector(response)
|
||||
goods_urls=page.xpath('//div[@class="grid g-clearfix"]/div[@class="items"]/div/div[3]/div[2]/a/@href').extract()
|
||||
# goods_class=page.xpath('//div[@class="grid g-clearfix"]/div[@class="items"]/div[1]/div[3]/div[2]/a/span[@class="H"]/text()').extract()
|
||||
goods_class=response.meta['sub_nav']
|
||||
areas = page.xpath('//div[@class="row row-3 g-clearfix"]/div[@class="location"]/text()').extract()
|
||||
sell_counts=page.xpath('//div[@class="deal-cnt"]/text()').extract()
|
||||
|
||||
# print(goods_urls)
|
||||
for i in range(0,len(goods_urls)):
|
||||
area=areas[i]
|
||||
sell_count=sell_counts[i]
|
||||
goods_url='http:'+goods_urls[i]
|
||||
yield scrapy.Request(goods_url,self.parse2,headers=headers3,dont_filter=True,
|
||||
meta={'goods_url':goods_url,
|
||||
'goods_class':goods_class,
|
||||
'area':area,
|
||||
'sell_count':sell_count})
|
||||
|
||||
def parse2(self, response):
|
||||
item=TaobaoItem()
|
||||
page=Selector(response)
|
||||
# print(response.text)
|
||||
item['title']=page.xpath('//head/title/text()').extract()[0][:-4]
|
||||
item['goods_url']=response.meta['goods_url']
|
||||
item['goods_class']=response.meta['goods_class']
|
||||
item['price']=page.xpath('//strong[@id="J_StrPrice"]/em[@class="tb-rmb-num"]/text()').extract()[0]
|
||||
item['sell_count']=response.meta['sell_count'][:-3]
|
||||
item['area']=response.meta['area']
|
||||
# item['trade']=page.xpath('//div[@class="tb-sell-counter"]/a/strong/text()').extract()
|
||||
seller= page.xpath('//div[@class="tb-shop-name"]/dl/dd/strong/a/@title').extract()
|
||||
if len(seller)==1:
|
||||
item['seller']=seller[0]
|
||||
else:
|
||||
seller=page.xpath('//span[@class="shop-name-title"]/@title').extract()
|
||||
if len(seller)==1:
|
||||
item['seller'] = seller[0]
|
||||
else:
|
||||
seller = page.xpath('//span[@class="shop-name-title"]/@title').extract()
|
||||
if len(seller) == 1:
|
||||
item['seller'] = seller[0]
|
||||
else:
|
||||
item['seller'] = '未知'
|
||||
|
||||
yield item
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -0,0 +1,48 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
import requests
|
||||
|
||||
# headers = {
|
||||
# 'Connection': 'keep-alive',
|
||||
# 'Host': 'item.taobao.com',
|
||||
# 'Accept-Encoding': 'gzip, deflate, br',
|
||||
# 'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
|
||||
# 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:58.0) Gecko/20100101 Firefox/58.0'
|
||||
# }
|
||||
# url='https://item.taobao.com/item.htm?spm=a219r.lm874.14.1.422f2140YG82hc&id=574990577169&ns=1&abbucket=20#detail'
|
||||
# # yield SplashRequest(page_url, self.parse1, args={'wait': 0.5}, splash_headers=self.headers, dont_filter=True)
|
||||
# page=requests.get(url,headers=headers)
|
||||
# print(page.text)
|
||||
import re
|
||||
# Start your middleware class
|
||||
class ProxyMiddleware(object):
|
||||
# overwrite process request
|
||||
def process_request(self, request, spider):
|
||||
# Set the location of the proxy
|
||||
request.meta['proxy'] =self.proxy_test()
|
||||
|
||||
def proxy_test(self):
|
||||
# ....
|
||||
def get_proxy():
|
||||
return requests.get("http://192.168.1.137:8001/get/").text
|
||||
|
||||
def delete_proxy(proxy):
|
||||
requests.get("http://192.168.1.137:8001/delete/?proxy={}".format(proxy))
|
||||
|
||||
proxy = "http://{}".format(get_proxy())
|
||||
try:
|
||||
requests.get('https://www.baidu.com', proxies={"proxy": proxy})
|
||||
print(proxy,'代理可用')
|
||||
# 使用代理访问
|
||||
return proxy
|
||||
except Exception:
|
||||
# 出错1次, 删除代理池中代理
|
||||
delete_proxy(proxy)
|
||||
return None
|
||||
|
||||
DOWNLOADER_MIDDLEWARES = {
|
||||
# 'taobao.middlewares.TaobaoDownloaderMiddleware': 543,
|
||||
'scrapy_splash.SplashCookiesMiddleware': 723,
|
||||
'scrapy_splash.SplashMiddleware': 725,
|
||||
'scrapy.downloadermiddlewares.httpcompression.HttpCompressionMiddleware': 810,
|
||||
'taobao.middlewares.ProxyMiddleware': 100,
|
||||
}
|
||||
Reference in New Issue
Block a user