Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

redis调研与实践 #88

Open
Draymonders opened this issue Sep 1, 2020 · 5 comments
Open

redis调研与实践 #88

Draymonders opened this issue Sep 1, 2020 · 5 comments
Labels
middleware 中间件相关,zk,kafka, mongo, redis, influxdb等

Comments

@Draymonders
Copy link
Owner

Draymonders commented Sep 1, 2020

redis-link

apply

Redis可以做

  • 缓存系统
  • 计数器,actuator
  • 消息队列系统, 借助队列
  • 排行榜
  • 社交网络, (求共同好友等)
  • 布隆过滤器

由于redis是单核的,所以尽量部署多个redis,然后进行loadblance

@Draymonders Draymonders added the middleware 中间件相关,zk,kafka, mongo, redis, influxdb等 label Sep 1, 2020
@Draymonders
Copy link
Owner Author

Draymonders commented Sep 1, 2020

Redis连接池设置

其实就是用来保持长连接, 因为redis-client和redis-server建立链接,要通过 tcp 和 自身的协议, 但是我们经常使用redis,并不希望频繁的去建立链接和释放链接

maxTotal

用来表示最大的连接数,受以下情况影响

  • 业务希望Redis并发量 * 客户端命令平均执行时间
  • Redis资源, 例如apps(应用个数) * maxTotal 是不能超过redis的最大连接数 (config get maxclients)

maxIdle or minIdle

建议 maxIdle = maxTotal

  • 减少创建新连接的开销

建议预热minIdle

@Draymonders
Copy link
Owner Author

对于RedisTimeOut可以进行的监控

@Draymonders
Copy link
Owner Author

Draymonders commented Sep 5, 2020

Redis持久化

数据异步保存在disk中

RDB

内存快照,可以理解为redis的键值序列化,也可以用于网络传输(主从复制)。

触发机制

  • save 同步去dump内存数据, 命令执行期间会阻塞
  • bgsave 异步, fork会阻塞一小部分时间, 用到的是copy on write策略
  • 自动, 也是调用了bgsave
save 900 1
save 300 10
save 60 10000

AOF

命令的备份写到文件中, redis -> 写命令缓冲区 -> disk

AOF策略

  • always, 每条命令写到缓冲区中
  • everysec, 每秒将命令写到缓冲区中,会丢1s的数据
  • no,由操作系统来决定何时写入到disk中

rewrite

由于每条命令都会append到disk里,disk占用较大,而命令中多会出现这样的结果

set a b
set a c
set a d

其实,只需要最后的set a d就可以了,因此redis提供了rewrite功能。

RDB 和 AOF抉择

最佳实践

  • rdb关闭,但在主从模式下,不可以关闭。因为rdb是内存的全量序列化, 大数据下容易导致其他命令time-out。但是每次机器重启可以提前做一次save操作,因为reload快。
  • aof开启,建议everysec,只会丢1s的数据,集中管理rewrite
  • 小分片原则,对每个redis实例,进行maxmemory 5G的设置,这样fork,以及write的代价不会很高。
  • 做好监控 (硬盘,内存,负载,网络)
  • 足够的内存

fork 信息查询

redis-cli info | grep latest_fork_usec

@Draymonders
Copy link
Owner Author

Draymonders commented Sep 5, 2020

内存相关

redis-cli info memory 查看redis内存相关的信息

内存分布

内存主要分为redis自身运行占用内存,缓冲区(客户端缓冲区, 复制缓冲区(slave复制时使用), AOF缓冲区), 对象(kv)占用内存,fork占用内存

客户端缓冲区

redis-cli client list查看客户端详细信息

  • 普通客户端
  • slave客户端
  • pubsub客户端

内存回收策略

删除过期键值

  • 惰性删除 访问key -> expired dict -> del key
  • 定时删除 每秒运行10次,采样删除

内存溢出策略

config get maxmemory-policy去查看内存溢出的策略,用config set maxmemory-policy allkeys-lru来修改内存溢出的策略

  • Noeviction: 默认策略,不会删除任何数据,拒绝写入操作,并且返回OOM command
  • Volatile-lru: 根据LRU算法删除设置了超时属性(expire)的键,直到腾出足够空间。如没有可删除的,回退到Noeviction
  • Allkeys-lru: 如上,只是所有的key都可以被删
  • Allkeys-random: 如其名
  • Volatile-random: 随机删除设置超时(expire)的键
  • Volatile-ttl: 删将要过期的键

内存优化

合理选择数据结构

也就是键的类型, string, hash, set, zset, hyperloglog, geo等

合理优化数据结构-内部编码

wZKGm4.jpg

给一个场景 picId -> userId (10亿)

  • 实现方案
    1. 全部string: set picId userId
    2. 一个hash: hset allPics picId userId (不好运维)
    3. 若干个小hash: hset picId/100 picId%100 userId (两级hash, 因为第二级的hash用的数据结构是ziplist)

@Draymonders
Copy link
Owner Author

Draymonders commented Sep 21, 2020

slowlog

slowlog是一个队列,先入先出,记录大于slowlog时间阈值的命令以及执行时间

  • 获取slowlog的长度 config get slowlog-max-len
  • 获取slowlog的阈值 config get slowlog-log-slower-than

自己还未解决的坑

  • redis线上扩容方案, map扩容
  • redis的value的限制
  • redis为什么不想存在大Key
  • redis slowlog打印
  • redis 中间件调研

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
middleware 中间件相关,zk,kafka, mongo, redis, influxdb等
Projects
None yet
Development

No branches or pull requests

1 participant