redis筆記-數據庫之持久化策略
阿新 • • 發佈:2018-01-18
拒絕 ... last proc 分享圖片 才會 rewrite 文本格式 足夠 2018-1-17 by Atlas
- redis持久化
將redis在內存中的數據庫狀態保持到磁盤裏面,避免數據意外丟失。
- RDB持久化
- 既可以手動執行,也可以根據服務器配置選項定期執行。
- 生成的RDB文件是一個經過壓縮的二進制文件,通過該文件可以還原生成RDB文件時的數據庫狀態。
- RDB文件載入時,服務器一直處於阻塞狀態,直到完成。
命令SAVE、BGSAVE
SAVE命令會阻塞redis服務器進程,直到RDB文件創建完畢為止,在服務器進程阻塞期間,服務器不能處理任何命令請求。
BGSAVE命令會派生出一個子進程,然後由子進程負責創建RDB文件,服務器進程(父進程)繼續處理命令請求。- AOF文件更新頻率通常比RDB文件更新頻率高。
so -->
如果開啟AOF,服務器優先使用AOF文件還原數據庫;
只有AOF關閉,服務器才會使用RDB文件還原數據庫。
BGSAVE命令執行時的服務器狀態:
(1)BGSAVE執行期間,客戶端發送的SAVE命令會被服務器拒絕。
(2)BGSAVE執行期間,客戶端發送的BGSAVE命令會被服務器拒絕。
(3)BGSAVE和BGREWRITEAOF不能同時執行:
如果BGSAVE正在執行,那麽客戶端發送的BGREWRITEAOF會被延遲到BGSAVE後執行;
如果BGREWRITEAOF正在執行,那麽客戶端發送的BGSAVE會被服務器拒絕。- SAVE保存條件
save 900 1 服務器在900秒之內,對數據庫進行了至少1次修改
save 300 10 服務器在300秒之內,對數據庫進行了至少10次修改
save 60 10000 服務器在60秒之內,對數據庫進行了至少10000次修改
struct redisServer { // ... // 記錄保存條件的數組 struct saveparam *saveparams; // 修改計數器 long long dirty; // 上次執行保存的時間 time_t lastsave; // ... } struct saveparam { // 秒數 time_t seconds; // 修改數 int changes; }
ServerCron 函數檢查保存條件的過程
RDB文件結構將和JAVA CLASS文件一同討論。
- AOF持久化
- AOF持久化是通過保存redis服務器所執行的 寫命令 來記錄數據庫狀態的。
AOF文件內容是純文本格式。
e.g.
redis> SET msg "hello"
ok
AOF文件內容(SELECT命令是服務器自動添加的):
2\r\n$6\r\nSELECT\r\n$1\r\n0\r\n
3\r\n$3\r\n$3\r\nSET\r\n$3\r\nmsg\r\n$5\r\nhello\r\n- AOF持久化實現步驟:
命令追加 --> 文件寫入 --> 文件同步- 命令追加是將執行的寫命令追加到服務器狀態的aof_buf緩存區的末尾:
struct redisServer {
// ...
// AOF緩沖區
sds aof_buf;
// ...
}
- 文件的寫入與同步
flushAppendOnlyFile()函數考慮是否要將aof_buf中的內容寫入和保存到AOF文件裏面,行為由服務器配置的appendfsync選項的值來決定。- appendfsync配置:
always:AOF持久化效率最慢,安全性來說最安全,故障只會丟失一個命令數據。
everysec:AOF持久化效率足夠快,安全性來說,故障只會丟失一秒鐘的命令數據。
no:AOF持久化效率最快,安全性來說,故障會丟失上次同步AOF文件之後的所有寫命令數據。
- AOF 文件載入過程
- AOF文件重寫,解決AOF文件體積膨脹問題。
- AOF文件重寫原理:
AOF文件重寫並不需要對現有的AOF文件進行讀取、分析或者寫入操作,而是通過讀服務器當前的數據庫狀態來實現的。
AOF文件重寫首先從數據庫中讀取鍵現在的值,然後用一條命令記錄鍵值對,代替之前記錄這個鍵的多條命令。
如果元素數量超過redis.h/REDIS_AOF_REWRITE_ITEMS_PER_CMD常量的值,那麽重寫多條命令記錄鍵的值。- AOF文件後臺重寫過程(BGREWRITEAOF原理)
參考文獻:《redis設計與實現》
redis筆記-數據庫之持久化策略