持久化

轉(zhuǎn)載

Redis 是一個(gè)開源( BSD 許可)的,內(nèi)存中的數(shù)據(jù)結(jié)構(gòu)存儲(chǔ)系統(tǒng)腾供,它可以用作數(shù)據(jù)庫仆邓、緩存和消息中間件.

它支持的數(shù)據(jù)類型很豐富,如字符串伴鳖、鏈表节值、集合、以及散列等榜聂,并且還支持多種排序功能搞疗。

什么叫持久化?

用一句話可以將持久化概括為:將數(shù)據(jù)(如內(nèi)存中的對象)保存到可永久保存的存儲(chǔ)設(shè)備中。

持久化的主要應(yīng)用是將內(nèi)存中的對象存儲(chǔ)在數(shù)據(jù)庫中须肆,或者存儲(chǔ)在磁盤文件中匿乃、 XML 數(shù)據(jù)文件中等等桩皿。

也可以從如下兩個(gè)層面來理解持久化:

應(yīng)用層:如果關(guān)閉( Close )你的應(yīng)用,然后重新啟動(dòng)則先前的數(shù)據(jù)依然存在幢炸。

系統(tǒng)層:如果關(guān)閉( Shut Down )你的系統(tǒng)(電腦)泄隔,然后重新啟動(dòng)則先前的數(shù)據(jù)依然存在。

Redis 為什么要持久化?

Redis 中的數(shù)據(jù)類型都支持 Push/Pop宛徊、Add/Remove 及取交集并集和差集及更豐富的操作梅尤,而且這些操作都是原子性的。

在此基礎(chǔ)上岩调,Redis 支持各種不同方式的排序巷燥。與 Memcached 一樣,為了保證效率号枕,數(shù)據(jù)都是緩存在內(nèi)存中缰揪。

因?yàn)閿?shù)據(jù)都是緩存在內(nèi)存中的,當(dāng)你重啟系統(tǒng)或者關(guān)閉系統(tǒng)后葱淳,緩存在內(nèi)存中的數(shù)據(jù)都會(huì)消失殆盡钝腺,再也找不回來了。

所以赞厕,為了讓數(shù)據(jù)能夠長期保存艳狐,就要將 Redis 放在緩存中的數(shù)據(jù)做持久化存儲(chǔ)。

Redis 怎么實(shí)現(xiàn)持久化?

在設(shè)計(jì)之初皿桑,Redis 就已經(jīng)考慮到了這個(gè)問題毫目。官方提供了多種不同級別的數(shù)據(jù)持久化的方式:

RDB 持久化方式能夠在指定的時(shí)間間隔對你的數(shù)據(jù)進(jìn)行快照存儲(chǔ)。

AOF 持久化方式記錄每次對服務(wù)器寫的操作诲侮,當(dāng)服務(wù)器重啟的時(shí)候會(huì)重新執(zhí)行這些命令來恢復(fù)原始的數(shù)據(jù)镀虐,AOF 命令以 Redis 協(xié)議追加保存每次寫的操作到文件末尾。

Redis 還能對 AOF 文件進(jìn)行后臺(tái)重寫沟绪,使得 AOF 文件的體積不至于過大刮便。

如果你只希望你的數(shù)據(jù)在服務(wù)器運(yùn)行的時(shí)候存在,你也可以不使用任何持久化方式绽慈。

你也可以同時(shí)開啟兩種持久化方式恨旱,在這種情況下,當(dāng) Redis 重啟的時(shí)候會(huì)優(yōu)先載入 AOF 文件來恢復(fù)原始的數(shù)據(jù)坝疼,因?yàn)樵谕ǔG闆r下 AOF 文件保存的數(shù)據(jù)集要比 RDB 文件保存的數(shù)據(jù)集要完整搜贤。

如果你不知道該選擇哪一個(gè)級別的持久化方式,那我們就先來了解一下 AOF 方式和 RDB 方式有什么樣的區(qū)別裙士,并且它們各自有何優(yōu)劣入客,學(xué)習(xí)完之后,再來考慮該選擇哪一種級別。

RDB 方式與 AOF 方式的優(yōu)勢對比

RDB 方式與 AOF 方式的優(yōu)點(diǎn)對比

首先我們來看一看官方對于兩種方式的優(yōu)點(diǎn)描述桌硫,并做個(gè)對比夭咬,然后再看一看兩種方式的缺點(diǎn)描述。

RDB 方式的優(yōu)點(diǎn):

RDB 是一個(gè)非常緊湊的文件,它保存了某個(gè)時(shí)間點(diǎn)的數(shù)據(jù)集铆隘,非常適用于數(shù)據(jù)集的備份卓舵。

比如你可以在每個(gè)小時(shí)保存一下過去 24 小時(shí)內(nèi)的數(shù)據(jù),同時(shí)每天保存過去 30 天的數(shù)據(jù)膀钠,這樣即使出了問題你也可以根據(jù)需求恢復(fù)到不同版本的數(shù)據(jù)集掏湾。

RDB 是一個(gè)緊湊的單一文件,很方便傳送到另一個(gè)遠(yuǎn)端數(shù)據(jù)中心肿嘲,非常適用于災(zāi)難恢復(fù)融击。

RDB 在保存 RDB 文件時(shí)父進(jìn)程唯一需要做的就是 Fork 出一個(gè)子進(jìn)程,接下來的工作全部由子進(jìn)程來做雳窟,父進(jìn)程不需要再做其他 IO 操作尊浪,所以 RDB 持久化方式可以最大化 Redis 的性能。

與 AOF 相比封救,在恢復(fù)大的數(shù)據(jù)集的時(shí)候拇涤,RDB 方式會(huì)更快一些。

當(dāng) Redis 需要保存 dump.rdb 文件時(shí)誉结, 服務(wù)器執(zhí)行以下操作:

Redis 調(diào)用 Forks鹅士,同時(shí)擁有父進(jìn)程和子進(jìn)程。

子進(jìn)程將數(shù)據(jù)集寫入到一個(gè)臨時(shí) RDB 文件中惩坑。

當(dāng)子進(jìn)程完成對新 RDB 文件的寫入時(shí)掉盅,Redis 用新 RDB 文件替換原來的 RDB 文件,并刪除舊的 RDB 文件旭贬。

這種工作方式使得 Redis 可以從寫時(shí)復(fù)制(copy-on-write)機(jī)制中獲益怔接。

AOF 方式的優(yōu)點(diǎn):

使用 AOF 會(huì)讓你的 Redis 更加耐久。

你可以使用不同的 Fsync 策略:無 Fsync稀轨、每秒 Fsync 、每次寫的時(shí)候 Fsync 使用默認(rèn)的每秒 Fsync 策略岸军。

Redis 的性能依然很好( Fsync 是由后臺(tái)線程進(jìn)行處理的奋刽,主線程會(huì)盡力處理客戶端請求),一旦出現(xiàn)故障艰赞,你最多丟失 1 秒的數(shù)據(jù)佣谐。

AOF文件是一個(gè)只進(jìn)行追加的日志文件,所以不需要寫入 Seek方妖,即使由于某些原因(磁盤空間已滿狭魂,寫的過程中宕機(jī)等等)未執(zhí)行完整的寫入命令,你也可使用 redis-check-aof 工具修復(fù)這些問題。

Redis 可以在 AOF 文件體積變得過大時(shí)雌澄,自動(dòng)地在后臺(tái)對 AOF 進(jìn)行重寫: 重寫后的新 AOF 文件包含了恢復(fù)當(dāng)前數(shù)據(jù)集所需的最小命令集合斋泄。

整個(gè)重寫操作是絕對安全的,因?yàn)?Redis 在創(chuàng)建新 AOF 文件的過程中镐牺,會(huì)繼續(xù)將命令追加到現(xiàn)有的 AOF 文件里面炫掐,即使重寫過程中發(fā)生停機(jī),現(xiàn)有的 AOF 文件也不會(huì)丟失睬涧。

而一旦新 AOF 文件創(chuàng)建完畢募胃,Redis 就會(huì)從舊 AOF 文件切換到新 AOF 文件,并開始對新 AOF 文件進(jìn)行追加操作畦浓。

AOF 文件有序地保存了對數(shù)據(jù)庫執(zhí)行的所有寫入操作痹束,這些寫入操作以 Redis 協(xié)議的格式保存。

因此 AOF 文件的內(nèi)容非常容易被人讀懂讶请, 對文件進(jìn)行分析(parse)也很輕松参袱。導(dǎo)出(export) AOF 文件也非常簡單。

舉個(gè)例子秽梅,如果你不小心執(zhí)行了 FLUSHALL 命令抹蚀,但只要 AOF 文件未被重寫,那么只要停止服務(wù)器企垦, 移除 AOF 文件末尾的 FLUSHALL 命令环壤,并重啟 Redis ,就可以將數(shù)據(jù)集恢復(fù)到 FLUSHALL 執(zhí)行之前的狀態(tài)钞诡。

優(yōu)點(diǎn)對比總結(jié):

RDB 方式可以保存過去一段時(shí)間內(nèi)的數(shù)據(jù)郑现,并且保存結(jié)果是一個(gè)單一的文件壕探,可以將文件備份到其他服務(wù)器褥实,并且在回復(fù)大量數(shù)據(jù)的時(shí)候,RDB 方式的速度會(huì)比 AOF 方式的回復(fù)速度要快片排。

AOF 方式默認(rèn)每秒鐘備份 1 次朵诫,頻率很高辛友,它的操作方式是以追加的方式記錄日志而不是數(shù)據(jù),并且它的重寫過程是按順序進(jìn)行追加剪返,所以它的文件內(nèi)容非常容易讀懂废累。

可以在某些需要的時(shí)候打開 AOF 文件對其編輯,增加或刪除某些記錄脱盲,最后再執(zhí)行恢復(fù)操作邑滨。

RDB 方式與 AOF 方式的缺點(diǎn)對比

RDB 方式的缺點(diǎn):

如果你希望在 Redis 意外停止工作(例如電源中斷)的情況下丟失的數(shù)據(jù)最少的話,那么 RDB 不適合你钱反。

雖然你可以配置不同的 Save 時(shí)間點(diǎn)(例如每隔 5 分鐘并且對數(shù)據(jù)集有 100 個(gè)寫的操作)掖看,但是 Redis 要完整的保存整個(gè)數(shù)據(jù)集是一個(gè)比較繁重的工作匣距。

你通常會(huì)每隔 5 分鐘或者更久做一次完整的保存,萬一 Redis 意外宕機(jī)哎壳,你可能會(huì)丟失幾分鐘的數(shù)據(jù)毅待。

RDB 需要經(jīng)常 Fork 子進(jìn)程來保存數(shù)據(jù)集到硬盤上,當(dāng)數(shù)據(jù)集比較大的時(shí)耳峦,F(xiàn)ork 的過程是非常耗時(shí)的恩静,可能會(huì)導(dǎo)致 Redis 在一些毫秒級內(nèi)不能響應(yīng)客戶端的請求。

如果數(shù)據(jù)集巨大并且 CPU 性能不是很好的情況下蹲坷,這種情況會(huì)持續(xù) 1 秒驶乾,AOF 也需要 Fork,但是你可以調(diào)節(jié)重寫日志文件的頻率來提高數(shù)據(jù)集的耐久度循签。

AOF 方式的缺點(diǎn):

對于相同的數(shù)據(jù)集來說级乐,AOF 文件的體積通常要大于 RDB 文件的體積。

根據(jù)所使用的 Fsync 策略县匠,AOF 的速度可能會(huì)慢于 RDB风科。在一般情況下,每秒 Fsync 的性能依然非常高乞旦,而關(guān)閉 Fsync 可以讓 AOF 的速度和 RDB 一樣快贼穆,即使在高負(fù)荷之下也是如此。

不過在處理巨大的寫入載入時(shí)兰粉,RDB 可以提供更有保證的最大延遲時(shí)間(Latency)故痊。

缺點(diǎn)對比總結(jié):

RDB 由于備份頻率不高,所以在回復(fù)數(shù)據(jù)的時(shí)候有可能丟失一小段時(shí)間的數(shù)據(jù)玖姑,而且在數(shù)據(jù)集比較大的時(shí)候有可能對毫秒級的請求產(chǎn)生影響愕秫。

AOF 的文件提及比較大,而且由于保存頻率很高焰络,所以整體的速度會(huì)比 RDB 慢一些戴甩,但是性能依舊很高。

RDB 與 AOF 工作原理

AOF 重寫和 RDB 創(chuàng)建快照一樣闪彼,都巧妙地利用了寫時(shí)復(fù)制機(jī)制:

Redis 執(zhí)行 fork() 甜孤,現(xiàn)在同時(shí)擁有父進(jìn)程和子進(jìn)程。

子進(jìn)程開始將新 AOF 文件的內(nèi)容寫入到臨時(shí)文件备蚓。

對于所有新執(zhí)行的寫入命令课蔬,父進(jìn)程一邊將它們累積到一個(gè)內(nèi)存緩存中,一邊將這些改動(dòng)追加到現(xiàn)有 AOF 文件的末尾郊尝,這樣即使在重寫的中途發(fā)生停機(jī),現(xiàn)有的 AOF 文件也還是安全的战惊。

當(dāng)子進(jìn)程完成重寫工作時(shí)流昏,它給父進(jìn)程發(fā)送一個(gè)信號扎即,父進(jìn)程在接收到信號之后,將內(nèi)存緩存中的所有數(shù)據(jù)追加到新 AOF 文件的末尾况凉。

現(xiàn)在 Redis 原子地用新文件替換舊文件谚鄙,之后所有命令都會(huì)直接追加到新 AOF 文件的末尾。

付諸實(shí)踐刁绒,RDB 與 AOF 的實(shí)現(xiàn)

RDB 方式持久化的開啟與配置

Redis 默認(rèn)的持久化方式是 RDB 闷营,并且默認(rèn)是打開的。RDB 的保存方式分為主動(dòng)保存與被動(dòng)保存知市。

主動(dòng)保存可以在 redis-cli 中輸入 Save 即可;被動(dòng)保存需要滿足配置文件中設(shè)定的觸發(fā)條件傻盟,目前官方默認(rèn)的觸發(fā)條件可以在 redis.conf 中看到:

save 900 1save 300 10save 60 10000

其含義為:

服務(wù)器在900秒之內(nèi),對數(shù)據(jù)庫進(jìn)行了至少1次修改嫂丙。服務(wù)器在300秒之內(nèi)娘赴,對數(shù)據(jù)庫進(jìn)行了至少10次修改。服務(wù)器在60秒之內(nèi)跟啤,對數(shù)據(jù)庫進(jìn)行了至少10000次修改诽表。

滿足觸發(fā)條件后,數(shù)據(jù)就會(huì)被保存為快照隅肥,正是因?yàn)檫@樣才說 RDB 的數(shù)據(jù)完整性是比不上 AOF 的竿奏。

觸發(fā)保存條件后,會(huì)在指定的目錄生成一個(gè)名為 dump.rdb 的文件腥放,等到下一次啟動(dòng) Redis 時(shí)泛啸,Redis 會(huì)去讀取該目錄下的 dump.rdb 文件,將里面的數(shù)據(jù)恢復(fù)到 Redis捉片。

這個(gè)目錄在哪里呢?我們可以在客戶端中輸入命令 config get dir 查看:

gannicus@$ src/redis-cli

127.0.0.1:6379> config get dir

1) "dir"

2) "/home/gannicus/Documents/redis-5.0.0"

127.0.0.1:6379>

返回結(jié)果中的"/home/gannicus/Documents/redis-5.0.0"就是存放 dump.rdb 的目錄平痰。

在測試之前,說明一下前提:Redis 是直接從官網(wǎng)下載的壓縮包伍纫,解壓后得到 redis-x.x.x 文件夾宗雇。

比如我的是 redis-5.0.0,然后進(jìn)入文件夾莹规,在 redis-5.0.0 項(xiàng)目根目錄使用 make 命令安裝赔蒲。

RDB 被動(dòng)觸發(fā)保存測試

剛才提到它分為主動(dòng)保存與被動(dòng)觸發(fā),現(xiàn)在我們來測試一下被動(dòng)觸發(fā)良漱。首先啟動(dòng) redis-server舞虱,然后再打開客戶端 redis-cli ,先增添幾條記錄:

127.0.0.1:6379> set lca 1OK127.0.0.1:6379> set lcb 1OK127.0.0.1:6379> set lcc 1OK127.0.0.1:6379> set lcd 1OK127.0.0.1:6379> set lce 1OK127.0.0.1:6379> set lcf 1OK127.0.0.1:6379> set lcg 1OK127.0.0.1:6379> set lch 1OK127.0.0.1:6379> set lci 1OK127.0.0.1:6379> set lcj 1OK127.0.0.1:6379> set lck 1OK127.0.0.1:6379> set lcl 1OK127.0.0.1:6379> set lcm 1OK

可以看到母市,總共添加了 13 條記錄:

127.0.0.1:6379> keys * 1) "lca" 2) "lcd" 3) "lcg" 4) "lce" 5) "lcb" 6) "lcm" 7) "lcf" 8) "lci" 9) "lcl"10) "lcc"11) "lck"12) "lcj"13) "lch"127.0.0.1:6379>

然后發(fā)現(xiàn) redis-server 端的日志窗口中出現(xiàn)了如下的提示:

21971:M 21 Oct 2018 16:52:44.062 * 10 changes in 300 seconds. Saving...21971:M 21 Oct 2018 16:52:44.063 * Background saving started by pid 2255222552:C 21 Oct 2018 16:52:44.066 * DB saved on disk21971:M 21 Oct 2018 16:52:44.165 * Background saving terminated with success

從英文提示中可以大概讀懂這些內(nèi)容矾兜,它檢測到 300 秒內(nèi)有 10 條記錄被改動(dòng),剛才我們添加了 13 條數(shù)據(jù)記錄患久,滿足 redis.conf 中對于 RDB 數(shù)據(jù)保存的條件椅寺。

所以這里執(zhí)行數(shù)據(jù)保存操作浑槽,并且提示開辟了一個(gè) 22552 的進(jìn)程出來執(zhí)行保存操作,最后提示保存成功返帕。并且在目錄內(nèi)看到有 dump.rdb 文件生成桐玻。

現(xiàn)在將 Redis 進(jìn)程 Kill,哪些數(shù)據(jù)會(huì)被保存?通過命令 kill -9 pid ( pid 是進(jìn)程編號)模擬 Redis 異常關(guān)閉荆萤,然后再啟動(dòng) Redis 镊靴。

我們來看一看,到底是只保存了 10 條記錄還是 13 條全都保存下來了?

127.0.0.1:6379> keys * 1) "lcb" 2) "lcj" 3) "lcd" 4) "lch" 5) "lci" 6) "lcc" 7) "lcf" 8) "lce" 9) "lca"10) "lcg"127.0.0.1:6379>

重啟后查看記錄链韭,發(fā)現(xiàn) 13 條記錄中只有 10 條記錄會(huì)被保存偏竟,這也印證了之前所說,RDB 方式的數(shù)據(jù)完整性是不可靠的梧油,除非斷掉的那一刻正好是滿足觸發(fā)條件的條數(shù)苫耸。

關(guān)閉 RDB

剛才提到了,它是默認(rèn)啟用的儡陨,如果你不需要它可以在配置文件中將這 3 個(gè)配置注釋掉褪子,并新增 save " " 即可:

save ""

# save 900 1

# save 300 10

# save 60 10000

保存配置文件后需要重新啟動(dòng) Redis 服務(wù)才會(huì)生效,然后繼續(xù)添加十幾條記錄:

127.0.0.1:6379> keys *

1) "lcb"

...

23) "lca"

24) "lcg"

127.0.0.1:6379>

在之前已有 10 條的基礎(chǔ)上我再增加了 14 條記錄骗村,這次同樣要通過 kill 來模擬 Redis 異常關(guān)閉嫌褪,再啟動(dòng)服務(wù)看一看,數(shù)據(jù)是否還被保存:

127.0.0.1:6379> keys *

1) "lcb"

2) "lcj"

3) "lcd"

4) "lch"

5) "lci"

6) "lcc"

7) "lcf"

8) "lce"

9) "lca"

10) "lcg"

127.0.0.1:6379>

發(fā)現(xiàn)后面添加的 14 條記錄并沒有被保存胚股,恢復(fù)數(shù)據(jù)的時(shí)候僅僅只是恢復(fù)了之前的 10 條笼痛。

并且觀察 Redis 服務(wù)端窗口日志,并未發(fā)現(xiàn)像之前一樣的觸發(fā)保存的提示琅拌,證明 RDB 方式已經(jīng)被關(guān)閉缨伊。

RDB 主動(dòng)保存測試

通過配置文件關(guān)閉被動(dòng)觸發(fā),那么主動(dòng)關(guān)閉是否還會(huì)生效呢?

在 Redis 客戶端( redis-cli )通過 del 命令刪除幾條記錄进宝,然后輸入 save 命令執(zhí)行保存操作:

127.0.0.1:6379> keys *

1) "lcc"

2) "lch"

3) "lcb"

4) "lci"

5) "lce"

6) "lcj"

7) "lcg"

8) "lca"

9) "lcd"

10) "lcf"

127.0.0.1:6379> del lca lcb lcc

(integer) 3

127.0.0.1:6379> save

OK

127.0.0.1:6379>

可以看到 redis-server 的日志有新的提示:22598:M 21 Oct 2018 17:22:31.365 * DB saved on disk刻坊,它告訴我們數(shù)據(jù)已經(jīng)保存。

那么繼續(xù)模擬異常關(guān)閉党晋,再打開服務(wù)谭胚,看一看是否真的保存了這些操作:

127.0.0.1:6379> keys *

1) "lci"

2) "lcj"

3) "lcd"

4) "lcg"

5) "lcf"

6) "lce"

7) "lch"

127.0.0.1:6379>

果不其然,這幾個(gè)刪除操作都被保存了下來未玻,恢復(fù)過來的數(shù)據(jù)中已經(jīng)沒有那 3 條記錄了灾而,證明主動(dòng)關(guān)閉不受配置文件的影響。除了 Save 還有其他的保存方式么?

Save 和 Bgsave 保存

有的扳剿,Redis 提供了 Save 和 Bgsave 這兩種不同的保存方式旁趟,并且這兩個(gè)方式在執(zhí)行的時(shí)候都會(huì)調(diào)用 rdbSave 函數(shù)。

但它們調(diào)用的方式各有不同:

Save 直接調(diào)用 rdbSave方法 庇绽,阻塞 Redis 主進(jìn)程轻庆,直到保存完成為止癣猾。在主進(jìn)程阻塞期間敛劝,服務(wù)器不能處理客戶端的任何請求余爆。

Bgsave 則 Fork 出一個(gè)子進(jìn)程,子進(jìn)程負(fù)責(zé)調(diào)用 rdbSave 夸盟,并在保存完成之后向主進(jìn)程發(fā)送信號蛾方,通知保存已完成。

因?yàn)?rdbSave 在子進(jìn)程被調(diào)用上陕,所以 Redis 服務(wù)器在 Bgsave 執(zhí)行期間仍然可以繼續(xù)處理客戶端的請求桩砰。

Save 是同步操作,Bgsave 是異步操作释簿。Bgsave 命令的使用方法和 Save 命令的使用方法是一樣的:

127.0.0.1:6379> keys *

1) "lci"

2) "lcj"

3) "lcd"

4) "lcg"

5) "lcf"

6) "lce"

7) "lch"

127.0.0.1:6379> del lci lcj

(integer) 2

127.0.0.1:6379> bgsave

Background saving started

127.0.0.1:6379> keys *

1) "lcd"

2) "lcg"

3) "lcf"

4) "lce"

5) "lch"

127.0.0.1:6379>

Shutdown 保存

事實(shí)上亚隅,Shutdown 命令也是可以保存數(shù)據(jù)的,驚不驚喜庶溶。它會(huì)在關(guān)閉前將數(shù)據(jù)保存下來煮纵,意不意外?

127.0.0.1:6379> set app 1

OK

127.0.0.1:6379> set apps 1

OK

127.0.0.1:6379> keys *

1) "apps"

2) "lcd"

3) "lcg"

4) "lcf"

5) "app"

6) "lce"

7) "lch"

127.0.0.1:6379> shutdown

not connected> quit

gannicus@$

然后 Redis 服務(wù)就被關(guān)閉掉了。我們需要重新啟動(dòng) Redis 服務(wù)偏螺,到客戶端中看一看是否生效:

gannicus@$ src/redis-cli

127.0.0.1:6379> keys *

1) "lce"

2) "lcf"

3) "lcd"

4) "lch"

5) "lcg"

竟然沒有生效行疏,刺不刺激?這是為什么呢?明明官方文檔之 Shutdown 就說會(huì)保存了才退出的,你騙人~注意到套像,文檔中有一句:

恍然大悟酿联,原來是要在持久化被打開的情況下,通過 Shutdown 命令關(guān)閉才不會(huì)丟失數(shù)據(jù)夺巩,那么就到配置文件中將那幾個(gè) Save 的配置項(xiàng)打開吧:

# save ""save 900 1

save 300 10

save 60 10000

然后再開啟 Redis 服務(wù)贞让,再嘗試一遍(過程為:添加 -> shutdown -> 重啟服務(wù) -> 查看):

127.0.0.1:6379> set app 1

OK

127.0.0.1:6379> set apps 1

OK

127.0.0.1:6379> shutdown

not connected> quit

gannicus@$ src/redis-cli

127.0.0.1:6379> keys *

1) "lce"

2) "lch"

3) "app"

4) "lcf"

5) "apps"

6) "lcd"

7) "lcg"

127.0.0.1:6379>

這下終于弄明白了。

AOF 方式持久化的開啟與配置

開啟 AOF

默認(rèn)是不開啟 AOF 的柳譬,如果想要啟用則需要到 redis.conf 配置文件中開啟喳张,打開 redis.conf:

$ vim redis.conf

然后在文件中找到 appendonly 并將 no 改為 yes:

appendonly yes

即為開啟了 AOF 方式的持久化。

設(shè)置同步方式

AOF 還有支持幾種同步方式征绎,它們分別是:

appendfsync always # 每次有數(shù)據(jù)修改發(fā)生時(shí)都會(huì)寫入AOF文件(安全但是費(fèi)時(shí))蹲姐。

appendfsync everysec # 每秒鐘同步一次,該策略為AOF的缺省策略人柿。

appendfsync no # 從不同步柴墩。高效但是數(shù)據(jù)不會(huì)被持久化。

默認(rèn)配置是 everysec凫岖,你可以根據(jù)需求進(jìn)行調(diào)整江咳,這里我將配置改成 always:

appendfsync always

# appendfsync everysec

# appendfsync no

自定義 AOF 記錄文件的文件名

Redis 設(shè)置有默認(rèn)的文件名,在配置中顯示為:

appendfilename "appendonly.aof"

你可以讓其保持默認(rèn)名字哥放,也可以指定其他的文件名歼指,比如:

appendfilename "RNGLetme.aof"

將 appendonly爹土、appendfsync 和 appendfilename 設(shè)置好并保存。重新啟動(dòng) Redis 服務(wù):

$./redis-server

通過命令 ls 查看本地文件踩身,可以看到新生成了一個(gè)名為 RNGLetme.aof 的文件胀茵,可以使用:

$cat RNGLetme.aof

來查看里面的內(nèi)容,由于當(dāng)前未進(jìn)行數(shù)據(jù)的改動(dòng)挟阻,所以是空白的琼娘。然后打開 Redis 的客戶端:

$./redis-cli

并且添加幾條數(shù)據(jù)記錄:

127.0.0.1:6379> set rng lpl

OK

127.0.0.1:6379> set ig lpl

OK

127.0.0.1:6379> set edg lpl

OK

127.0.0.1:6379> keys *

1) "edg"

2) "rng"

3) "ig"

127.0.0.1:6379>

可以看到,成功添加了 rng附鸽、edg脱拼、ig 這三條記錄,然后打開 RNGLetme.aof 文件坷备,看看里面的記錄:

*2

$6

SELECT

$1

0

*3

$3

set

$3

rng

$3

lpl

*3

$3

set

$2

ig

$3

lpl

*3

$3

set

$3

edg

$3

lpl

每一次的數(shù)據(jù)添加都被記錄下來了熄浓。那如果是刪除操作呢,也會(huì)被記錄下來么?

127.0.0.1:6379> del edg

(integer) 1

127.0.0.1:6379> keys *

1) "rng"

2) "ig"

127.0.0.1:6379>

執(zhí)行完刪除操作后省撑,再看一看 RNGLetme.aof 文件中的記錄:

對比之前的記錄赌蔑,新增了 del edg 的操作記錄。這就印證了之前對 AOF 的描述:以日志的方式將數(shù)據(jù)變動(dòng)記錄下來丁侄。

AOF 恢復(fù)測試

下面同樣是通過 Kill 命令模擬 Redis 異常關(guān)閉:

gannicus@$ kill -9 22645

然后再重新啟動(dòng) Redis 服務(wù):

$ src/redis-server redis.conf

接著通過客戶端看一看惯雳,那些數(shù)據(jù)是否都在:

$ src/redis-cli

127.0.0.1:6379> keys *

1) "ig"

2) "rng"

可以看到,rng 和 ig 都還在鸿摇,意味著持久化是生效的石景。

怎樣從 RDB 方式切換為 AOF 方式

在 Redis 2.2 或以上版本,可以在不重啟的情況下拙吉,從 RDB 切換到 AOF :

為最新的 dump.rdb 文件創(chuàng)建一個(gè)備份潮孽、將備份放到一個(gè)安全的地方。

執(zhí)行以下兩條命令:

redis-cli config set appendonly yes

redis-cli config set save “”

確保寫命令會(huì)被正確地追加到 AOF 文件的末尾筷黔。執(zhí)行的第一條命令開啟了 AOF 功能:Redis 會(huì)阻塞直到初始 AOF 文件創(chuàng)建完成為止往史,之后 Redis 會(huì)繼續(xù)處理命令請求,并開始將寫入命令追加到 AOF 文件末尾佛舱。

執(zhí)行的第二條命令用于關(guān)閉 RDB 功能椎例。這一步是可選的,如果你愿意的話请祖,也可以同時(shí)使用 RDB 和 AOF 這兩種持久化功能订歪。

注意:別忘了在 redis.conf 中打開 AOF 功能!否則服務(wù)器重啟后,之前通過 CONFIG SET 命令設(shè)置的配置就會(huì)被遺忘肆捕,程序會(huì)按原來的配置來啟動(dòng)服務(wù)器刷晋。

優(yōu)先選擇 RDB 還是 AOF 呢?

分析對比兩種方式并做了測試后,發(fā)現(xiàn)這是兩種不同風(fēng)格的持久化方式。那么應(yīng)該如何選擇呢?

對于企業(yè)級的中大型應(yīng)用眼虱,如果不想犧牲數(shù)據(jù)完整性但是又希望保持高效率喻奥,那么你應(yīng)該同時(shí)使用 RDB 和 AOF 兩種方式。

如果你不打算耗費(fèi)精力在這個(gè)地方捏悬,只需要保證數(shù)據(jù)完整性撞蚕,那么優(yōu)先考慮使用 AOF 方式。

RDB 方式非常適合大規(guī)模的數(shù)據(jù)恢復(fù)邮破,如果業(yè)務(wù)對數(shù)據(jù)完整性和一致性要求不高诈豌,RDB 是很好的選擇。

備份 Redis 數(shù)據(jù)的建議

確保你的數(shù)據(jù)有完整的備份抒和,磁盤故障、節(jié)點(diǎn)失效等問題可能讓你的數(shù)據(jù)消失不見彤蔽, 不進(jìn)行備份是非常危險(xiǎn)的摧莽。

Redis 對于數(shù)據(jù)備份是非常友好的,因?yàn)槟憧梢栽诜?wù)器運(yùn)行的時(shí)候?qū)?RDB 文件進(jìn)行復(fù)制:RDB 文件一旦被創(chuàng)建顿痪,就不會(huì)進(jìn)行任何修改镊辕。

當(dāng)服務(wù)器要?jiǎng)?chuàng)建一個(gè)新的 RDB 文件時(shí),它先將文件的內(nèi)容保存在一個(gè)臨時(shí)文件里面蚁袭,當(dāng)臨時(shí)文件寫入完畢時(shí)征懈,程序才使用 rename(2) 原子地用臨時(shí)文件替換原來的 RDB 文件。

這也就是說揩悄,無論何時(shí)卖哎,復(fù)制 RDB 文件都是絕對安全的:

創(chuàng)建一個(gè)定期任務(wù)( cron job ),每小時(shí)將一個(gè) RDB 文件備份到一個(gè)文件夾删性,并且每天將一個(gè) RDB 文件備份到另一個(gè)文件夾亏娜。

確保快照的備份都帶有相應(yīng)的日期和時(shí)間信息蹬挺,每次執(zhí)行定期任務(wù)腳本時(shí)维贺,使用 Find 命令來刪除過期的快照:比如說你可以保留最近 48 小時(shí)內(nèi)的每小時(shí)快照,還可以保留最近一兩個(gè)月的每日快照巴帮。

至少每天一次溯泣,將 RDB 備份到你的數(shù)據(jù)中心之外,或者至少是備份到你運(yùn)行 Redis 服務(wù)器的物理機(jī)器之外榕茧。

Redis 密碼持久化

在 Redis 中數(shù)據(jù)需要持久化垃沦,密碼也要持久化。在客戶端通過命令:

config set requirepass zxc9527

可以為 Redis 設(shè)置值為 zxc9527 的密碼雪猪,但是當(dāng) Redis 關(guān)閉并重新啟動(dòng)后栏尚,權(quán)限驗(yàn)證功能就會(huì)失效,再也不需要密碼。

所以译仗,密碼也需要在 redis.conf 中持久化抬虽。打開 redis.conf 找到 requirepass 配置項(xiàng),取消其注釋并在后面設(shè)置密碼:

requirepass zxc9527

保存后重啟 Redis 服務(wù)纵菌,密碼持久化即生效阐污。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市咱圆,隨后出現(xiàn)的幾起案子笛辟,更是在濱河造成了極大的恐慌,老刑警劉巖序苏,帶你破解...
    沈念sama閱讀 223,002評論 6 519
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件手幢,死亡現(xiàn)場離奇詭異,居然都是意外死亡忱详,警方通過查閱死者的電腦和手機(jī)围来,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 95,357評論 3 400
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來匈睁,“玉大人监透,你說我怎么就攤上這事『剿簦” “怎么了胀蛮?”我有些...
    開封第一講書人閱讀 169,787評論 0 365
  • 文/不壞的土叔 我叫張陵,是天一觀的道長糯钙。 經(jīng)常有香客問我粪狼,道長,這世上最難降的妖魔是什么超营? 我笑而不...
    開封第一講書人閱讀 60,237評論 1 300
  • 正文 為了忘掉前任鸳玩,我火速辦了婚禮,結(jié)果婚禮上演闭,老公的妹妹穿的比我還像新娘不跟。我一直安慰自己,他們只是感情好米碰,可當(dāng)我...
    茶點(diǎn)故事閱讀 69,237評論 6 398
  • 文/花漫 我一把揭開白布窝革。 她就那樣靜靜地躺著,像睡著了一般吕座。 火紅的嫁衣襯著肌膚如雪虐译。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 52,821評論 1 314
  • 那天吴趴,我揣著相機(jī)與錄音漆诽,去河邊找鬼。 笑死,一個(gè)胖子當(dāng)著我的面吹牛厢拭,可吹牛的內(nèi)容都是我干的兰英。 我是一名探鬼主播,決...
    沈念sama閱讀 41,236評論 3 424
  • 文/蒼蘭香墨 我猛地睜開眼供鸠,長吁一口氣:“原來是場噩夢啊……” “哼畦贸!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起楞捂,我...
    開封第一講書人閱讀 40,196評論 0 277
  • 序言:老撾萬榮一對情侶失蹤薄坏,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后寨闹,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體胶坠,經(jīng)...
    沈念sama閱讀 46,716評論 1 320
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,794評論 3 343
  • 正文 我和宋清朗相戀三年鼻忠,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了涵但。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 40,928評論 1 353
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡帖蔓,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出瞳脓,到底是詐尸還是另有隱情塑娇,我是刑警寧澤,帶...
    沈念sama閱讀 36,583評論 5 351
  • 正文 年R本政府宣布劫侧,位于F島的核電站埋酬,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏烧栋。R本人自食惡果不足惜写妥,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 42,264評論 3 336
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望审姓。 院中可真熱鬧珍特,春花似錦、人聲如沸魔吐。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,755評論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽酬姆。三九已至嗜桌,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間辞色,已是汗流浹背骨宠。 一陣腳步聲響...
    開封第一講書人閱讀 33,869評論 1 274
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人层亿。 一個(gè)月前我還...
    沈念sama閱讀 49,378評論 3 379
  • 正文 我出身青樓桦卒,卻偏偏與公主長得像,于是被迫代替她去往敵國和親棕所。 傳聞我的和親對象是個(gè)殘疾皇子闸盔,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,937評論 2 361

推薦閱讀更多精彩內(nèi)容

  • 企業(yè)級redis集群架構(gòu)的特點(diǎn) 海量數(shù)據(jù) 高并發(fā) 高可用 要達(dá)到高可用,持久化是不可減少的琳省,持久化主要是做災(zāi)難恢復(fù)...
    lucode閱讀 2,208評論 0 7
  • 介紹 首先迎吵,我們應(yīng)該明確持久化的數(shù)據(jù)有什么用,答案是用于重啟后的數(shù)據(jù)恢復(fù)针贬。 Redis是一個(gè)內(nèi)存數(shù)據(jù)庫击费,無論是RD...
    小王寫bug閱讀 922評論 0 1
  • 從這篇文章開始,將依次介紹Redis高可用相關(guān)的知識——持久化桦他、復(fù)制(及讀寫分離)蔫巩、哨兵、以及集群快压。 本文將先說明...
    不變甄心閱讀 696評論 0 4
  • 以后,我們再聚…… 以后脉幢,我們再說…… 以后歪沃,我們再去…… 以后,我們再…… ...
    高飛的Dream閱讀 862評論 0 0
  • 大型企業(yè)分布式互聯(lián)網(wǎng)電子商務(wù)平臺(tái)嫌松,推出PC+微信+APP+云服務(wù)的云商平臺(tái)系統(tǒng)沪曙,其中包括B2B、B2C萎羔、C2C液走、O...
    swiftie10閱讀 175評論 3 3