晒晒我家小院子

0%

Scrapy-redis

spider编写
1
2
3
4
5
6
class MySpider(RedisSpider):
name = 'myspider'

def parse(self, response):
# do stuff
pass
setting
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
# 启用调度redis中的存储请求队列
SCHEDULER = "scrapy_redis.scheduler.Scheduler"
# 确保所有蜘蛛通过redis共享同一个过滤器。
DUPEFILTER_CLASS = "scrapy_redis.dupefilter.RFPDupeFilter"
# 不清理redis队列,允许暂停/恢复爬网。
SCHEDULER_PERSIST = True
# 使用优先级队列调度请求。(默认)
SCHEDULER_QUEUE_CLASS = 'scrapy_redis.queue.PriorityQueue'
# 备用队列。
SCHEDULER_QUEUE_CLASS = 'scrapy_redis.queue.FifoQueue'
SCHEDULER_QUEUE_CLASS = 'scrapy_redis.queue.LifoQueue'
# 防止蜘蛛在分布式爬网时关闭的最大空闲时间。这仅在队列类为SpiderQueue或SpiderStack时有效,并且在蜘蛛第一次启动时也可能会阻止这么长的时间(因为队列为空)。
SCHEDULER_IDLE_BEFORE_CLOSE = 10
# 将爬取的item存储在redis数据库中
ITEM_PIPELINES = {
'scrapy_redis.pipelines.RedisPipeline': 300
}
# 存储item的redis的key
REDIS_ITEMS_KEY = '%(spider)s:items'
# 默认情况下,item的序列化程序是ScrapyJSONEncoder。
REDIS_ITEMS_SERIALIZER = 'json.dumps'
# 连接Redis时,使用的主机和端口(可选)。
REDIS_HOST = 'localhost'
REDIS_PORT = 6379
# 指定用于连接Redis的完整URL(可选)。
# 如果设置,它将优先于REDIS_HOST和REDIS_PORT设置。
REDIS_URL = 'redis://user:pass@hostname:9001'
# 自定义Redis客户端参数(即:套接字超时等)
REDIS_PARAMS = {}
# 是否对初始urls去重,默认False,为不去重
REDIS_START_URLS_AS_SET = False
# 获取起始URL默认的redis key。
REDIS_START_URLS_KEY = '%(name)s:start_urls'
# 使用utf-8以外的其他编码对redis进行编码,默认是utf-8
# REDIS_ENCODING = 'latin1'
启动spider
1
2
3
4
5
# 1. run the spider:
scrapy runspider myspider.py
# 2. push urls to redis:
redis-cli lpush myspider:start_urls http://google.com
# 两者先后顺序不重要,因为 SCHEDULER_IDLE_BEFORE_CLOSE = 10 会等待

scrapy的一些知识点

1
命令加上参数 --nolog 可以去掉log日志输出

异常处理

1
2
3
4
5
from scrapy.downloadermiddlewares.retry import RetryMiddleware # 参考这个写即可
# 设置最大等待时间、失败重试次数
DOWNLOAD_TIMEOUT = 10
RETRY_ENABLED = True # 失败重试
RETRY_TIMES = 5

scrapy复习笔记

1
allowed_domains = [] # 与OffsiteMiddleware中间件挂钩
1
scrapy.FormRequest() # post请求
1
2
from scrapy.downloadermiddlewares.retry import RetryMiddleware 
# 异常处理,必须看源码,必须对异常进行处理
选择器
1
2
3
4
get()和getall()
get(default='not-found') #设置默认值
.attrib['src'] # 获取属性值,它返回第一个匹配元素的属性
scrapy css特有的::text和::attr(name)
1
2
3
4
>>> response.css('base').attrib   # 变成dict了
{'href': 'http://example.com/'}
>>> response.css('base').attrib['href']
'http://example.com/'
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
# 例子
>>> response.xpath('//base/@href').get()
'http://example.com/'

>>> response.css('base::attr(href)').get()
'http://example.com/'

>>> response.css('base').attrib['href']
'http://example.com/'

>>> response.xpath('//a[contains(@href, "image")]/@href').getall()
['image1.html',
'image2.html',
'image3.html',
'image4.html',
'image5.html']

>>> response.css('a[href*=image]::attr(href)').getall()
['image1.html',
'image2.html',
'image3.html',
'image4.html',
'image5.html']

>>> response.xpath('//a[contains(@href, "image")]/img/@src').getall()
['image1_thumb.jpg',
'image2_thumb.jpg',
'image3_thumb.jpg',
'image4_thumb.jpg',
'image5_thumb.jpg']

>>> response.css('a[href*=image] img::attr(src)').getall()
['image1_thumb.jpg',
'image2_thumb.jpg',
'image3_thumb.jpg',
'image4_thumb.jpg',
'image5_thumb.jpg']
1
2
3
4
>>> response.xpath('//span/text()').get()
'good'
>>> response.css('span::text').get()
'good'
1
2
3
4
5
Selector类可以用文本直接构造,用于xpath解析
>>> from scrapy.selector import Selector
>>> body = '<html><body><span>good</span></body></html>'
>>> Selector(text=body).xpath('//span/text()').get()
'good'
1
response.css('.shout').xpath('./time/@datetime').getall()  # xpath的'.'点号必须加上
scrapy shell
1
2
3
4
fetch(url[, redirect=True])   #  Fetch URL and update local objects
fetch(req) # Fetch a scrapy.Request and update local objects
shelp() # Shell help (print this help) 很重要,常用,类似于help
view(response) # View response in a browser
1
2
3
# scrapy.shell.inspect_response的用法如下:便于运行时,检查
from scrapy.shell import inspect_response
inspect_response(response, self)
请求
1
FormRequest.from_response()

使用scrapy的shell测试网站

1
2
3
4
5
# 给scrapy shell 调试加上headers
scrapy shell # 进入shell,但没有url
headers = {'User-Agent': 'User-Agent:Mozilla/5.0 (Windows NT 6.1; rv:2.0.1) Gecko/20100101 Firefox/4.0.1'}
req = scrapy.Request(url='url',headers=headers)
fetch(req) # 如此就等价于scrapy shell url # 添加了headers

Python常用内置库

0.内置函数

  • chr() 转换一个[0, 255]之间的整数为对应的ASCII字符
  • ord() 将一个ASCII字符转换为对应整数

1.copy

  • copy.deepcopy(a)
  • copy.copy(a)

2.random

  • random.shuffle(list) 洗牌
  • random.randint(a,b) 随机整数[a,b]
  • random.random() 随机(0,1)
  • random.choice(seq)
  • random.randrange(0, 101, 2) 包前不包后

3.os

  • 负责与操作系统交互
  • os.remove()
  • os.rename(src, dst) 重命名
  • os.mkdir()
  • os.remkdir() 删除目录
  • os.getcwd()
  • os.chdir() 改变当前脚本的工作路径,相当于shell下的cd

4.sys

  • 负责与Python解释器交互
  • sys.exit(0)
  • sys.path 解释器的环境变量是list格式

5.time

  • time.time() 时间戳数字
  • time.localtime() 返回struct_time对象
  • time.asctime() 格式化输出
  • time.strftime(“%Y-%m-%d %H:%M:%S”) 格式化输出
  • time.strptime(“2016/05/22”,”%Y/%m/%d”) 返回struct_time对象

6.datetime

  • a = datetime.datetime.now()
  • a.strftime(“%Y-%m-%d %H:%M:%S”) 格式化输出
  • a.utctimetuple() # 返回struct_time对象,与time.localtime()对象类型相同,值也相同
  • datetime.timedelta(day=3, hours=12, minutes=30, seconds=30)

Python标准数据结构

一、数字 Number

1.支持类型
  • int、float、complex
2.转换
  • int(x) , float(x) , complex(x[,y])
3.整数表示
  • 0xA1 , 0o241 , 161 , 0b10100001
  • hex() , otc() , int() , bin()