Redis如何只使用内存存储而不持久化存储数据在内存中如何存储

在 SegmentFault,学习技能、解决问题
每个月,我们帮助 1000 万的开发者解决各种各样的技术问题。并助力他们在技术能力、职业生涯、影响力上获得提升。
问题对人有帮助,内容完整,我也想知道答案
问题没有实际价值,缺少关键内容,没有改进余地
Redis如何只使用内存存储而不持久化存储数据(每次重启数据都将变空),也就是说把他当作一个类似于Memcache的内存型缓存来使用,怎么做?
答案对人有帮助,有参考价值
答案没帮助,是错误的答案,答非所问
不启用持久化即可,注释掉save 一行。
答案对人有帮助,有参考价值
答案没帮助,是错误的答案,答非所问
redis配置里注释掉 save 行
同步到新浪微博
分享到微博?
关闭理由:
删除理由:
忽略理由:
推广(招聘、广告、SEO 等)方面的内容
与已有问题重复(请编辑该提问指向已有相同问题)
答非所问,不符合答题要求
宜作评论而非答案
带有人身攻击、辱骂、仇恨等违反条款的内容
无法获得确切结果的问题
非开发直接相关的问题
非技术提问的讨论型问题
其他原因(请补充说明)
我要该,理由是:
在 SegmentFault,学习技能、解决问题
每个月,我们帮助 1000 万的开发者解决各种各样的技术问题。并助力他们在技术能力、职业生涯、影响力上获得提升。redis内存数据的持久化方式
的强大性能很大程度上都是因为所有数据都是存储在内存中的,然而当Redis重启后,所有存储在内存中的数据将会丢失,在很多情况下是无法容忍这样的事情的。所以,我们需要将内存中的数据持久化!典型的需要持久化数据的场景如下:
将Redis作为数据库使用;将Redis作为缓存服务器使用,但是缓存miss后会对性能造成很大影响,所有缓存同时失效时会造成服务雪崩,无法响应。
本文介绍Redis所支持的两种数据持久化方式。
Redis支持两种数据持久化方式:RDB方式和AOF方式。前者会根据配置的规则定时将内存中的数据持久化到硬盘上,后者则是在每次执行写命令之后将命令记录下来。两种持久化方式可以单独使用,但是通常会将两者结合使用。
RDB方式的持久化是通过快照的方式完成的。当符合某种规则时,会将内存中的数据全量生成一份副本存储到硬盘上,这个过程称作”快照”,Redis会在以下几种情况下对数据进行快照:
根据配置规则进行自动快照;用户执行SAVE, BGSAVE命令;执行FLUSHALL命令;执行复制(replication)时。
Redis允许用户自定义快照条件,当满足条件时自动执行快照,快照规则的配置方式如下:
save 900 1
save 300 10
save 60 10000
每个快照条件独占一行,他们之间是或(||)关系,只要满足任何一个就进行快照。上面配置save后的第一个参数T是时间,单位是秒,第二个参数M是更改的键的个数,含义是:当时间T内被更改的键的个数大于M时,自动进行快照。比如save 900 1的含义是15分钟内(900s)被更改的键的个数大于1时,自动进行快照操作。
除了让Redis自动进行快照外,当我们需要重启,迁移,备份Redis时,我们也可以手动执行SAVE或BGSAVE命令主动进行快照操作。
SAVE命令:当执行SAVE命令时,Redis同步进行快照操作,期间会阻塞所有来自客户端的请求,所以放数据库数据较多时,应该避免使用该命令;BGSAVE命令: 从命令名字就能看出来,这个命令与SAVE命令的区别就在于该命令的快照操作是在后台异步进行的,进行快照操作的同时还能处理来自客户端的请求。执行BGSAVE命令后Redis会马上返回OK表示开始进行快照操作,如果想知道快照操作是否已经完成,可以使用LASTSAVE命令返回最近一次成功执行快照的时间,返回结果是一个Unix时间戳。
当执行FLUSHALL命令时,Redis会清除中的所有数据。需要注意的是:不论清空数据库的过程是否触发 了自动快照的条件,只要自动快照条件不为空,Redis就会执行一次快照操作,当没有定义自动快照条件时,执行FLUSHALL命令不会进行快照操作。
当设置了主从模式时,Redis会在复制初始化是进行自动快照。
Redis默认会将快照文件存储在Redis当前进程的工作目录的dump.rdb文件中,可以通过配置文件中的dir和dbfilename两个参数分别指定快照文件的存储路径和文件名,例如:
dbfilename dump.rdb
dir /opt/soft/redis-3.0.4/cache
快照执行的过程如下:
Redis使用fork函数复制一份当前进程(父进程)的副本(子进程);父进程继续处理来自客户端的请求,子进程开始将内存中的数据写入硬盘中的临时文件;当子进程写完所有的数据后,用该临时文件替换旧的RDB文件,至此,一次快照操作完成。
需要注意的是:
在执行fork是时候(类Unix操作系统)会使用写时复制(copy-on-write)策略,即fork函数发生的一刻,父进程和子进程共享同一块内存数据,当父进程需要修改其中的某片数据(如执行写命令)时,操作系统会将该片数据复制一份以保证子进程不受影响,所以RDB文件存储的是执行fork操作那一刻的内存数据。所以RDB方式理论上是会存在丢数据的情况的(fork之后修改的的那些没有写进RDB文件)。
通过上述的介绍可以知道,快照进行时时不会修改RDB文件的,只有完成的时候才会用临时文件替换老的RDB文件,所以就保证任何时候RDB文件的都是完整的。这使得我们可以通过定时备份RDB文件来实现Redis数据的备份。RDB文件是经过压缩处理的二进制文件,所以占用的空间会小于内存中数据的大小,更有利于传输。
Redis启动时会自动读取RDB快照文件,将数据从硬盘载入到内存,根据数量的不同,这个过程持续的时间也不尽相同,通常来讲,一个记录1000万个字符串类型键,大小为1GB的快照文件载入到内存需要20-30秒的时间。
下面演示RDB方式持久化,首先使用配置有如下快照规则:
save 900 1
save 300 10
save 60 10000
dbfilename dump.rdb
dir /opt/soft/redis-3.0.4/cache
的配置文件/opt/soft/redis-3.0.4/conf/redis.conf启动Redis服务:
然后通过客户端设置一个键值:
[qifuguang@Mac~]$ /opt/soft/redis-3.0.4/src/redis-cli -p 6379
127.0.0.1:6379& set test-rdb HelloWorld
127.0.0.1:6379& get test-rdb
"HelloWorld"
127.0.0.1:6379&
现在强行kill Redis服务:
现在到/opt/soft/redis-3.0.4/cache目录看,目录下出现了Redis的快照文件dump.rdb:
[qifuguang@Mac/opt/soft/redis-3.0.4/cache]$ ls
现在重新启动Redis:
然后再用客户端连接,检查之前设置的key是否还存在:
[qifuguang@Mac~]$ /opt/soft/redis-3.0.4/src/redis-cli -p 6379
127.0.0.1:6379& get test-rdb
"HelloWorld"
127.0.0.1:6379&
可以发现,之前设置的key在Redis重启之后又通过快照文件dump.rdb恢复了。
在使用Redis存储非临时数据时,一般都需要打开AOF持久化来降低进程终止导致的数据丢失,AOF可以将Redis执行的每一条写命令追加到硬盘文件中,这已过程显然会降低Redis的性能,但是大部分情况下这个影响是可以接受的,另外,使用较快的硬盘能提高AOF的性能。
默认情况下,Redis没有开启AOF(append only file)持久化功能,可以通过在配置文件中作如下配置启用:
appendonly yes
开启之后,Redis每执行一条写命令就会将该命令写入硬盘中的AOF文件。AOF文件保存路径和RDB文件路径是一致的,都是通过dir参数配置,默认文件名是:appendonly.aof,可以通过配置appendonlyfilename参数修改,例如:
AOF纯文本的形式记录了Redis执行的写命令,例如在开启AOF持久化的情况下执行如下命令:
[qifuguang@Mac/opt/soft/redis-3.0.4]$ ./src/redis-cli
127.0.0.1:6379&
127.0.0.1:6379&
127.0.0.1:6379&
127.0.0.1:6379& set aof1 value1
127.0.0.1:6379& set aof2 value2
127.0.0.1:6379&
然后查看/opt/soft/redis-3.0.4/cache/appendonly.aof文件:
[qifuguang@Mac/opt/soft/redis-3.0.4/cache]$ cat appendonly.aof
文件中的内容正是Redis刚才执行的命令的内容,内容的格式就先不展开叙述了。
假设Redis执行了如下命令:
[qifuguang@Mac/opt/soft/redis-3.0.4]$ ./src/redis-cli
127.0.0.1:6379&
127.0.0.1:6379&
127.0.0.1:6379&
127.0.0.1:6379& set k v1
127.0.0.1:6379& set k v2
127.0.0.1:6379& set k v3
127.0.0.1:6379&
如果这所有的命令都写到AOF文件的话,将是一个比较蠢行为,因为前面两个命令会被第三个命令覆盖,所以AOF文件完全不需要保存前面两个文件,事实上Redis确实就是这么做的。删除AOF文件中无用的命令的过程成为”AOF重写”,AOF重写可以在配置文件中做相应的配置,当满足配置的条件时,自动进行AOF重写操作。配置如下:
auto-aof-rewrite-percentage 100
auto-aof-rewrite-min-size 64mb
第一行的意思是,目前的AOF文件的大小超过上一次重写时的AOF文件的百分之多少时再次进行重写,如果之前没有重写过,则以启动时AOF文件大小为依据。
第二行的意思是,当AOF文件的大小大于64MB时才进行重写,因为如果AOF文件本来就很小时,有几个无效的命令也是无伤大雅的事情。
这两个配置项通常一起使用。
我们还可以手动执行BDREWRITEAOF命令主动让Redis重写AOF文件,执行重写命令之后查看现在的AOF文件:
[qifuguang@Mac/opt/soft/redis-3.0.4]$ cat cache/appendonly.aof
可以看到,文件中并没有再记录set k v1这样的无效命令。
虽然每次执行更改数据库的内容时,AOF都会记录执行的命令,但是由于操作系统本身的硬盘缓存的缘故,AOF文件的内容并没有真正地写入硬盘,在默认情况下,操作系统会每隔30s将硬盘缓存中的数据同步到硬盘,但是为了防止系统异常退出而导致丢数据的情况发生,我们还可以在Redis的配置文件中配置这个同步的频率:
# appendfsync always
appendfsync everysec
# appendfsync no
第一行表示每次AOF写入一个命令都会执行同步操作,这是最安全也是最慢的方式;
第二行表示每秒钟进行一次同步操作,一般来说使用这种方式已经足够;
第三行表示不主动进行同步操作,这是最不安全的方式。
总结:redis的持久化
Snapshotting(快照)RDB
修改配置文件,在指定时间内修改的键个数大于设定的值执行save,参数:秒数,修改的键个数
save 900 1
save 300 10
save 60 10000
配置文件不起作用是因为重启的时候没有加配置文件的参数,例如:
redis-server
/tsh/redis-3.0.0/redis.conf
append only file(AOF模式)
修改配置文件redis.conf,appendonly yes
重启服务,一定有加上配置文件的参数
此时在 src目录下生成文件appendonly.aof,这个文件记录了每一步的操作,效率稍慢但是更安全
没有更多推荐了,Redis持久化磁盘IO方式及其带来的问题   有Redis线上运维经验的人会发现Redis在物理内存使用比较多,但还没有超过实际物理内存总容量时就会发生不稳定甚至崩溃的问题,有人认为是基于快照方式持
时间: 17:47:09
&&&& 阅读:660
&&&& 评论:
&&&& 收藏:0
标签:&&&&&&&&&&&&&&&&&&&&&&&&&&&转自:http://blog.csdn.net/kaosini/article/details/9176961
一、对持久化的探讨与理解&&&&是一个支持持久化的内存,也就是说redis需要经常将内存中的数据同步到磁盘来保证持久化。redis支持两种持久化方式,一种是 Snapshot(RDB)也是默认方式,另一种是Append only file(AOF)的方式。具体的理论说明请见。&&&&我们应该明确持久化的数据有什么用,答案是用于重启后的数据恢复。Redis是一个内存数据库,无论是RDB还是AOF,都只是其保证数据恢复的措施。所以Redis在利用RDB和AOF进行恢复的时候,都会读取RDB或AOF文件,重新加载到内存中。
&&&&RDB就是Snapshot快照存储,是默认的持久化方式。即按照一定的策略周期性的将数据保存到磁盘。对应产生的数据文件为dump.rdb,通过配置文件中的save参数来定义快照的周期。Redis支持将当前数据的快照存成一个数据文件的持久化机制。而一个持续写入的数据库如何生成快照呢。Redis借助了fork命令的copy on write机制。在生成快照时,将当前进程fork出一个子进程,然后在子进程中循环所有的数据,将数据写成为RDB文件。&&& Redis的RDB文件不会坏掉,因为其写操作是在一个新进程中进行的。当生成一个新的RDB文件时,Redis生成的子进程会先将数据写到一个临时文件中,然后通过原子性rename系统调用将临时文件重命名为RDB文件。这样在任何时候出现故障,Redis的RDB文件都总是可用的。并且Redis的RDB文件也是Redis主从同步内部实现中的一环:第一次Slave向Master同步的实现是:Slave向Master发出同步请求,Master先dump出rdb文件,然后将rdb文件全量传输给slave,然后Master把缓存的命令转发给Slave,初次同步完成。第二次以及以后的同步实现是:Master将变量的快照直接实时依次发送给各个Slave。但不管什么原因导致Slave和Master断开重连都会重复以上两个步骤的过程。Redis的主从复制是建立在内存快照的持久化基础上的,只要有Slave就一定会有内存快照发生。&&& 不足:就是一旦数据库出现问题,那么我们的RDB文件中保存的数据并不是全新的,从上次RDB文件生成到Redis停机这段时间的数据全部丢掉了(因为刷写机制还没有出发)。RDB就是Snapshot快照存储,是默认的持久化方式。相关参数:
1 ################################ SNAPSHOTTING
#################################
2 # Save the DB on disk:
设置sedis进行数据库镜像的频率。
900秒(15分钟)内至少1个key值改变(则进行数据库保存--持久化)。
300秒(5分钟)内至少10个key值改变(则进行数据库保存--持久化)。
60秒(1分钟)内至少10000个key值改变(则进行数据库保存--持久化)。
7 save 900 1
8 save 300 10
9 save 60 10000
11 stop-writes-on-bgsave-error yes
12 # 在进行镜像备份时,是否进行压缩。yes:压缩,但是需要一些cpu的消耗。no:不压缩,需要更多的磁盘空间。
13 rdbcompression yes
14 # 一个CRC64的校验就被放在了文件末尾,当存储或者加载rbd文件的时候会有一个10%左右的性能下降,为了达到性能的最大化,你可以关掉这个配置项。
15 rdbchecksum yes
16 # 快照的文件名
17 dbfilename dump.rdb
18 # 存放快照的目录
19 dir /var/lib/redis
&&&&&AOF(Append Only File)比RDB方式有更好的持久化性。由于在使用AOF持久化方式时,Redis会将每一个收到的写命令都通过Write函数追加到文件中,类似于的binlog。当Redis重启是会通过重新执行文件中保存的写命令来在内存中重建整个数据库的内容。&&&& AOF的完全持久化方式同时也带来了另一个问题,持久化文件会变得越来越大。(比如我们调用INCR test命令100次,文件中就必须保存全部的100条命令,但其实99条都是多余的。因为要恢复数据库的状态其实文件中保存一条SET test 100就够了)。为了压缩AOF的持久化文件,Redis提供了bgrewriteaof命令。收到此命令后Redis将使用与快照类似的方式将内存中的数据以命令的方式保存到临时文件中,最后替换原来的文件,以此来实现控制AOF文件的增长。由于是模拟快照的过程,因此在重写AOF文件时并没有读取旧的AOF文件,而是将整个内存中的数据库内容用命令的方式重写了一个新的AOF文件。相关参数:
1 ############################## APPEND ONLY MODE ###############################
2 # 是否开启AOF,默认关闭(no)
3 appendonly yes
4 # 指定 AOF 文件名
5 appendfilename appendonly.aof
6 # Redis支持三种不同的刷写模式:
7 # appendfsync always #每次收到写命令就立即强制写入磁盘,是最有保证的完全的持久化,但速度也是最慢的,一般不推荐使用。
8 appendfsync everysec #每秒钟强制写入磁盘一次,在性能和持久化方面做了很好的折中,是受推荐的方式。
9 # appendfsync no
#完全依赖OS的写入,一般为30秒左右一次,性能最好但是持久化最没有保证,不被推荐。
11 #在日志重写时,不进行命令追加操作,而只是将其放在缓冲区里,避免与命令的追加造成DISK IO上的冲突。
12 #设置为yes表示rewrite期间对新写操作不fsync,暂时存在内存中,等rewrite完成后再写入,默认为no,建议yes
13 no-appendfsync-on-rewrite yes
14 #当前AOF文件大小是上次日志重写得到AOF文件大小的二倍时,自动启动新的日志重写过程。
15 auto-aof-rewrite-percentage 100
16 #当前AOF文件启动新的日志重写过程的最小值,避免刚刚启动Reids时由于文件尺寸较小导致频繁的重写。
17 auto-aof-rewrite-min-size 64mb
到底选择什么呢?下面是来自官方的建议:通常,如果你要想提供很高的数据保障性,那么建议你同时使用两种持久化方式。如果你可以接受灾难带来的几分钟的数据丢失,那么你可以仅使用RDB。很多用户仅使用了AOF,但是我们建议,既然RDB可以时不时的给数据做个完整的快照,并且提供更快的重启,所以最好还是也使用RDB。在数据恢复方面:RDB的启动时间会更短,原因有两个:一是RDB文件中每一条数据只有一条记录,不会像AOF日志那样可能有一条数据的多次操作记录。所以每条数据只需要写一次就行了。另一个原因是RDB文件的存储格式和Redis数据在内存中的编码格式是一致的,不需要再进行数据编码工作,所以在CPU消耗上要远小于AOF日志的加载。&
&&&&&&上面说了RDB快照的持久化,需要注意:在进行快照的时候(save),fork出来进行dump操作的子进程会占用与父进程一样的内存,真正的copy-on-write,对性能的影响和内存的耗用都是比较大的。比如机器8G内存,Redis已经使用了6G内存,这时save的话会再生成6G,变成12G,大于系统的8G。这时候会发生交换;要是虚拟内存不够则会崩溃,导致数据丢失。所以在用redis的时候一定对系统内存做好容量规划。
&&&&& 目前,通常的设计思路是利用Replication机制来弥补aof、snapshot性能上的不足,达到了数据可持久化。即Master上Snapshot和AOF都不做,来保证Master的读写性能,而Slave上则同时开启Snapshot和AOF来进行持久化,保证数据的安全性。
二、对Redis持久化的
通过上面的理论对snapshot和aof有了一定的理解,下面开始进行一些测试::1、redis.conf 基本配置: 开启snapshot,关闭aof
1 save 900 1
2 save 300 10
3 save 60 10000
5 rdbcompression no
6 rdbchecksum no
7 dbfilename zhoujy.rdb
8 dir /var/lib/redis
10 appendonly
1 redis 127.0.0.1:6379& keys *
#查看0库下是否有key
2 (empty list or set)
3 redis 127.0.0.1:6379& set name zhoujinyi
5 redis 127.0.0.1:6379& set sex man
7 redis 127.0.0.1:6379& set age 27
9 redis 127.0.0.1:6379& keys *
10 1) "age"
11 2) "sex"
12 3) "name"
13 redis 127.0.0.1:6379&
14 zhoujy@zhoujy:~$ ls -lh /var/lib/redis/
#rdb文件初始化大小
15 总用量 4.0K
16 -rw-rw---- 1 redis redis 18
16:19 zhoujy.rdb
17 zhoujy@zhoujy:~$ redis
18 redis 127.0.0.1:6379& save
#保存,进行持久化,每执行一次save,会在日至里面记录一条:“ * DB saved on disk ”
20 redis 127.0.0.1:6379&
21 zhoujy@zhoujy:~$ ls -lh /var/lib/redis/
#文件大小改变,数据写入文件进行了持久化
22 总用量 4.0K
23 -rw-rw---- 1 redis redis 52
16:20 zhoujy.rdb
25 验证持久化,重启redis:
27 redis 127.0.0.1:6379& keys *
28 1) "name"
29 2) "age"
30 3) "sex"
31 redis 127.0.0.1:6379& set address hangzhou
#key没有被保存就重启了
33 redis 127.0.0.1:6379&
34 zhoujy@zhoujy:~$ sudo /etc/init.d/redis-server restart
35 Stopping redis-server: redis-server.
36 Starting redis-server: redis-server.
37 zhoujy@zhoujy:~$ redis
38 redis 127.0.0.1:6379& keys *
#发现刚才没有被保存的key也被持久化了,怎么回事?
39 1) "name"
40 2) "address"
41 3) "sex"
42 4) "age"
43 redis 127.0.0.1:6379&
45 查看日志,看看日志里面有什么信息:
47 [21154] 25 May 16:28:12.122 # User requested shutdown...
48 [21154] 25 May 16:28:12.122 * Saving the final RDB snapshot before exiting.
49 [21154] 25 May 16:28:12.165 * DB saved on disk
50 [21154] 25 May 16:28:12.165 * Removing the pid file.
51 [21154] 25 May 16:28:12.165 * Removing the unix socket file.
52 [21154] 25 May 16:28:12.165 # Redis is now ready to exit, bye bye...
54 从日志里面得到了解释,正常关闭redis,他会自己在关闭前执行save命令。那异常关闭呢? 用kill的效果和上面一样,属于正常关闭。只能用kill -9 才行:54
55 redis 127.0.0.1:6379& keys *
56 1) "age"
57 2) "name"
58 3) "sex"
59 4) "address"
60 redis 127.0.0.1:6379& set company dxy
62 redis 127.0.0.1:6379& keys *
63 1) "name"
64 2) "sex"
65 3) "age"
66 4) "address"
67 5) "company"
68 redis 127.0.0.1:6379&
#key没有被保存就重启了
69 zhoujy@zhoujy:~$ sudo kill -9 21250
70 zhoujy@zhoujy:~$ redis
71 Could not connect to Redis at 127.0.0.1:6379: Connection refused
72 not connected&
73 zhoujy@zhoujy:~$ sudo /etc/init.d/redis-server start
74 Starting redis-server: redis-server.
75 zhoujy@zhoujy:~$ redis
76 redis 127.0.0.1:6379& keys *
#company没有被持久化,数据丢失,重启日志里没有“* DB saved on disk” 信息
77 1) "sex"
78 2) "age"
79 3) "address"
80 4) "name"
81 redis 127.0.0.1:6379&
从上面的结果看出,开启RDB持久化,在满足save条件、手动save、正常关闭的时候数据都会被持久化,而异常关闭终止的时候数据丢失。
&2、redis.conf 基本配置: 关闭snapshot,关闭aof
1 #save 900 1
2 #save 300 10
3 #save 60 10000
4 rdbcompression no
5 rdbchecksum no
6 dbfilename zhoujy.rdb
7 dir /var/lib/redis
9 appendonly
1 redis 127.0.0.1:6379& keys *
#查看0库下是否有key
2 (empty list or set)
3 redis 127.0.0.1:6379& set name zhoujinyi
5 redis 127.0.0.1:6379& set sex man
7 redis 127.0.0.1:6379& set age 27
9 redis 127.0.0.1:6379& save
#保存,进行持久化,即使没有开始snapshot,执行save命令一样可以持久化,不手动的触发永远不会持久化。
#每执行一次save,会在日志里面记录一条:“ * DB saved on disk ”
11 redis 127.0.0.1:6379& set address hangzhou
#set操作,但不save,正常重启
13 redis 127.0.0.1:6379&
14 zhoujy@zhoujy:~$ sudo /etc/init.d/redis-server restart #正常重启
15 [sudo] password for zhoujy:
16 Stopping redis-server: redis-server.
17 Starting redis-server: redis-server.
18 zhoujy@zhoujy:~$ redis
19 redis 127.0.0.1:6379& keys *
#发现刚才没有被保存的key丢失了
20 1) "sex"
21 2) "name"
22 3) "age"
23 redis 127.0.0.1:6379&
从上面的结果看出,关闭持久化,只有在手动save的时候数据都会被持久化,正常关闭的时候数据丢失。要是从一开始到关闭写入的数据没有手动save,则数据全部丢失!既然能手动save间接的说明了快照一直都存在,所以不能说是禁止snapshot,应该是禁止自动snapshot功能。
通过1,2验证了之前说的:一旦数据库出现问题,那么我们的RDB文件中保存的数据并不是全新的。
3、redis.conf 基本配置: 关闭snapshot,开启aof
1 #save 900 1
2 #save 300 10
3 #save 60 10000
5 appendonly
6 appendfilename zhoujy.aof
7 # appendfsync always
8 appendfsync everysec
9 # appendfsync no
11 no-appendfsync-on-rewrite no
12 auto-aof-rewrite-min-size 64mb
1 #重启数据库之前有3个key:
2 redis 127.0.0.1:6379& keys *
3 1) "sex"
4 2) "age"
5 3) "name"
6 #修改开启AOF参数,重启数据库:
7 zhoujy@zhoujy:~$ ls -lh /var/lib/redis/
8 总用量 4.0K
9 -rw-r----- 1 redis redis
17:41 appendonly.aof
#aof持久化已经开启,0字节大小
10 -rw-rw---- 1 redis redis 52
17:34 zhoujy.rdb
12 redis 127.0.0.1:6379& keys *
#数据库里面没有记录?之前还有3个key,Why?
13 (empty list or set)
14 redis 127.0.0.1:6379&
16 #查看日志:
17 * DB loaded from append only file: 0.000 seconds
18 发现是从0字节的aof文件里面同步数据,为什么不同步rdb的数据?原来redis代码里面写好了优先级,AOF&RDB
20 redis.c里的代码如下:
22 void loadDataFromDisk(void) {
long long start = ustime();
if (server.aof_state == REDIS_AOF_ON) {
if (loadAppendOnlyFile(server.aof_filename) == REDIS_OK)
redisLog(REDIS_NOTICE,"DB loaded from append only file: %.3f seconds",(float)(ustime()-start)/1000000);
if (rdbLoad(server.rdb_filename) == REDIS_OK) {
redisLog(REDIS_NOTICE,"DB loaded from disk: %.3f seconds",
(float)(ustime()-start)/1000000);
} else if (errno != ENOENT) {
redisLog(REDIS_WARNING,"Fatal error loading the DB: %s. Exiting.",strerror(errno));
&&&&&这里需要注意的是:当中途开启AOF,重启让他生效的时候,千万不能再让他第2次正常重启了。因为第一次重启让aof生效的时候,启动redis已经读取这个文件了,导致此时的redis数据为空的(优先级)。要是再重启的,则会把这个空的数据save到RDB文件,这样导致RDB原有的数据被替换,导致数据丢失。所以一定要小心,为了避免悲剧的发生,当要重启redis的时候最好都备份下RDB文件。
1 redis 127.0.0.1:6379& keys *
2 (empty list or set)
3 redis 127.0.0.1:6379& set name zhoujinyi
5 redis 127.0.0.1:6379& save
8 #开启aof参数,重启redis生效(第一次重启)
9 root@m2:/var/lib/redis# /etc/init.d/redis-server restart
10 Stopping redis-server: redis-server stop!.
11 Starting redis-server: redis-server start!
12 root@m2:/var/lib/redis# ls -lh #生成aof文件,已经生效
13 总用量 4.0K
14 -rw-r----- 1 root root
5月 26 01:12 appendonly.aof
15 -rw-rw---- 1 root root 36
5月 26 01:12 dump.rdb
17 redis 127.0.0.1:6379& keys *
#如上面所说的优先级原因:aof & rdb,结果为空
18 (empty list or set)
20 #再重启(第2次正常重启),把上面空的结果save到了RDB,数据丢失。此时的db是空的,日志记录 "* DB saved on disk"21 root@m2:/var/lib/redis# /etc/init.d/redis-server restart
22 Stopping redis-server: redis-server stop!.
23 Starting redis-server: redis-server start!
25 root@m2:/var/lib/redis# ls -lh
#数据已经被初始化了,数据丢失。
26 总用量 4.0K
27 -rw-r----- 1 root root
5月 26 01:12 appendonly.aof
28 -rw-rw---- 1 root root 18
5月 26 01:13 dump.rdb
29 redis 127.0.0.1:6379& keys *
30 (empty list or set)
&&&& 这里就有一个问题,比如在用redis的时候,刚开始只开启RDB的持久方式,AOF没有开启,在跑一段时间之后想开启AOF,那如何把RDB的数据直接写到AOF文件呢?有2种方法:①: 在开启AOF之前,先执行bgrewriteaof,再重启。
1 redis 127.0.0.1:6379& keys *
#查看是否有数据
2 (empty list or set)
3 redis 127.0.0.1:6379& set name zhoujinyi
5 redis 127.0.0.1:6379& set sex man
7 redis 127.0.0.1:6379& set age 27
9 redis 127.0.0.1:6379& keys *
10 1) "name"
11 2) "sex"
12 3) "age"
13 redis 127.0.0.1:6379& bgsave
14 Background saving started
15 redis 127.0.0.1:6379& keys *
16 1) "name"
17 2) "sex"
18 3) "age"
19 root@m2:/var/lib/redis# ls -lh
#只有一个RDB文件,没有AOF文件
20 总用量 4.0K
21 -rw-rw---- 1 root root 52
5月 25 23:48 dump.rdb
23 redis 127.0.0.1:6379& bgrewriteaof
#执行合并重写功能,生成AOF文件
24 Background append only file rewriting started
26 root@m2:/var/lib/redis# ls -lh
#AOF文件生成成功
27 总用量 8.0K
28 -rw-rw---- 1 root root 122
5月 25 23:49 appendonly.aof
29 -rw-rw---- 1 root root
5月 25 23:48 dump.rdb
30 #这时候去打开redis.conf 文件中的aof参数(appendonly yes),重启生效。
31 root@m2:/var/lib/redis# /etc/init.d/redis-server restart
32 Stopping redis-server: redis-server stop!33 Starting redis-server: redis-server start!
35 #日志里面出现:* DB loaded from append only file: 0.000 seconds
37 redis 127.0.0.1:6379& keys *
38 1) "sex"
39 2) "name"
40 3) "age"
②: 利用CONFIG GET/SET 的方法动态修改配置文件,和①比少了重启的操作。
1 redis 127.0.0.1:6379& set name zhoujinyi
3 redis 127.0.0.1:6379& set sex man
5 redis 127.0.0.1:6379& set age 27
7 redis 127.0.0.1:6379& keys *
8 1) "age"
9 2) "name"
10 3) "sex"
11 redis 127.0.0.1:6379& BGSAVE
12 Background saving started
13 redis 127.0.0.1:6379&
15 root@m2:/var/lib/redis# ls -lh
#只有rdb文件
16 总用量 4.0K
17 -rw-rw---- 1 root root 52
5月 26 00:09 dump.rdb
19 #动态修改参数,把aof功能开启:appendonly yes
21 redis 127.0.0.1:6379& CONFIG GET append*
#在线查看参数
22 1) "appendonly"
23 2) "no"
24 3) "appendfsync"
25 4) "everysec"
26 redis 127.0.0.1:6379& CONFIG SET appendonly yes
#动态修改参数
28 redis 127.0.0.1:6379& CONFIG GET append*
29 1) "appendonly"
30 2) "yes"
31 3) "appendfsync"
32 4) "everysec"
33 redis 127.0.0.1:6379&
35 root@m2:/var/lib/redis# ls -lh
#aof文件已经生成,并且有数据(同步rdb)。
36 总用量 8.0K
37 -rw-rw---- 1 root root 122
5月 26 00:10 appendonly.aof
38 -rw-rw---- 1 root root
5月 26 00:09 dump.rdb
40 #日志里面的信息:* Background append only file rewriting started by pid 3165
41 #因为参数是动态修改的,在重启之后会失效,所以在维护的时候修改redis.conf文件的参数即可。
&从上面的结果看出,redis读取aof的文件要先于rdb文件,所以尽量一开始开启aof选项,不要在中途开启。通过日志可以很清楚的知道redis通过那个文件来取数据的:RDB:&& * DB loaded from disk: 0.000 secondsAOF: * DB loaded from append only file: 0.000 seconds保存数据则是:RDB:* DB saved on diskAOF:& * Calling fsync() on the AOF file.
4、redis.conf 基本配置: 开启snapshot,开启aof
1 save 900 1
2 save 300 10
3 save 60 10000
5 appendonly
6 appendfilename zhoujy.aof
# appendfsync always
8 appendfsync everysec
# appendfsync no
11 no-appendfsync-on-rewrite no
12 auto-aof-rewrite-min-size 64mb
1 #同时开启这2个参数,在日志里面会记录:
2 * Calling fsync() on the AOF file.
3 * DB saved on disk
5 redis 127.0.0.1:6379& keys *
6 (empty list or set)
7 redis 127.0.0.1:6379& set name zhoujinyi
9 redis 127.0.0.1:6379& set age 27
11 redis 127.0.0.1:6379& set sex man
13 redis 127.0.0.1:6379& keys *
14 1) "name"
15 2) "age"
16 3) "sex"
18 root@m2:/var/lib/redis# ls -lh
#aof,rdb 2个文件已经生成,并且aof文件大小根据操作命令实时增加,而rbd需要手动save或则到了刷写机制的阀值才增加
19 总用量 8.0K
20 -rw-r----- 1 root root 122
5月 26 00:39 appendonly.aof
21 -rw-rw---- 1 root root
5月 26 00:37 dump.rdb
23 redis 127.0.0.1:6379& save
26 root@m2:/var/lib/redis# ls -lh
#rdb文件大小增加
27 总用量 8.0K
28 -rw-r----- 1 root root 136
5月 26 00:41 appendonly.aof
29 -rw-rw---- 1 root root
5月 26 00:41 dump.rdb
31 redis 127.0.0.1:6379& flushall
#清除所有数据
34 root@m2:/var/lib/redis# ls -lh
#数据清除之后,rdb文件大小初始化了,而aof文件却增加了,Why?
35 总用量 8.0K
36 -rw-r----- 1 root root 154
5月 26 00:43 appendonly.aof
37 -rw-rw---- 1 root root
5月 26 00:43 dump.rdb
38 #原来aof文件记录的是修改数据的操作,所以文件是追加形式的,flushall命令被追加到最后。
40 root@m2:/var/lib/redis# /etc/init.d/redis-server restart
#重启,看看通过aof的载入能否被读取到?
41 Stopping redis-server: redis-server stop!.
42 Starting redis-server: redis-server start!
43 root@m2:/var/lib/redis# ls -lh
#aof文件大小不变,重启不能初始化aof文件
44 总用量 8.0K
45 -rw-r----- 1 root root 154
5月 26 00:43 appendonly.aof
46 -rw-rw---- 1 root root
5月 26 00:45 dump.rdb
48 redis 127.0.0.1:6379& keys *
#日志里面记录“* DB loaded from append only file: 0.012 seconds”,但没有数据,说明aof确实被初始化了。
49 (empty list or set)
51 #因为数据都已经被清除了,想让aof文件大小也初始化掉,该如何操作呢?
52 很简单:
53 redis 127.0.0.1:6379& bgrewriteaof
#让aof合并重写,因为aof文件的最后一条记录的flushall操作,前面的记录都无效了,合并所有操作之后就初始化了。
54 Background append only file rewriting started
55 redis 127.0.0.1:6379&
57 root@m2:/var/lib/redis# ls -lh
#aof文件被初始化
58 总用量 4.0K
59 -rw-rw---- 1 root root
5月 26 00:51 appendonly.aof
60 -rw-rw---- 1 root root 18
5月 26 00:45 dump.rdb
通过上面的这些测试,已经说明RDB和AOF他们的操作方式,以及如重启时的载入,重启时将按照以下优先级恢复数据到内存:&?如果只配置AOF,重启时加载AOF文件恢复数据。&?如果同时 配置了RBD和AOF,启动是只加载AOF文件恢复数据。&?如果只配置RBD,启动是讲加载dump文件恢复数据。
为了防止悲剧的发生,我们应该进行备份。
三、对Redis备份
备份很简单,只需要把RDB,AOF的文件复制备份起来就可以了。相同版本的备份文件可以任意使用。不同版本没有试过。
1 #redisA: A上生成测试数据
2 redis 127.0.0.1:6379& set name zhoujinyi
4 redis 127.0.0.1:6379& set sex man
6 redis 127.0.0.1:6379& set age 17
8 redis 127.0.0.1:6379& keys *
9 1) "age"
10 2) "name"
11 3) "sex"
12 redis 127.0.0.1:6379& bgsave
13 Background saving started
19 #redisB: B上没有数据
20 redis 127.0.0.1:6380& keys *
21 (empty list or set)
23 #复制A的文件到B(rdb和aof文件)
24 cp redis/* redis2/
25 #修改权限
26 chown -R redis.redis *
28 zhoujy@m2:~$ redis -p 6380 shutdown
29 zhoujy@m2:~$ redis -p 6380
30 #还原成功
31 redis 127.0.0.1:6380& keys *
32 1) "sex"
33 2) "name"
34 3) "age"
以上完成。标签:&&&&&&&&&&&&&&&&&&&&&&&&&&&原文:http://www.cnblogs.com/yycc/p/7449420.html
教程昨日排行
&&国之画&&&& &&&&&&
&& &&&&&&&&&&&&&&
鲁ICP备号-4
打开技术之扣,分享程序人生!

我要回帖

更多关于 长整型数据在内存中的存储形式是 的文章

 

随机推荐