我们为什么使用redis

2020-04-16  本文已影响0人  zjp999988

思路比结论重要
缓存的本质就是从慢的介质->内存;

image.png

我们可以在各层都可以看到缓存的身影;
pc/app 和ng负责均衡层都可以设计相应的缓存逻辑,减少响应耗时;

在服务端,本质上由于db的特性,读写性能始终是有瓶颈的;
因此为了提高服务端性能,把db的数据load到cache上;
其实使用hashMap本质也可以理解为单进程的cache,只不过功能特性很少,不如实现key超时,清除,需要另起一个线程判断key是不是过时;
开源的单进程jvm的有google开源的guava cache,提供了很多类似redis功能的功能;
jvm进程缓存始终会有单点故障;

因此我们需要使用分布式缓存来避免单点故障;假如公司需要自研缓存产品,都要解决以下问题:

1.客户端和我交互的协议怎么设计,是采用http协议还是类似于mq的协议?
2.当大量数据存储在缓存时,缓存的内存管理是什么样的机制?
3.如何解决单点故障问题?怎么保证高可用?
4.如果我的数据要持久化,我的持久化的实际和数据文件格式?
5.如何水平扩展扩容?
6.如何监控服务节点的信息?
7.需要支持哪些数据结构,来支持上层业务功能呢?

至此我们看下redis是如何涉及解决以上问题的;

1.协议
之前写了一篇使用netty实现redis客户端,redis都是基于命令的,因此使用了自定义的轻量级协议
消息看到是文本命令 set zjp 18;
如果我们要想发送给redis客户端需要转换成redis服务端的协议格式 每部分都是\r\n间隔
*3 \r\n (消息的组成部分 )
3\r\n(各部分消息的长度 set 长度为3) set3\r\n
zjp
$2\r\n
18
这样的协议传输文本占用字节和带宽比http的协议文本要小的多,因此传输效率会高的多;
可见协议也是redis高效的原因之一;

2.redis 如何管理我们的内存?
当应用运行一段时间后,我们的服务的内存如果管理,服务器总会有最大瓶颈;jvm会有内存gc机制,当发送oom或者内存不够时会有一定的回收机制?
1 .redis会有对用的策略lru 最近最少使用,根据最近使用的key,选择一定比列的key,选择时间较长key;释放内存
2.根据使用次数,根据使用次数,选择使用此时和频率较少的key,选择一个比列的key,删除掉使用评率较少的key;释放内存

可以看到,redis会有不同的回收策略对内存进行释放,如果需要二次开发,可以自实现内存的回收策略;

3.高可用设计
redis设计中提供了2中高可用方案
1.哨兵机制


image.png

如图一主2从3哨兵 ,3个哨兵分别保持链接检查master节点状态和信息
同时通过info命令拿到当前主节点,当多数哨兵认为主节点挂了,通过投票机制,选举一个哨兵执行主从切换;
2.集群


image.png

数据通过分片存储,每一个分片也是一个主从架构
主从切换类似哨兵主从切换;

4.数据持久化
redis也支持2种持久化方式
1.rdb 基于快照的持久化方式,是命令执行的结果文件 (异步刷盘,存在数据丢失可能)写入速度慢,数据恢复快
2.aof 日志文件 是记录命令本身,写入文件较快(支持同步和异步刷盘)

5.支持的数据结构
1String
2List set sortedSet
3hash
4.bitmap(bite位,可以用于实现类似布隆过滤器)
5.pubsub(发布订阅)
6.Stream(类似的消息队列)
以上数据结构有着丰富的使用场景,需要结合业务需求;

6、
redis 集群的节点的分片,支持动态的reshard,可以为某个分片节点重新分片多个shot(hash槽)

7.redis
本身提供多个监控命令,很多监控工具也是局域redis的监控命令
类似于 info ,moniter,hotkey...拿到集群的状态信息;

上一篇 下一篇

猜你喜欢

热点阅读