数据持久化
测试redis是否会自动进行数据持久化
关闭redis服务
127.0.0.1:6379> SHUTDOWN
not connected>
not connected> EXIt
查看redis状态:关闭
[root@db ~]# ps -ef |grep redis
root 41024 40992 0 16:25 pts/2 00:00:00 redis-cli
root 41102 41054 0 16:57 pts/3 00:00:00 redis-cli
root 41119 39878 0 17:03 pts/1 00:00:00 redis-cli
root 41128 2390 0 17:16 pts/0 00:00:00 grep --color=auto redis
重新登录redis服务
[root@db ~]# redis-server /etc/redis.conf
41133:C 20 Jul 2024 17:17:01.406 # WARNING Memory overcommit must be enabled! Without it, a background save or replication may fail under low memory condition. Being disabled, it can also cause failures without low memory condition, see https://github.com/jemalloc/jemalloc/issues/1328. To fix this issue add 'vm.overcommit_memory = 1' to /etc/sysctl.conf and then reboot or run the command 'sysctl vm.overcommit_memory=1' for this to take effect.
[root@db ~]# redis-cli
127.0.0.1:6379> get k1
"v1"
127.0.0.1:6379> get k2
"v2"
重启主机后登录
[root@db ~]# redis-server /etc/redis.conf
2267:C 20 Jul 2024 17:23:29.793 # WARNING Memory overcommit must be enabled! Without it, a background save or replication may fail under low memory condition. Being disabled, it can also cause failures without low memory condition, see https://github.com/jemalloc/jemalloc/issues/1328. To fix this issue add 'vm.overcommit_memory = 1' to /etc/sysctl.conf and then reboot or run the command 'sysctl vm.overcommit_memory=1' for this to take effect.
[root@db ~]# redis-cli
127.0.0.1:6379> get k1
"v1"
两者测试数据均已数据持久化
Redis提供了主要提供了 2 种不同形式的持久化方式:
- RDB(Redis数据库):RDB 持久性以指定的时间间隔执行数据集的时间点快照。
- AOF(Append Only File):AOF 持久化记录服务器接收到的每个写操作,在服务器启动时再次播放,重建原始数据集。 命令使用与 Redis 协议本身相同的格式以仅附加方式记录。 当日志变得太大时,Redis 能够在后台重写日志。
1.RDB
(1)定义
- 在指定的时间间隔内将内存中的数据集快照写入磁盘, 也就是Snapshot快照,它恢复时是将快照文件直接读到内存里。
(2)如何备份
- Redis会单独创建(fork)一个子进程来进行持久化,会先将数据写入到 一个临时文件中,待持久化过程都结束后,再用这个临时文件替换上次持久化好的文件。 整个过程中,主进程是不进行任何IO操作的,这就确保了极高的性能。如果需要进行大规模数据的恢复,且对于数据恢复的完整性不是非常敏感,那RDB方式要比AOF方式更加的高效。RDB的缺点是最后一次持久化后的数据可能丢失。
(3)Fork
-
Fork 的作用是复制一个与当前进程一样的进程。新进程的所有数据(变量、环境变量、程序计数器等) 数值都和原进程一致,但它是一个全新的进程,并作为原进程的子进程。
-
在 Linux 程序中,fork() 会产生一个和父进程完全相同的子进程,但子进程在此后多会 exec 系统调用,出于效率考虑,Linux 中引入了“写时复制技术”。
-
一般情况下父进程和子进程会共用同一段物理内存,只有进程空间的各段的内容要发生变化时,才会将父进程的内容复制一份给子进程。
流程(待添加)
(4)相关配置
禁用RDB
save “”
触发RDB的机制,没有配置save的情况,默认使用
# save 3600 1 300 100 60 10000
停止写的操作,前提是RDB持久化过程出现错误
stop-writes-on-bgsave-error yes
启动压缩
rdbcompression yes
校验文件完整性
rdbchecksum yes
指定文件的名称
dbfilename dump.rdb
默认配置是rdb-del-sync-files no,主从进行全量同步时,通过传输RDB内存快照文件实现;没有开启RDB持久化的实例在同步完成后会删除该文件,通常情况下保持默认就行
rdb-del-sync-files no
指定存储目录
dir ./
(5)配置测试
先把之前的数据清空
查找哪些位置都有dump.rdb文件(这个文件保存数据信息,只要启动服务,那么就会把这个文件加载到内存中)
[root@db ~]# find / -name 'dump.rdb'
/root/dump.rdb
/usr/local/redis-stable/dump.rdb
下边操作是删除这两个文件
[root@db ~]# ls -l
total 5836
-rw-------. 1 root root 1232 Jun 22 20:23 anaconda-ks.cfg
-rw-r--r--. 1 root root 1234230 Jul 9 16:06 backup.sql
-rw-r--r--. 1 root root 226 Jul 10 14:41 create_procedure.sql
-rw-r--r--. 1 root root 1370 Jul 20 17:18 dump.rdb
-rw-r--r--. 1 root root 5237 Jul 9 16:29 increment.sql
-rw-r--r--. 1 root root 1232273 Jul 9 15:23 my.sql
-rw-r--r--. 1 root root 3483771 May 19 14:18 redis-stable.tar.gz
[root@db ~]# rm -rf dump.rdb
[root@db ~]# ls -l
total 5832
-rw-------. 1 root root 1232 Jun 22 20:23 anaconda-ks.cfg
-rw-r--r--. 1 root root 1234230 Jul 9 16:06 backup.sql
-rw-r--r--. 1 root root 226 Jul 10 14:41 create_procedure.sql
-rw-r--r--. 1 root root 5237 Jul 9 16:29 increment.sql
-rw-r--r--. 1 root root 1232273 Jul 9 15:23 my.sql
-rw-r--r--. 1 root root 3483771 May 19 14:18 redis-stable.tar.gz
[root@db ~]# cd /usr/local/redis-stable/
[root@db redis-stable]# ls -l
total 264
-rw-rw-r--. 1 roo roo 21840 May 19 14:12 00-RELEASENOTES
-rw-rw-r--. 1 roo roo 51 May 19 14:12 BUGS
-rw-rw-r--. 1 roo roo 5027 May 19 14:12 CODE_OF_CONDUCT.md
-rw-rw-r--. 1 roo roo 2634 May 19 14:12 CONTRIBUTING.md
-rw-rw-r--. 1 roo roo 1487 May 19 14:12 COPYING
drwxrwxr-x. 8 roo roo 4096 Jul 18 08:50 deps
-rw-r--r--. 1 root root 88 Jul 18 21:05 dump.rdb
-rw-rw-r--. 1 roo roo 11 May 19 14:12 INSTALL
-rw-rw-r--. 1 roo roo 151 May 19 14:12 Makefile
-rw-rw-r--. 1 roo roo 6888 May 19 14:12 MANIFESTO
-rw-rw-r--. 1 roo roo 22607 May 19 14:12 README.md
-rw-rw-r--. 1 roo roo 107513 Jul 18 20:17 redis.conf
-rwxrwxr-x. 1 roo roo 279 May 19 14:12 runtest
-rwxrwxr-x. 1 roo roo 283 May 19 14:12 runtest-cluster
-rwxrwxr-x. 1 roo roo 1772 May 19 14:12 runtest-moduleapi
-rwxrwxr-x. 1 roo roo 285 May 19 14:12 runtest-sentinel
-rw-rw-r--. 1 roo roo 1695 May 19 14:12 SECURITY.md
-rw-rw-r--. 1 roo roo 14700 May 19 14:12 sentinel.conf
drwxrwxr-x. 4 roo roo 12288 Jul 18 08:52 src
drwxrwxr-x. 11 roo roo 4096 May 19 14:12 tests
-rw-rw-r--. 1 roo roo 3628 May 19 14:12 TLS.md
drwxrwxr-x. 9 roo roo 4096 May 19 14:12 utils
[root@db redis-stable]# rm -rf dump.rdb
[root@db redis-stable]# ls -l
total 260
-rw-rw-r--. 1 roo roo 21840 May 19 14:12 00-RELEASENOTES
-rw-rw-r--. 1 roo roo 51 May 19 14:12 BUGS
-rw-rw-r--. 1 roo roo 5027 May 19 14:12 CODE_OF_CONDUCT.md
-rw-rw-r--. 1 roo roo 2634 May 19 14:12 CONTRIBUTING.md
-rw-rw-r--. 1 roo roo 1487 May 19 14:12 COPYING
drwxrwxr-x. 8 roo roo 4096 Jul 18 08:50 deps
-rw-rw-r--. 1 roo roo 11 May 19 14:12 INSTALL
-rw-rw-r--. 1 roo roo 151 May 19 14:12 Makefile
-rw-rw-r--. 1 roo roo 6888 May 19 14:12 MANIFESTO
-rw-rw-r--. 1 roo roo 22607 May 19 14:12 README.md
-rw-rw-r--. 1 roo roo 107513 Jul 18 20:17 redis.conf
-rwxrwxr-x. 1 roo roo 279 May 19 14:12 runtest
-rwxrwxr-x. 1 roo roo 283 May 19 14:12 runtest-cluster
-rwxrwxr-x. 1 roo roo 1772 May 19 14:12 runtest-moduleapi
-rwxrwxr-x. 1 roo roo 285 May 19 14:12 runtest-sentinel
-rw-rw-r--. 1 roo roo 1695 May 19 14:12 SECURITY.md
-rw-rw-r--. 1 roo roo 14700 May 19 14:12 sentinel.conf
drwxrwxr-x. 4 roo roo 12288 Jul 18 08:52 src
drwxrwxr-x. 11 roo roo 4096 May 19 14:12 tests
-rw-rw-r--. 1 roo roo 3628 May 19 14:12 TLS.md
drwxrwxr-x. 9 roo roo 4096 May 19 14:12 utils
再查,没有了
[root@db redis-stable]# find / -name 'dump.rdb'
重启redis服务,重启主机
接着开启服务,查看是否还有数据
127.0.0.1:6379> keys *
(empty array)
(6)开启RDB,并修改部分配置
进入配置文件
vim /etc/redis.conf
注释掉
save ""
修改保存时间,69秒三次
save 60 3
修改保存路径
dir /rdbdata
保存并退出
:wq
要测试RDB,则需要把AOF关闭,查看配置文件,发现AOF默认关闭
appendonly no
查询有无数据
127.0.0.1:6379> keys *
(empty array)
先插入两条
127.0.0.1:6379> set k1 v1
OK
127.0.0.1:6379> set k2 v2
OK
查询到这个文件下没有变化
[root@db ~]# ls -l /rdbdata/
total 0
插入第三条数据
127.0.0.1:6379> set k3 v3
OK
查询,发生变化
[root@db ~]# ls -l /rdbdata/
total 4
-rw-r--r--. 1 root root 114 Jul 21 08:23 dump.rdb
(7)优点和缺点
优点:RDB 方式适合大规模的数据恢复,并且对数据完整性和一致性要求不高更适合使用。节省磁盘空间;恢复速度快
缺点:Fork的时候,内存中的数据被克隆了一份,大致2倍的膨胀性需要考虑;虽然Redis在fork时使用了写时拷贝技术,但是如果数据庞大时还是比较消耗性能;在备份周期在一定间隔时间做一次备份,所以如果Redis意外down掉的话,就会丢失最后一次快照后的所有修改。
2、AOF
(1)定义
- 以日志的形式来记录每个写操作(增量保存),将Redis执行过的所有写指令记录下来(读操作不记录), 只追加文件但不可以改写文件,Redis启动之初会读取该文件重新构建数据。简单说,Redis 重启时会根据日志文件的内容将写指令从前到后执行一次以完成数据的恢复工作。
- 在Redis的默认配置中AOF(Append Only File)持久化机制是没有开启的,要想使用AOF持久化需要先开启此功能。AOF持久化会将被执行的写命令写到AOF文件末尾,以此来记录数据发生的变化,因此只要Redis从头到尾执行一次AOF文件所包含的所有写命令,就可以恢复AOF文件的记录的数据集。
(2)持久化流程
1)客户端的请求写命令会被 append 追加到 AOF 缓冲区内。
2)AOF 缓冲区根据 AOF 持久化策略 [always,everysec,no] 将操作sync同步到磁盘的 AOF 文件中。
3)AOF 文件大小超过重写策略或手动重写时,会对 AOF 文件 rewrite 重写,压缩 AOF 文件容量。
4)Redis 服务重启时,会重新 load 加载 AOF 文件中的写操作达到数据恢复的目的。
(3)AOF操作
相关配置文件介绍
是否开启AOF
appendonly no
AOF文件的基名
appendfilename "appendonly.aof"
# For example, if appendfilename is set to appendonly.aof, the following file
# names could be derived:
#
# - appendonly.aof.1.base.rdb as a base file.
# - appendonly.aof.1.incr.aof, appendonly.aof.2.incr.aof as incremental files.
# - appendonly.aof.manifest as a manifest file.
AOF存储的目录
appenddirname "appendonlydir"
刷盘的时机
appendfsync everysec
每秒刷一次
everysec:
总是:每一次写操作都刷盘
always:
不决定刷盘的时机,交给操作系统
no:redis
在重写的时候是否进行刷盘
no-appendfsync-on-rewrite no
# 触发AOF重写的机制:
auto-aof-rewrite-percentage 100 # 100% 对比:上次文件大小
auto-aof-rewrite-min-size 64mb # 最小文件大小64mb
aof-load-truncated yes # 是否加载后清空aof
aof-use-rdb-preamble yes # rdb+aof的方式来持久化
aof-timestamp-enabled no # 是否启用时间戳
开启AOF
配置文件中
关闭RDB
save ""
开启AOF
appendonly yes
测试
127.0.0.1:6379> keys *
1) "k3"
2) "k2"
3) "k1"
127.0.0.1:6379> shutdown
not connected> exit
[root@db ~]# redis-server /etc/redis.conf
2524:C 21 Jul 2024 08:56:17.510 # WARNING Memory overcommit must be enabled! Without it, a background save or replication may fail under low memory condition. Being disabled, it can also cause failures without low memory condition, see https://github.com/jemalloc/jemalloc/issues/1328. To fix this issue add 'vm.overcommit_memory = 1' to /etc/sysctl.conf and then reboot or run the command 'sysctl vm.overcommit_memory=1' for this to take effect.
[root@db ~]# redis-cli
127.0.0.1:6379> keys *
(empty array)
插入数据
127.0.0.1:6379> set k1 v1
OK
127.0.0.1:6379> set k2 v2
OK
127.0.0.1:6379> set k3 v3
OK
查看对应文件位置
[root@db ~]# find / -name 'appendonlydir'
/rdbdata/appendonlydir
[root@db ~]# cd /rdbdata/
[root@db rdbdata]# ls -l
total 4
drwxr-xr-x. 2 root root 103 Jul 21 08:56 appendonlydir
-rw-r--r--. 1 root root 114 Jul 21 08:59 dump.rdb
查看文件里面的内容(开启AOF后产生)
[root@db rdbdata]# cd appendonlydir
[root@db appendonlydir]# ls -l
total 12
-rw-r--r--. 1 root root 88 Jul 21 08:56 appendonly.aof.1.base.rdb
-rw-r--r--. 1 root root 110 Jul 21 08:59 appendonly.aof.1.incr.aof
-rw-r--r--. 1 root root 88 Jul 21 08:56 appendonly.aof.manifest
查看文件里面的内容
[root@db appendonlydir]# cat appendonly.aof.1.incr.aof
*2(这个指令两部分组成)
$6(6个字符)
SELECT
$1(1个字符)
0
*3
$3
set
$2
k1
$2
v1
*3
$3
set
$2
k2
$2
v2
*3
$3
set
$2
k3
$2
v3
测试AOF会不会压缩瘦身(文件达到一定大小),可以手动触发(待补充)
127.0.0.1:6379> set k1 v4
OK
127.0.0.1:6379> set k1 v5
OK
127.0.0.1:6379> set k1 v6
OK
[root@db appendonlydir]# cat appendonly.aof.1.incr.aof
*2
$6
SELECT
$1
0
*3
$3
set
$2
k1
$2
v1
*3
$3
set
$2
k2
$2
v2
*3
$3
set
$2
k3
$2
v3
*3
$3
set
$2
k1
$2
v4
*3
$3
set
$2
k1
$2
v5
*3
$3
set
$2
k1
$2
v6
rewrite(待补充)