什么是NoSQL
NoSQL,泛指非关系型数据库,NoSQL即Not_Only_SQL,它可以作为关系型数据库的良好补充。NoSQL数据库的产生就是为了解决大规模数据库集合,多重数据库种类带来的挑战,尤其是大数据应用的难题。Nosql说白了就是不能使用sql了,不是关系型数据库,解决高并发的问题。因为像mysql或oracle单机能够承受的并发数最多也就几千,Redis是纯内存操作, 它的性能非常出色, 每秒可以处理超过10万次读写操作。
01
redis介绍
Redis是用C语言开发的一个开源的高性能键值对(key-value)数据库。它通过提供多种键值数据类型来适应不同场景下的存储需求,目前为止Redis支持的键值数据类型如下:
字符串类型 string
散列类型 hash
列表类型 list
集合类型 set
有序集合类型
02
Redis持久化
Redis的高性能是由于其将所有数据都存储在了内存中,为了使Redis在重启之后仍能保证数据不丢失,需要将数据从内存中同步到硬盘中,这一过程就是持久化。
Redis支持两种方式的持久化,一种是RDB方式,一种是AOF方式。可以单独使用其中一种或将二者结合使用。
RDB持久化
DB方式的持久化是通过快照(snapshotting)完成的,当符合一定条件时Redis会自动将内存中的数据进行快照并持久化到硬盘。
RDB是Redis默认采用的持久化方式,在redis.conf配置文件中默认有此下配置:save 900 1。
save 开头的一行就是持久化配置,可以配置多个条件(每行配置一个条件),每个条件之间是“或”的关系。
AOF持久化
默认情况下Redis没有开启AOF(append only file)方式的持久化,可以通过appendonly参数开启:appendonly yes。
开启AOF持久化后每执行一条会更改Redis中的数据的命令,Redis就会将该命令写入硬盘中的AOF文件。AOF文件的保存位置和RDB文件的位置相同,都是通过dir参数设置的,默认的文件名是appendonly.aof,通过appendfilename参数修改:appendfilename appendonly.aof。
项目开发中的情况
通过RDB方式实现持久化,一旦Redis异常退出,就会丢失最后一次快照以后更改的所有数据。项目当中必须使用RDB,手动开启AOF,来保证数据的完整性。
03
redis的哨兵机制
redis主从之间可以通过哨兵进行检查,如果主节点出现故障,会自动切换从节点为主。
04
redis cluster集群原理
redis cluster集群默认16384个hash槽,集群搭建成功之后,需要给每一个主节点分配hash槽。当外部数据插入的时候,会对key进行crc16然后对16384取模,这样就计算出哪个节点对该数据进行管理。我们在项目当中采用的3主3从的结构,主从之间通过哨兵,出现故障自动切换。
问
你们在项目当中哪些地方用到redis?
1、我们项目当中一些字典表数据,通过redis进行缓存提高查询性能,比如品牌表省市县表等等 (spring-cache-redis)。
2、我们利用redis的过期策略,短信验证码存入redis,两分钟之内有效。
3、我们整个项目架构采用redis充当session容器,实现分布式环境下的session共享(Spring-session-redis)。
4、我们利用redis的list队列,基于push pop的原子性,实现商品抢购秒杀的场景。
5、购物车功能使用redis来存储登录用户的购物车信息。
6、数据过期处理(可以精确到毫秒)。
问
redis是单线程执行的,为什么性能这么高?
redis通过C语言实现了多路复用chanel select 轮询的机制,保证了高性能(类似于NIO)。
问
缓存的穿透和雪崩问题,你们是如何解决的?
穿透 :顾名思义,就是大量的请求穿过缓存层,达到数据库,造成数据库压力过大。
举例:你登录淘宝之后,订单搜索,你输入一个无效的订单,通过压测工具恶意攻击。
解决方案:1.每次请求时,可以在redis层,做一个bitMap,先去bitmap中查询一下是否存在该条件,进行过滤。 2.每次请求,查询数据库就算不存在,我也将查询条件和null在redis中进行缓存,设置一个很短的存活时间。
雪崩:是指在某一个时间点,大量的缓存同时失效,请求达到数据库,造成数据库压力过大。
解决方案:对大量数据设置过期时间时,哪怕业务需要同时失效,我也不设置同一个时间,分别对每一组key value 设置失效时间,让每一组key value的失效时间间隔个几毫秒。