千万级学生管理系统的考试试卷存储方案
一.业务诉求
对于不同学校,不同年级的试卷进行存储
对于对应试卷的学生试题答案进行存储
二.千万级学生管理系统数据估计情况
在校学生(试卷+试题): 2.4T
离校学生(试卷+试题)(每年增长):每年 250 万,存储量为 0.6T
试卷请求:5 万 QPS
提交试卷:1700TPS
三.redis 数据类型选型
3.1 对于前置业务的存储分析
考试的试卷存储量相对较少,但是考试时读取并发量较高
学生的试题答案是存储的核心诉求,存储数据量较大,且每年累加
试题答案在业务上,只有写入,没有更新等操作
3.2 redis 数据类型说明
redis 有 5 种数据类型,除 String 外,都可以称为集合类型。
其中 List 多用于做队列服务,底层实现为双向链表和压缩列表。Set 以及 Zset 更多是更加快速的查看是否有重复数据,以及集合操作等。这 3 种都不符合当前的业务诉求。
3.3 redis 的选型
主要选型为 Hash,采用 String 也可
Hash 和 String 的读取复杂度都为 O(1),适合当前这种读读取性能要求较高的场景
Hash 和 String 在这里的区别就是,Hash 是个集合的类型,是个符合结构,最上层的 key 可以存储学校 ID,或是试卷 ID,也可是专业的 ID。主要体现向下聚合的逻辑。String 因为就是最简单的 KV 存储,所以 KEY 值要采用专业 ID+试题序号这种符合的写法。以便存储。
其实抽象出来看,试卷本身就是序号+题目的逻辑。答案就是序号+答案的逻辑,更上层的组织维度则包含,专业,班级,年级,系,学校等。为了不让 redis 本身嵌入过多层,更上层的维度可以专门用一个 redis 的结构做映射。
四.读写流程
先出题,存储到 mysql 当中,题目整体的量级较小,选型 mysql 较为合适,普通的主备架构即可
再同步,mysql 的试卷同步到 redis 集群当中,增加读取性能
限时间,redis 更多的是当缓存进行使用,所以原则就是,在需要的时间,占用内存,发挥读写价值。根据考试的时间安排,做好 redis 的存储时间
读试卷,考试过程中,可以访问不同的 redis 节点
存答案,学生的试题答案存到 redis 当中。以保证比较高的 TPS
落数据,最终把 redis 的试题答案,存入到 Hbase 当中,选型 Hbase 主要考虑到,试题存储量较大,且每年递增
五.计算 Redis sentinel 集群的服务器数量和性能
考试时,试题的读取为 5 万 QPS,一般单台 redis 的性能为 5W-10W(QPS)之间
Redis sentinel 模式为了保证高可用,一般最少为 3 节点(奇数节点防止脑裂)
采用经典的三节点即可,因为 sentinel 耗费的资源不多,工作为监控,选主,通知。可以把 sentinel 和本身的三节点部署一起即可。需要 3 台机器。读写性能 15 万 QPS+
其实主流配置的服务器,带宽 15M+,单台 redis,加上做一些优化,基本可以 hold 住。引入 redis sentinel 一个是为了增加性能,底子上也是 master-slave 的模式。另一个原因就是为了高可用
评论