欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

爬梯:Redis全解析(二)

程序员文章站 2022-07-13 08:35:44
...

学习资源整理自:B站《狂神说》
书接上回

11、Redis配置文件详解

redis.conf以下都是默认配置

######### INCLUDES #########
# 包含,可以想properties一样包含其他配置文件
# include /path/to/local.conf
# include /path/to/other.conf
######### NETWORK ##########
# 绑定地址,可以接收请求的链接,改成 0.0.0.0 或者 * 表示通配
bind 127.0.0.1

# 保护模式,非本机访问需要将其关闭
protected-mode yes

port 6379 # 监听端口
######### GENERAL ########
# 以守护进程的方式运行,默认no,意思是是否可以后台运行redis
daemonize no

# 如果以后台方式运行,我们需要制定一个pid文件
pidfile /var/run/redis_6379.pid

# 日志级别
# Specify the server verbosity level.
# This can be one of:
# debug (a lot of information, useful for development/testing)
# verbose (many rarely useful info, but not a mess like the debug level)
# notice (moderately verbose, what you want in production probably) 生产环境适用
# warning (only very important / critical messages are logged)
loglevel notice

logfile "" # 日志文件名

databases 16 # 数据库数量,默认16个

#是否显示logo,就是运行redis-server的时候那个redis logo
always-show-logo yes

########## SNAPSHOTTING  ########
# 快照 

# 持久化的执行规则,复合条件则执行一次数据持久化 .rdb .aof
# 如果900秒内,有至少1个key修改过
# 如果300秒内,有至少10个key修改过
# 如果60秒内,至少有10000个key修改过
save 900 1
save 300 10
save 60 10000

# 持久化出错,是否继续工作
stop-writes-on-bgsave-error yes

rdbcompression yes # 是否压缩rdb文件(压缩会消耗cpu资源)

rdbchecksum yes # 保存rdb文件的时候,进行错误的检查校验

dbfilename dump.rdb # rdb文件名

dir ./   # rdb文件保存的目录 

########## SECURITY #########
# 密码,默认是注释掉,没有密码的
# requirepass foobared
# 也可以通过命令修改密码:config set requirepass 123

######### CLIENTS ##########
# 最大连接数,默认不限制,指的是同时存活的redis客户端
# maxclients 10000

######## MEMORY MANAGEMENT ########
# 最大内存容量
# maxmemory <bytes>

# 内存满了之后的处理策略
# maxmemory-policy 六种方式
# 1、volatile-lru:只对设置了过期时间的key进行LRU(默认值) 
# 2、allkeys-lru : 删除lru算法的key   
# 3、volatile-random:随机删除即将过期key   
# 4、allkeys-random:随机删除   
# 5、volatile-ttl : 删除即将过期的   
# 6、noeviction : 永不过期,返回错误
# maxmemory-policy noeviction

####### APPEND ONLY MODE #######
# aof
# 默认不开启aof模式,默认使用rdb模式
appendonly no    
    
# aof持久化文件名
appendfilename "appendonly.aof"
    
# aof同步模式 
# appendfsync always  # 每次修改都会 sync,比较消耗性能
appendfsync everysec  # 每秒执行一次sync,可能会丢失1秒的数据
# appendfsync no # 不执行 sync,操作系统自己同步数据

12、Redis持久化

概念

Redis是内存数据库,数据属于断电既失的情况,所以需要持久化的能力。

redis有两种持久化策略 rdb 和 aof,默认使用rdb模式。

触发机制:

1、save规则,满足则执行rdb持久化

2、执行flushall

3、退出redis

数据恢复:

当redis启动的时候,会自动检查redis.conf中配置的持久化规则,去寻找是否有对应的持久化文件,如果有则会回复文件中的数据。

rdb

redis database

在指定持久化条件符合时,将内存中的数据集写入磁盘中。

redis会创建一个fork子进程来进行持久化操作:

1、首先将数据写入一个临时文件中;

2、等到全部数据都写入临时文件后,再用这个临时的rdb文件替代上一次持久化的rdb文件,成为正式rdb文件。

在整个持久化过程中,全部io操作都由fork进程完成,确保了主进程的高性能。

爬梯:Redis全解析(二)

redis.conf

dbfilename dump.rdb # rdb文件名
dir ./   # rdb文件保存的目录 

优点:高性能、适合大规模恢复数据

缺点:可能会丢失最后一次持久化的数据(持久化过程中宕机等情况)、fork进程会占用一定的系统资源

aof

append only file 将命令追加到文件

aof策略是指,将每一条写指令以日志的形式存入aof文件,在需要恢复时redis会将aof文件中的写指令逐行执行

aof文件修复:

如果aof文件遭到破坏,aof模式的redis将无法启动。使用redis-check-aof工具修复:

redis-check-aof --fix appendonly.aof

爬梯:Redis全解析(二)

redis.conf

##### APPEND ONLY MODE #####
# 默认不开启,修改为yes重启生效
appendonly no
appendfilename "appendonly.aof"

# appendfsync always
appendfsync everysec
# appendfsync no

# 是否不需要重写aof文件
no-appendfsync-on-rewrite no

# 当aof文记达到64兆的100%时,重写一个新的文件来继续存储指令
auto-aof-rewrite-percentage 100
auto-aof-rewrite-min-size 64mb

优点

1、数据的完整性会更好

2、最多丢失1秒的数据

3、不需要同步则不需要fork进程周期进行持久化

缺点

1、aof的文件远大于rdb的文件大小

2、数据恢复的速度慢于rdb

持久化总结扩展

  1. RDB持久化方式能够在指定的时间间隔内对数据进行快照存储
  2. AOF持久化方式记录每次对服务器的写操作,当服务器重启的时候会重新执行这些命令来恢复原始数据,AOF命令以Redis协议追加保存命令到文件末尾,Redis还能对AOF文件进行后台重写,使得AOF文件的体积不至于过大;
  3. 制作缓存,如果你只希望你的数据在服务器运行的时候存在,你也可以不做任何持久化
  4. 同时开启两种缓存的方式
    • 在这种情况下,当Redis重启的时候会优先载入AOF文件来恢复原始数据,因为在通常情况下AOF文件保存的数据集要比RDB文件保存的更完整;
    • RDB的数据不实时,同事使用两者时服务器重启也只会找AOF文件,即便如此,也不是说仅仅只开启AOF模式就可以,因为RDB更适合用于备份数据库(AOF在不断变化不好备份),快速重启,而且不能保证AOF不会出现语句错误,留一个后手;
  5. 性能建议
    • 因为RDB文件只用作后备用途,建议只在Slave上持久化RDB文件,而且只要15分钟备份一次即可,只保留900 1的规则;
    • 如果开启AOF,好处是在恶劣情况下也只会丢失不超过两秒的数据,启动脚本较简单只load AOF文件就可以,代价是:1.带来持续的IO 2、AOF rewrite的最后将rewrite过程中产生的新数据写到新文件造成阻塞几乎是不可避免的,所以只要硬盘大小允许,应该尽量减少AOF rewrite的频率,AOF重写的基础大小默认为64m太小了,可以设置到5G以上,默认超过原始大小100%时重写可以改到适当值;
    • 如果不启动AOF,仅靠Master-Slave Replication 实现 高可用也可以,能节省大部分IO,也减少了rewrite时带来的系统波动。代价是如果Master/Slave同事崩掉,会丢失十几分钟的数据,启动脚本也要比较两个Master/Slave中的RDB文件,载入较新的那个(微博使用这种架构)。

14、Redis发布订阅

引用菜鸟资料
爬梯:Redis全解析(二)
订阅/发布消息图
爬梯:Redis全解析(二)

演示

订阅端:

127.0.0.1:6379> subscribe ssxChennel
Reading messages... (press Ctrl-C to quit)
1) "subscribe"
2) "ssxChennel"
3) (integer) 1
#进入等待阶段,等待频道消息推送
1) "message" 	#消息
2) "ssxChennel" #频道名
3) "helloCust" 	#消息内容

发送端:

127.0.0.1:6379> publish ssxChennel helloCust
(integer) 1

应用场景

  1. 实时消息系统

  2. 实时聊天(频道当作聊天室,将信息回显给聊天的人)

  3. 订阅,关注系统

    稍微复杂的场景使用消息队列实现。

15、Redis主从复制

概念

主从复制是指将一台Redis服务器的数据,复制到其它的Redis服务器。前者称为主节点(Master/Leader),后者称为从节点(Slave/Follower)。数据的复制是单向的,只能由主节点到从节点(主从复制、读写分离)Master以写为主、Slave以读为主。

PS:默认情况下,每台Redis服务器都是主节点,且一个主节点可以有多个从节点(或没有),而一个从节点只能由一个主节点。

主从复制的作用主要包括:

  1. 数据冗余:主从复制实现了数据的热备份,是持久化之外的数据冗余方式;
  2. 故障恢复:当主节点出问题时,可以由从节点提供服务,实现快速的故障恢复(服务冗余);
  3. 负载均衡:在主从复制的基础上,配合读写分离,可以由主节点提供写服务,由从节点提供读服务,分担服务器负载;一般系统是读的压力更大可以通过多个从节点分担“读”的压力;
  4. 高可用:主从复制还是哨兵和集群能够实现的基础,因此说主从复制是Redis高可用的基础。

爬梯:Redis全解析(二)

一般生产环境是不可以使用单台Redis;

环境配置

默认情况下,每台Redis服务器都是主节点

127.0.0.1:6379> info replication
# Replication
role:master #主节点
connected_slaves:0
master_replid:d1ca96e10d765ebb85d9db44475211bade81534d
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:0
second_repl_offset:-1
repl_backlog_active:0
repl_backlog_size:1048576
repl_backlog_first_byte_offset:0
repl_backlog_histlen:0

配置集群:

三份配置文件:实例:6379 6380 6381

  1. 端口:port 6379

  2. 后台服务:daemonize yes

  3. pid文件 :pidfile /var/run/redis_6379.pid

  4. rdb文件:dbfilename dump.rdb

  5. 日志文件:logfile “6379.log”

  6. 分别启动三个redis
    爬梯:Redis全解析(二)

集群配置:一主二从

让从机去认老大
爬梯:Redis全解析(二)

使用命令配置主从集群

配置6380:

127.0.0.1:6380> slaveof 127.0.0.1 6379	#配置主机的host和port  (我使用localhost能连接成功,但主机没找到从机....)
OK
127.0.0.1:6380> info replication
# Replication
role:slave
master_host:127.0.0.1
master_port:6379
master_link_status:up
master_last_io_seconds_ago:2
master_sync_in_progress:0
slave_repl_offset:0
slave_priority:100
slave_read_only:1
connected_slaves:0
master_replid:d507237df1352cd264dfe399b439c2872dca4977
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:0
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:0

主机6379:

127.0.0.1:6379> info replication
# Replication
role:master
connected_slaves:1
slave0:ip=127.0.0.1,port=6380,state=online,offset=14,lag=1
master_replid:d507237df1352cd264dfe399b439c2872dca4977
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:14
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:14

一般生产环境直接在配置文件中配置,永久配置

# replicaof <masterip> <masterport>
# masterauth <master-password>

主写 从读

#主机写入
127.0.0.1:6379> set key1 v1
OK

#从机读取
127.0.0.1:6380> get key1
"v1"
127.0.0.1:6380> set key2 v2
(error) READONLY You can't write against a read only replica. #从机不能进行写操作

主机宕机重连

127.0.0.1:6379> shutdown
not connected> exit

此时关闭了主机
爬梯:Redis全解析(二)
然后主机重启 设值

[aaa@qq.com redis-5.0.8]# src/redis-server redis.conf
[aaa@qq.com redis-5.0.8]# src/redis-cli -p 6379
127.0.0.1:6379> set key2 v2
OK

从机读取值

127.0.0.1:6380> get key2  
"v2"   #还是可以读取到,意味着恢复了主从链接关系

从机宕机重连

如果使用命令配置的主从关系,从机重启会失去关联主机(重启不能恢复主从结构)

但如果再使用命令关联到主机 slaveof,此时会将主机中的数据全部恢复过来从机。

复制原理

Slave启动成功连接到Master后会发送一个sync同步命令。

Master接到命令后,启动后台存盘进程,收集所有接收到的写命令,在后台进程执行完毕之后,Master将传送整个文件到Slave完成一次数据同步;

官方名词:

  • 全量复制:Slave服务器接收到数据文件后,将其存盘并全数加载到内存中;
  • 增量复制:Master在接收到写命令时,依次将命令发送给Slave完成同步;

只有Slave重新连接到Master,就会完成一次全量复制。

集群配置:链路集群

这种模式下,当Master宕机之后,需要手动执行命令让Slave1成为老大:

slaveof on one

此时如果Master回来了,需要手动配置集群结构。
爬梯:Redis全解析(二)

16、Redis哨兵模式

自动选取老大

概述

主从切换技术的方法是:当主服务器宕机后,手动把一台从服务器切换为主服务器,需要人工干预,耗时费力并且会造成一段时间内服务不可用情况。这不是一种推荐的方法,更多时候我们优先考虑哨兵模式。Redis2.8开始正式提供Sentinel(哨兵)架构来解决这个问题。

谋朝篡位自动版,能够后台监控主机是否故障,如果故障了将根据投票决定自动将一台从机转换为主机

哨兵模式是一种特殊的模式,首先Redis提供了哨兵的命令,哨兵是一个独立的进程。进程原理:哨兵通过发送命令,等待Redis服务器响应,从而监控运行的多个Redis实例。

单哨兵模式

爬梯:Redis全解析(二)

多哨兵模式

爬梯:Redis全解析(二)

  1. 当主服务器宕机后,假设哨兵1先检测到这个结果,此时这个主服务会被判定为“主观下线”,不会立刻进行failover(故障转移)操作。
  2. 当另外的哨兵都检测到主服务器宕机并且数量达到一定值后,那么哨兵之间就会进行一次投票,投票的行为由其中一台哨兵发起,即进行failover操作。
  3. 切换成功后,会通过发布订阅模式,让各个哨兵把自己监控的从服务器实现切换主机操作,这个过程成为“客观下线”。

实操

目前集群结构为:一主二从

  1. 配置哨兵文件 sentinel.conf
#sentinel monitor 监听名 host port 票数
sentinel monitor myredis 127.0.0.1 6379 2

后面的票数代表主机挂了之后,Slave投票让谁成为主机,票数多的成为主机。

  1. 启动哨兵进程
    爬梯:Redis全解析(二)
    当主机宕机,一定时间后会由哨兵进行选举另外一台作为主机。

优点

  1. 哨兵集群,基于主从复制模式,所有的主从配置优点
  2. 主从可以自动切换,故障自动转移,Redis实现高可用
  3. 从手动模式的主从模式升级,更加健壮实时

缺点

  1. Redis不好进行在线扩容,集群容量一旦达到上限后,在线扩容十分麻烦
  2. 实现哨兵模式的全套配置较为麻烦

哨兵模式全套配置:

bind 172.31.11.235
port 26380
daemonize yes
logfile "/usr/local/redis-4.0.9/sentinel.log.26380"

#master1
# 哨兵监控这个master,在至少1个哨兵实例都认为master down后把master标记为odown
sentinel monitor master1 172.31.11.235 6380 1#多少毫秒后,sentinel 认定redis master 服务器已掉线sentinel down-after-milliseconds master1 5000
# 若sentinel在该配置值内未能完成failover操作(即故障时master/slave自动切换),则认为本次failover失败
sentinel failover-timeout master1 10000
#sentinel can-failover master1 yes
sentinel parallel-syncs master1 2
# Generated by CONFIG REWRITE
dir "/usr/local/redis-4.0.9"
sentinel auth-pass master1 xxxxx

17、Redis缓存穿透、击穿和雪崩

Redis缓存的使用极大的提升了性能和效率,特别是数据查询方面。但是也带来了一些问题,其中最致命的是数据一致性问题,从严格意义上讲这个问题无解。如果对数据一致性要求较高,那么就不能使用缓存。

另外一些典型问题如:缓存穿透、缓存雪崩和缓存击穿。

缓存穿透

(某类绕过缓存查询数据库的数据)

缓存穿透的意思是,当用户想要查询一个数据,然后Redis中并没有,于是缓存没有命中,那么就会进入持久层中去数据库查,发现也没有,于是本次查询失败。

然后当这类查询被无数次执行时(恶意攻击、秒杀等),一直无法存入缓存,一直向数据库进行查询,则会造成数据库被攻击的现象,这就叫做 缓存击穿。
爬梯:Redis全解析(二)

布隆过滤器

布隆过滤器是一种数据结构,对所有可能查询的参数以hash形式存储,在控制层先进行校验,不符合则丢弃,从而避免了对底层存储系统的查询攻击。
爬梯:Redis全解析(二)

缓存空对象

当存储层不命中后,即使返回的空对象也将其缓存起来,同时设置一个过期时间,之后再访问这个数据会从缓存中获取,保护了后端数据源
爬梯:Redis全解析(二)
存在两个问题:

  1. 如果空值被存储存储起来,也意味着使用了更多的内存空间;
  2. 虽然对空值设置了过期时间,还是会存在缓存层和存储层会有一段时间数据不一致问题,此时业务对一致性要求较高时则会造成不必要的影响。

缓存击穿

(某个热点缓存持续高并发查询)

指的是一个key非常热门,一直在被大并发集中查询,然后当这个key瞬间过期失效时,持续的大并发就会穿透缓存,直接冲击到数据库(类似于一堵墙,在一个空被穿出一个洞)

设置热点数据不过期

从缓存层面来看,没有设置过期时间,所以不会出现热点key过期问题,避免了缓存击穿

加互斥锁

分布式锁:使用分布式锁,保证对于每个key同时只有一个线程去查询后端服务,其它线程没有获得分布式锁的权限不能去查询。这种实现方式将高并发的压力转移到分布式锁上,因此对分布式锁的考验较大。

缓存雪崩

指的是缓存在某一个时间点,集体失效。(Redis宕机、集体过期)

比如:双十一的时候,热门商品被放入缓存中,过期设置1小时,那么凌晨一点时,缓存集体过期,那么就会对数据库造成一个压力波峰,极有可能将持久层冲垮;
爬梯:Redis全解析(二)
集中过期还不是非常危险,更为致命的是缓存服务器某个节点宕机断网,将全部压力直接卸到持久层上。

Redis高可用

redis集群,当一台挂了还会有别的redis顶上。(异地多活)

限流降级

  • 分布式锁限流,控制只能有一个或几个线程可以访问后台;
  • 降级:临时关闭其他不紧急的服务,来为主服务让出服务器资源;

数据预热

意思是在正式启用之前,先把可能访问的数据预先访问一遍,让大部分数据先存入缓存中。

在即将发生大并发访问前,手动触发加载缓存不同的key,设置不同的过期时间,让缓存失效的时间点分布均匀。

相关标签: Redis redis