Redis

Redis

灵魂拷问:啥场景?哪儿用?为啥非它不可?

咱们先别急着敲代码,得先搞清楚为什么要请Redis这尊"大佛"。

想象一下,如果你的数据量其实不大(比如就几万个配置项),但是访问量却大得像早晚高峰的地铁(每秒几万次查询),这时候如果让MySQL去抗,那简直就是在虐待硬盘。MySQL走的是硬盘(哪怕是SSD也有IO瓶颈),就像你要去图书馆查资料,得走路、找书架、抽书,这一套流程下来,高并发下数据库直接累吐血。

最典型的例子就是首页广告 或者热点资讯 。这玩意儿谁都要看,但又不常变。如果每次刷新首页都要去MySQL里翻箱倒柜,服务器早就罢工了。而Redis走的是内存,就像把书直接背在脑子里,想啥时候调出来就啥时候调出来,速度是微秒级的。

所以,Redis就是个高性能的Key-Value(键值对)数据库,由C语言编写,读操作能飙到110,000次/秒,写操作也有81,000次/秒。它就是为了在高并发场景下,替MySQL分担压力而生的。

安装与启动:从入门到"入土"(划掉)精通

接下来是动手环节。虽然现在的包管理器很方便,但为了理解原理,我们还是按最原始的源码安装方式来走一遍,这样你才知道它肚子里卖的什么药。

首先,把压缩包扔到Linux服务器的 /usr/upload 目录下,然后解压它。

bash 复制代码
cd /usr/upload
ll  # 看看文件在不在,强迫症必备
tar -zxvf redis-3.0.0.tar.gz  # 解压,释放它的灵魂

Redis是C写的,得先给它装个翻译官(编译器),不然它听不懂系统的指令。

bash 复制代码
yum install gcc-c++

环境好了,就可以开始打造金身了。进入目录,执行编译,然后指定安装路径。

bash 复制代码
cd /usr/upload/redis-3.0.0
make
make install PREFIX=/usr/local/redis

默认情况下,Redis是个"粘人精",它会占用你的终端窗口,你一关掉终端,它就挂了。我们需要修改配置文件,让它在后台默默守护(守护进程模式)。

bash 复制代码
# 拷贝配置文件到安装目录
cp /usr/upload/redis-3.0.0/redis.conf /usr/local/redis/bin

# 修改配置
vim /usr/local/redis/bin/redis.conf

在配置文件里,找到 daemonize no,把它改成 daemonize yes。这一步至关重要,改完保存退出。

最后就是启动和测试了。

bash 复制代码
cd /usr/local/redis/bin
./redis-server redis.conf  # 启动服务
./redis-cli  # 启动客户端,连接服务器

如果你看到 127.0.0.1:6379> 的提示符,恭喜你,Redis已经跑起来了!想关闭它的时候,别直接杀进程,优雅一点,用 ./redis-cli shutdown,这样能保证数据安全落地。

基本命令:跟Redis对话的艺术

进了 redis-cli 就像进了一个聊天室,你可以对它发号施令。

最常用的就是 keys *,这就像是点名,让Redis把所有存在的键都亮出来。如果你想知道某个键还在不在,用 exists key,返回1就是在,0就是没了。

Redis最强大的功能之一是自动过期,比如做验证码或者会话管理。用 expire key 秒数 给数据定个闹钟,时间一到它自动消失。想知道还有多久消失,就用 ttl key(Time To Live)。

对于计数器场景(比如点赞、浏览量),Redis简直是神器。incr key 让数值加1,decr key 让数值减1,原子操作,线程安全,比自己在代码里写锁要快得多。

bash 复制代码
# 1. 查看所有key,看看现在库里都有啥
127.0.0.1:6379> keys *
(empty list or set)  # 现在是空的

# 2. 存一个字符串,模拟存个用户信息
127.0.0.1:6379> set username "zhangsan"
OK

# 3. 查一下这个key存在吗
127.0.0.1:6379> exists username
(integer) 1  # 返回1表示存在

# 4. 模拟验证码场景,设置10秒后过期
127.0.0.1:6379> expire code 10
(integer) 1  # 设置成功

# 5. 看看还有几秒挂掉
127.0.0.1:6379> ttl code
(integer) 8  # 还有8秒

# 6. 模拟文章阅读量,自增
127.0.0.1:6379> set view_count 10
OK
127.0.0.1:6379> incr view_count
(integer) 11  # 变成了11
127.0.0.1:6379> incr view_count
(integer) 12  # 变成了12

# 7. 模拟点踩,自减
127.0.0.1:6379> decr view_count
(integer) 11  # 变回11
多数据库:Redis的"分身术"

很多人以为Redis只有一个数据库,其实它默认提供了16个数据库,编号从0到15。这就像一栋楼有16层,你可以通过 select 1 这样的命令在不同楼层之间穿梭。

但是要注意,Redis是单线程处理命令的,虽然分库了,但在高并发下切换数据库并不会带来性能提升,反而容易造成数据管理混乱,所以生产环境通常只用0号库。

如果你想清空数据,有两个选择:flushdb 是清空当前这一层楼的数据,flushall 则是毁灭性的,清空整栋楼(所有数据库)的数据,慎用!

bash 复制代码
# 1. 默认我们在0号库
127.0.0.1:6379> select 0
OK

# 2. 在0号库存个数据
127.0.0.1:6379> set db0_data "我是0号库的数据"
OK

# 3. 切换到1号库
127.0.0.1:6379> select 1
OK

# 4. 在1号库存个数据
127.0.0.1:6379[1]> set db1_data "我是1号库的数据"
OK

# 5. 切回0号库,看看刚才的数据还在不在
127.0.0.1:6379[1]> select 0
OK
127.0.0.1:6379> get db0_data
"我是0号库的数据"  # 还在

# 6. 清空当前库(0号库)
127.0.0.1:6379> flushdb
OK
127.0.0.1:6379> get db0_data
(nil)  # 没了

# 7. 去1号库看看,刚才的数据还在吗
127.0.0.1:6379> select 1
OK
127.0.0.1:6379[1]> get db1_data
"我是1号库的数据"  # 还在,flushdb只杀当前库
持久化:断电了数据还在吗?

这是面试必问,也是生产环境最核心的问题。内存虽快,但它是易失的,断电就失忆。为了不让数据裸奔,Redis搞了两套方案:RDB和AOF。

RDB (Redis DataBase) 是默认开启的。它的原理是"拍快照"。每隔一段时间,Redis会fork一个子进程,把内存里的数据全部 Dump 到硬盘上,生成一个 dump.rdb 文件。

配置策略通常写在配置文件里,比如 save 900 1 表示900秒内至少有1个key变了,就存一次;save 60 10000 表示60秒内有1万个key变了,就存一次。

RDB的优点是恢复数据极快,而且文件紧凑,适合做冷备份。缺点是可能会丢数据。比如在900秒的间隔内,你刚写完数据,还没来得及拍快照,服务器就断电了,那最后一次快照后的数据就全没了。

AOF (Append Only File) 则是另一种思路:存命令。你每敲一个写命令(如set),它就把它记在小本本(appendonly.aof)上。重启的时候,Redis会把小本本上的命令重新执行一遍,数据就回来了。

AOF默认是关闭的,需要在配置文件里把 appendonly no 改成 appendonly yes。它的同步策略有三种:always(来一个写一个,最安全但最慢)、everysec(每秒同步一次,推荐,平衡了速度和安全)、no(看操作系统心情)。

AOF的优点是数据完整性高,顶多丢1秒数据。缺点是文件体积通常比RDB大,而且恢复数据时要把命令重放一遍,速度比RDB慢。

在生产环境中,通常建议混合使用:用RDB做冷备份(比如每天半夜存一次),用AOF做实时恢复(每秒同步)。这样既保证了恢复速度,又保证了数据安全。

bash 复制代码
# --- RDB 实验 ---
# 1. 找到你的 dump.rdb 文件位置(通常在 /usr/local/redis/bin 目录下)
# 2. 删掉它,模拟全新开始
rm -f dump.rdb

# 3. 启动 Redis
./redis-server redis.conf

# 4. 存个数据
127.0.0.1:6379> set rdb_test "rdb数据持久化测试"
OK

# 5. 优雅关闭,触发保存
127.0.0.1:6379> shutdown

# 6. 再次启动
./redis-server redis.conf

# 7. 查数据,发现还在!说明RDB生效了
127.0.0.1:6379> get rdb_test
"rdb数据持久化测试"


# --- AOF 实验 ---
# 1. 修改配置文件 redis.conf
# 把 appendonly no 改为 appendonly yes
# 把 appendfsync no 改为 appendfsync everysec
# 或appendfsync always

# 2. 重启 Redis
./redis-server redis.conf

# 3. 存个数据
127.0.0.1:6379> set aof_test "aof数据持久化测试"
OK

# 4. 等待1秒(让AOF刷盘)

# 5. 强制杀掉进程(模拟断电,不优雅关闭)
kill -9 <redis进程ID>

# 6. 再次启动
./redis-server redis.conf

# 7. 查数据,发现还在!说明AOF生效了,数据没丢
127.0.0.1:6379> get aof_test
"aof数据持久化测试"
主从复制:找个"备胎"防身

单机Redis再强,也有挂掉的一天。为了保证高可用,我们需要搞"主从复制"。

这个过程其实很简单:

从节点(Slave)启动后,会向主节点(Master)发送 sync 命令,说"大哥,我想跟你混"。

主节点收到后,会触发一次RDB快照,把数据文件发给从节点。

从节点加载完数据后,主节点之后收到的每一个写命令,都会实时转发给从节点,保证大家的数据是一致的。

配置起来非常简单:

主节点(Master):啥都不用配,躺着就行,自带大佬气质。

从节点(Slave):在配置文件里加一句 slaveof masterIp masterPort,或者在命令行敲 slaveof 192.168.x.x 6379

测试的时候你会发现,往主节点写数据,从节点立马就能读到。但是,如果主节点挂了,从节点会发现自己没老大了。这时候要注意,默认情况下,从节点只能读,不能写(因为写了也没人同步给它,数据会乱)。

bash 复制代码
# --- 准备工作 ---
# 假设你有两台Redis,或者在同一台机器开了两个端口
# 主节点(Master): 6379
# 从节点(Slave): 6380

# --- 配置从节点 ---
# 方法一:修改 6380 的 redis.conf 配置文件
# 添加一行:slaveof  masterIp masterPort(换成主节点的ip和端口)

# 方法二:直接在 6380 的客户端命令行敲(临时生效)
127.0.0.1:6380> slaveof 127.0.0.1 6379
OK

# --- 测试同步 ---
# 1. 在主节点(6379)写数据
127.0.0.1:6379> set master_data "我是主节点的数据"
OK

# 2. 去从节点(6380)读数据
127.0.0.1:6380> get master_data
"我是主节点的数据"  # 哇!秒同步!

# --- 测试主节点挂了 ---
# 1. 把主节点(6379)关掉
127.0.0.1:6379> shutdown

# 2. 尝试在从节点(6380)写数据
127.0.0.1:6380> set slave_write "我想写数据"
(error) READONLY You can't write against a read only replica.
# 报错!提示只读!说明从节点虽然活着,但为了保护数据一致性,禁止写入。

这就是Redis的基础架构。它就像是一个极速的缓存层,挡在应用和数据库之间,用内存换时间,用主从换高可用。掌握了这些,你就拿到了高并发系统的入场券。

相关推荐
IvorySQL2 小时前
2MB 的 PostgreSQL work_mem,如何吃掉 2TB 内存?
数据库·postgresql·开源
桑榆肖物2 小时前
有字幕,没配音?用浏览器自带语音能力,让网页视频直接“开口说话”
数据库·edge·音视频·tts
熬夜的咕噜猫2 小时前
MySQL主从复制与读写分离
网络·数据库·mysql
道清茗2 小时前
【MySQL知识点问答题】 备份技术、Invisible Indexes 和直方图的应用
数据库·mysql
芒果披萨2 小时前
sql存储过程
java·开发语言·数据库
jnrjian2 小时前
RAC 去除node的建议 dbca 和手动方法
数据库·oracle
TlYf NTLE3 小时前
redis分页查询
数据库·redis·缓存
翻斗包菜3 小时前
MySQL 全量、增量备份与恢复实战指南(含 mysqldump + binlog + XtraBackup)
数据库·oracle
|华|3 小时前
MySQL主从复制与读写分离
数据库·mysql