日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > 数据库 >内容正文

数据库

Redis持久化锦囊在手,再也不会担心数据丢失了

發布時間:2025/3/16 数据库 48 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Redis持久化锦囊在手,再也不会担心数据丢失了 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

Redis 的讀寫都是在內存中進行的,所以它的性能高。而當我們的服務器斷開或者重啟的時候,數據就會消失,那么我們該怎么解決這個問題呢?

其實 Redis 已經為我們提供了一種持久化的機制,分別是 RDB 和 AOF 兩種方式,接下來跟著我一起看看這兩個錦囊都是怎么保證數據的持久化的。

持久化

由于 Redis 是基于內存的數據庫,所以當服務器出現故障的時候,我們的數據就得不到安全保障。

這個時候就需要將內存中的數據存儲到磁盤中,當我們服務器重啟時,便可以通過磁盤來恢復數據,這個過程就叫做 Redis 持久化。

Redis持久化

?

?

RDB

簡介

RDB全稱Redis Database Backup file(Redis數據備份文件),也可以稱為Redis數據快照。

  • RDB 文件是一個經過壓縮的二進制文件(默認:dump.rdb);

  • RDB 文件保存在硬盤里;

  • 通過保存數據庫中的鍵值對來記錄數據庫狀態。

創建

當 Redis 持久化時,程序會將當前內存中的數據庫狀態保存到磁盤中。

創建

創建 RDB 文件主要有兩個 Redis 命令:SAVE 和 BGSAVE。

SAVE

同步操作,執行命令時,會阻塞 Redis 服務器進程,拒絕客戶端發送的命令請求。

代碼示例:

def?SAVE():#?創建?RDB?文件rdbSave()

圖示:

Save命令

BGSAVE

異步操作,執行命令時,子進程執行保存工作,服務器還可以繼續讓主線程處理客戶端發送的命令請求。

代碼示例:

def?BGSAVE():#?創建子進程pid?=?fork()if?pid?==?0:#?子進程負責創建?RDB?文件rdbSave()#?完成之后向父進程發送信號signal_parent()elif?pid?>?0:#?父進程繼續處理命令請求,并通過輪訓等待子進程的信號handle_request_and_wait_signal()else:handle_fork_error()

圖示:

bgSave命令

載入

載入工作在服務器啟動時自動執行。

載入

服務器在載入 RDB 文件期間,會一直處于阻塞狀態,直到載入工作完成為止。

主要設置

Redis 允許用戶通過設置服務器配置的 save 選項,讓服務器每隔一段時間自動執行一次 BGSAVE 命令。

設置保存條件

提供配置如下:

save?900?1 save?300?10

在這種情況下,只要滿足以下條件中的一個,BGSAVE 命令就會被執行:

  • 服務器在 900 秒之內,對數據庫進行了至少 1 次修改了;

  • 服務器在 300 秒之內,對數據庫進行了至少 10 次修改。

saveparams

服務器程序會根據 save 選項所設置的保存條件,設置服務器狀態 redisServer 結構的 saveparams 屬性。

  • saveparams 屬性是一個數組;

  • 數組中的每一個元素都是一個 saveparam 結構;

  • 每個 saveparam 結構都保存了一個 save 選項設置的保存條件。

struct?saveparam?{//?秒數time_t?seconds;//?修改數int?changes; }
dirty

dirty 計數器記錄距離上一次成功執行 SAVE 命令或 BGSAVE 命令之后,服務器對數據庫狀態進行了多少次修改(包括寫入、刪除、更新等操作)。

lastsave

是一個 UNINX 時間戳,記錄了服務器上一次成功執行 SAVE 命令或者 BGSAVE 命令的時間。

檢查保存條件是否滿足

服務器周期性操作函數 serverCron (該函數對正在運行的服務器進行維護)默認每隔 100 毫秒就會執行一次,其中一項工作就是檢查 save 選項所設置的保存條件是否已經滿足,滿足的話就執行 BGSAVE 命令。

代碼示例:

def?serverCron():#?....#?遍歷所有保存條件for?saveparam?in?server.saveparams:#?計算距離上次執行保存操作有多少秒save_interval?=?unixtime_now()?-?server.lastsave#?如果數據庫狀態的修改次數超過條件所設置的次數#?如果距離上次保存的時間超過條件所設置的時間if?server.dirty?>=?saveparam.changes?and?save_interval?>?saveparam.seconds:BGSAVE()

默認配置

RDB 文件默認的配置如下:

################################?SNAPSHOTTING??################################ # #?Save?the?DB?on?disk: #在給定的秒數和給定的對數據庫的寫操作數下,自動持久化操作。 #???save?<seconds>?<changes> #? save?900?1 save?300?10 save?60?10000#bgsave發生錯誤時是否停止寫入,一般為yes stop-writes-on-bgsave-error?yes#持久化時是否使用LZF壓縮字符串對象? rdbcompression?yes#是否對rdb文件進行校驗和檢驗,通常為yes rdbchecksum?yes#?RDB持久化文件名 dbfilename?dump.rdb#持久化文件存儲目錄 dir?./

?

?

AOF

簡介

AOF全稱為 Append Only File(追加日志文件)。日志是寫后日志,Redis 是先執行命令,把數據寫入內存,然后才記錄日志。

寫后日志

  • 通過保存 Redis 服務器所執行的寫命令來記錄數據庫狀態;

  • 寫入 AOF 文件的所有命令都是以 Redis 的命令請求協議格式保存的。

實現

AOF 持久化流程實現主要是通過以下流程來實現的:

AOF流程

命令追加

若 AOF 持久化功能處于打開狀態,服務器在執行完一個命令后,會以協議格式將被執行的寫命令追加到服務器狀態的 aof_buf 緩沖區的末尾。

文件同步

服務器每次結束一個事件循環之前,都會調用 flushAppendOnlyFile 函數,這個函數會考慮是否需要將 aof_buf 緩沖區中的內容寫入和保存到 AOF 文件里。

flushAppendOnlyFile 函數執行以下流程:

  • WRITE:根據條件,將 aof_buf 中的緩存寫入到 AOF 文件;

  • SAVE:根據條件,調用 fsync 或 fdatasync 函數,將 AOF 文件保存到磁盤中。

這個函數是由服務器配置的 appendfsync 的三個值:always、everysec、no 來影響的,也被稱為三種策略。

Always

每條命令都會 fsync 到硬盤中,這樣 redis 的寫入數據就不會丟失。

Always

everysec

每秒都會刷新緩沖區到硬盤中(默認值)。

everysec

no

根據當前操作系統的規則決定什么時候刷新到硬盤中,不需要我們來考慮。

no

數據加載

  • 創建一個不帶網絡連接的偽客戶端;

  • 從 AOF 文件中分析并讀取出一條寫命令;

  • 使用偽客戶端執行被讀出的寫命令;

  • 一直執行步驟 2 和 3,直到 AOF 文件中的所有寫命令都被處理完畢為止。

  • 文件重寫

    為何需要文件重寫:

    • 為了解決 AOF 文件體積膨脹的問題;

    • 通過重寫創建一個新的 AOF 文件來替代現有的 AOF 文件,新的 AOF 文件不會包含任何浪費空間的冗余命令。

    實現

    文件重寫的實現原理:

    • 不需要對現有的 AOF 文件進行任何操作;

    • 從數據庫中直接讀取鍵現在的值;

    • 用一條命令記錄鍵值對,從而代替之前記錄這個鍵值對的多條命令。

    后臺重寫

    為不阻塞父進程,Redis 將 AOF 重寫程序放到子進程里執行。

    在子進程執行 AOF 重寫期間,服務器進程需要執行三個流程:

  • 執行客戶端發來的命令;

  • 將執行后的寫命令追加到 AOF 緩沖區;

  • 將執行后的寫命令追加到 AOF 重寫緩沖區。

  • 服務器流程

    默認配置

    AOF 文件默認的配置如下:

    ##############################?APPEND?ONLY?MODE?################################開啟AOF持久化方式 appendonly?no#AOF持久化文件名 appendfilename?"appendonly.aof" #每秒把緩沖區的數據fsync到磁盤 appendfsync?everysec #?appendfsync?no #是否在執行重寫時不同步數據到AOF文件 no-appendfsync-on-rewrite?no#?觸發AOF文件執行重寫的增長率 auto-aof-rewrite-percentage?100 #觸發AOF文件執行重寫的最小size auto-aof-rewrite-min-size?64mb#redis在恢復時,會忽略最后一條可能存在問題的指令 aof-load-truncated?yes#是否打開混合開關 aof-use-rdb-preamble?yes

    ?

    ?

    總結

    通過以上的簡介,想必大家都對 Redis 持久化有了大致的了解,那么這兩種方式,我們該如何選擇呢?

    • 對于大中型的應用,我們既想保證數據完整性又想保證高效率,就應該結合使用 RDB 和 AOF 兩種方式;

    • 如果只是需要保證數據的完整性,保護數據不會丟失,那么優先使用 AOF 方式;

    • 如果是處理大規模的數據恢復,追求更高更快的效率的話,優先使用 RDB 方式。

    也可以參照下圖進行選擇:

    主要對比

    有道無術,術可成;有術無道,止于術

    歡迎大家關注Java之道公眾號

    好文章,我在看??

    總結

    以上是生活随笔為你收集整理的Redis持久化锦囊在手,再也不会担心数据丢失了的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。