Redis - 核心原理深度解析:线程模型、持久化与高可用性

文章目录

  • 概述
  • 一、Redis线程模型演进
    • [1. 经典单线程模型(Redis 4.0前)](#1. 经典单线程模型(Redis 4.0前))
    • [2. 多线程优化演进](#2. 多线程优化演进)
  • 二、数据持久化机制
    • [1. AOF(Append Only File)](#1. AOF(Append Only File))
    • [2. RDB(Redis Database)](#2. RDB(Redis Database))
    • [3. 混合持久化(Redis 4.0+)](#3. 混合持久化(Redis 4.0+))
  • 三、高可用架构设计
    • [1. 主从复制(Replication)](#1. 主从复制(Replication))
    • [2. 哨兵模式(Sentinel)](#2. 哨兵模式(Sentinel))
    • [3. Redis Cluster(分布式集群)](#3. Redis Cluster(分布式集群))
  • 四、总结

概述

Redis作为当前最流行的缓存中间件,凭借其高性能和高可用性成为分布式系统中的核心组件。接下来 将深入剖析Redis的线程模型、数据持久化机制及高可用方案,全面掌握Redis的核心原理。


一、Redis线程模型演进

1. 经典单线程模型(Redis 4.0前)

核心特点

  • 单线程处理网络I/O与键值操作
  • 避免线程竞争与锁开销
  • 基于I/O多路复用处理高并发请求

Redis 是单线程的,主要是指 Redis 的网络 I/O 线程,以及键值的 SET 和 GET 等读写操作都是由一个线程来完成的。但 Redis 的持久化、集群同步等操作,则是由另外的线程来执行的。

高性能秘诀

  • 全内存操作
  • 高效数据结构(哈希表、跳表)
  • 非阻塞I/O多路复用(Epoll/Kqueue)

2. 多线程优化演进

  • Redis 4.0 :引入异步删除(UNLINKFLUSHDB ASYNC
  • Redis 6.0 :网络I/O多线程化(默认关闭)
    • 核心改进:主线程处理命令,多线程处理网络数据读写
    • 性能提升:网络密集型场景吞吐量提升2倍

虽然 Redis 一直是单线程模型,但是在 Redis 6.0 版本之后,也采用了多个 I/O 线程来处理网络请求,这是因为随着网络硬件的性能提升,Redis 的性能瓶颈有时会出现在网络 I/O 的处理上,所以为了提高网络请求处理的并行度,Redis 6.0 对于网络请求采用多线程来处理。但是对于读写命令,Redis 仍然使用单线程来处理。


二、数据持久化机制

1. AOF(Append Only File)

通常情况下,关系型数据库(如 MySQL)的日志都是"写前日志"(Write Ahead Log, WAL),也就是说,在实际写数据之前,先把修改的数据记到日志文件中,以便当出现故障时进行恢复,比如 MySQL 的 redo log(重做日志),记录的就是修改后的数据。

而 AOF 里记录的是 Redis 收到的每一条命令,这些命令是以文本形式保存的,不同的是,Redis 的 AOF 日志的记录顺序与传统关系型数据库正好相反,它是写后日志,"写后"是指 Redis 要先执行命令,把数据写入内存,然后再记录日志到文件。

实现原理

  • 记录所有写命令(文本格式)
  • 写后日志机制(先执行命令再记录日志)

优缺点

  • ✅ 数据完整性高
  • ❌ 文件体积大、恢复速度慢
  • ❌ 同步策略(Always/Everysec/No)影响性能与可靠性

2. RDB(Redis Database)

因为 AOF 日志记录的是操作命令,不是实际的数据,所以用 AOF 方法做故障恢复时,需要全量把日志都执行一遍,一旦日志非常多,势必会造成 Redis 的恢复操作缓慢。

为了解决这个问题,Redis 增加了 RDB 内存快照(所谓内存快照,就是将内存中的某一时刻状态以数据的形式记录在磁盘中)的操作,它即可以保证可靠性,又能在宕机时实现快速恢复。

和 AOF 不同的是,RDB 记录 Redis 某一时刻的数据,而不是操作,所以在做数据恢复时候,只需要直接把 RDB 文件读入内存,完成快速恢复。

实现原理

  • 生成内存快照(二进制压缩文件)
  • 支持SAVE(阻塞)与BGSAVE(后台子进程)

RDB 做快照时会阻塞线程吗?

因为 Redis 的单线程模型决定了它所有操作都要尽量避免阻塞主线程,所以对于 RDB 快照也不例外,这关系到是否会降低 Redis 的性能。

为了解决这个问题,Redis 提供了两个命令来生成 RDB 快照文件,分别是 save 和 bgsave。save 命令在主线程中执行,会导致阻塞。而 bgsave 命令则会创建一个子进程,用于写入 RDB 文件的操作,避免了对主线程的阻塞,这也是 Redis RDB 的默认配置。

RDB 做快照的时候数据能修改吗?

如果在执行快照的过程中,数据如果能被修改或者不能被修改都会带来什么影响?

  • 如果此时可以执行写操作:意味着 Redis 还能正常处理写操作,就可能出现正在执行快照的数据是已经被修改了的情况;

  • 如果此时不可以执行写操作:意味着 Redis 的所有写操作都得等到快照执行完成之后才能执行,那么就又出现了阻塞主线程的问题。

那Redis 是如何解决这个问题的呢? 它利用了 bgsave 的子进程,具体操作如下:

  • 如果主线程执行读操作,则主线程和 bgsave 子进程互相不影响;

  • 如果主线程执行写操作,则被修改的数据会复制一份副本,然后 bgsave 子进程会把该副本数据写入 RDB 文件,在这个过程中,主线程仍然可以直接修改原来的数据。

核心优势

  • ⚡️ 快速恢复(秒级重启)
  • 💾 紧凑存储(适合备份)
  • ⚠️ 数据可能丢失(两次快照间宕机)

3. 混合持久化(Redis 4.0+)

Redis 对 RDB 的执行频率非常重要,因为这会影响快照数据的完整性以及 Redis 的稳定性,所以在 Redis 4.0 后,增加了 AOF 和 RDB 混合的数据持久化机制: 把数据以 RDB 的方式写入文件,再将后续的操作命令以 AOF 的格式存入文件,既保证了 Redis 重启速度,又降低数据丢失风险。

创新设计

  • RDB快照 + 增量AOF日志
  • 重启时先加载RDB,再重放AOF
  • 优势:兼顾启动速度与数据完整性

三、高可用架构设计

1. 主从复制(Replication)

核心机制

  • 一主多从架构
  • 全量同步(RDB) + 增量同步(命令传播)
  • 读写分离提升读吞吐量

痛点

  • 主节点故障需手动切换

2. 哨兵模式(Sentinel)

核心功能

  • 监控节点健康状态
  • 自动故障转移(选举新主节点)
  • 客户端服务发现

3. Redis Cluster(分布式集群)

核心特性

  • 数据分片(16384哈希槽)
  • 自动故障转移
  • 无中心节点设计

哈希槽分配策略

  • 自动分配CLUSTER CREATE平均分布
  • 手动分配CLUSTER ADDSLOTS精准控制

Redis Cluster 方案采用哈希槽(Hash Slot),来处理数据和实例之间的映射关系。在 Redis Cluster 方案中,一个切片集群共有 16384 个哈希槽,这些哈希槽类似于数据分区,每个键值对都会根据它的 key,被映射到一个哈希槽中,具体执行过程分为两大步。

  • 根据键值对的 key,按照 CRC16 算法计算一个 16 bit 的值。

  • 再用 16bit 值对 16384 取模,得到 0~16383 范围内的模数,每个模数代表一个相应编号的哈希槽。

剩下的一个问题就是,这些哈希槽怎么被映射到具体的 Redis 实例上的呢?有两种方案。

  • 平均分配: 在使用 cluster create 命令创建 Redis 集群时,Redis 会自动把所有哈希槽平均分布到集群实例上。比如集群中有 9 个实例,则每个实例上槽的个数为 16384/9 个。

  • 手动分配: 可以使用 cluster meet 命令手动建立实例间的连接,组成集群,再使用 cluster addslots 命令,指定每个实例上的哈希槽个数 。

为了方便理解,通过一张图来解释数据、哈希槽,以及实例三者的映射分布关系。


四、总结

通过深入理解Redis的线程模型、持久化机制与高可用架构,开发者能够更好地设计高性能、高可靠的缓存方案。在实际应用中,需根据业务场景灵活选择持久化策略与集群方案,持续优化系统表现

相关推荐
一代...2 小时前
【Redis】Redis基本命令(1)
数据库·redis·缓存
八股文领域大手子2 小时前
深入浅出 Redis:核心数据结构解析与应用场景Redis 数据结构
java·数据结构·数据库·人工智能·spring boot·redis·后端
成工小白2 小时前
Redis的下载安装和使用(超详细)
数据库·redis·缓存
dl8106727314 小时前
Redis的IO多路复用
数据库·redis·缓存
洛神灬殇12 小时前
【Redis技术进阶之路】「原理分析系列开篇」分析客户端和服务端网络诵信交互实现(服务端执行命令请求的过程 - 文件事件处理部分)
redis·后端
kinlon.liu13 小时前
SpringBoot整合Redis限流
spring boot·redis·后端
kinlon.liu15 小时前
使用Redis实现分布式限流
数据库·redis·分布式·缓存
bing_15818 小时前
Redis 的不同数据结构分别适用于哪些微服务场景
数据结构·redis·微服务
大数据魔法师19 小时前
Redis(一) - Redis安装教程(Windows + Linux)
linux·windows·redis
烂漫心空21 小时前
Windows 系统如何使用Redis 服务
数据库·数据仓库·redis·mysql·缓存·数据库架构