一、Redis AOF模式設置
修改配置文件redis.conf參數:
appendonly yes
# appendfsync always
appendfsync everysec
# appendfsync no
二、測試方法
創(chuàng)建多線程,其中每一個線程執(zhí)行一個無限循環(huán)向Redis 發(fā)送set key-value命令,由于處理器執(zhí)行一次循環(huán)操作的速度非???,因此這樣每一個線程都模擬了一個多并發(fā)的情況。
- <span style="font-size:18px;">class pushThread extends Thread {
- private JedisPool jedisPool;
- private Jedis jj;
- private String threadName;
- public pushThread(String threadName) {
- jedisPool = new JedisPool(new JedisPoolConfig(),"localhost");
- jj = jedisPool.getResource();
- this.threadName = threadName;
- }
- public void run() {
- int n = 1;
- for(;;) {
- jj.set("key" + threadName, "" + n);
- System.out.println(n + " has been set by " + threadName);
- n++;
- }
- }
- }</span>
…
- <span style="font-size:18px;">public static void main(String[] args) {
- for(int i = 0; i < 80; i++) {
- new pushThread("" + i).start();
- }
- }</span>
三、測試說明
1、讀取Redis的timeout異常
創(chuàng)建線程數在50以下時程序可以正常執(zhí)行,當線程數設置為100以上時,某些線程執(zhí)行出現異常:
java.net.SocketTimeoutException: Read timed out
造成這種異常可能有以下兩個原因:
原因一:在連接Redis的Jedis的默認構造方法中,超時一般被默認設置為2000毫秒,也就是2秒。當然這個時間,對于Redis這種從內存中讀取數據的數據庫來說應該是相當大了,但是為什么還會超時?可能的原因是,當Redis的數據量很大時,可能在Redis server可能會出現超時。因為Redis在運行時,是單線程來處理所有的客戶端的連接的。當連接數非常多或者數據量很大時,也要遵循FIFO的調度策略,這就造成等待隊列過長,因此可能會出現超時的情況。
解決方法:嘗試在調用jedis的構造方法時,將超時時間設置的更大些。
Jedis jedis = new Jedis("127.0.0.1", 8371,100000);//將超時時間設置為100000毫秒
原因二:因為Redis是基于TCP連接的,大量數據反復交互相當于遠程讀寫內存的操作,勢必會造成帶寬的使用緊張,在帶寬吃緊的情況下,Redis客戶端即Jedis拿不到連接或拿不到后續(xù)數據包。
解決方法:最直接的方法是增加帶寬,但針對這種問題,對并發(fā)交互數據的頻率進行調整,對數據量進行精減才是解決這一問題的最佳方案。
2、AOF模式相關問題與快照模式的優(yōu)點
創(chuàng)建50個線程,執(zhí)行1分鐘之后,每個線程大約循環(huán)了13800次,AOF日志(appendonly.aof)的大小是25.5M。Redis重啟時會先加載appendonly.aof文件,加載25M配置文件大約耗時5秒。同時做了多次突然關閉Redis 的試驗,日志記錄準確沒有出現丟失數據的情況。
AOF生成的命令日志,只是操作過程的記錄文件,它的主要作用是保證高可用性。因為在高并發(fā)的情況下,AOF日志文件appendonly.aof會迅速變得很大(當我將線程數調整為50,1分鐘appendonly.aof 的文件大小已達到了25M)。
Redis AOF rewrite(重新生成一份AOF文件)設置:
(1)Redis接收到客戶端發(fā)送的BGREWRITEAOF指令請求,執(zhí)行AOF rewrite;
(2)在Redis配置文件redis.conf中,如果用戶設置了auto-aof-rewrite-percentage和auto-aof-rewrite-min-size參數,當AOF日志文件大小大于auto-aof-rewrite-min-size,同時AOF文件大小的增長率大于auto-aof-rewrite-percentage時,會自動觸發(fā)AOF rewrite;
另外需要注意的是根據網上反饋AOF曾經出現過,因為個別命令導致 AOF 文件在重新載入時,無法恢復原樣的問題。
快照模式的優(yōu)點是:日志的內容更加緊湊,可以在加密后保存到其他數據中心或者亞馬遜 S3;快照可以最大化 Redis 的性能:父進程在保存快照文件時唯一要做的就是生成一個子進程,然后這個子進程就會處理接下來的所有保存工作,父進程無須執(zhí)行任何磁盤 I/O 操作;
快照在恢復大數據集時的速度比 AOF 的恢復速度要快。一個原因是快照文件中每一條數據只有一條記錄,不會像AOF日志那樣可能有一條數據的多次操作記錄。所以每條數據只需要寫一次就行了。另一個原因是快照文件的存儲格式和Redis數據在內存中的編碼格式是一致的,不需要再進行數據編碼工作,所以在CPU消耗上要小于AOF日志的加載。
四、部署架構說明
結合以上分析,建議采用如下的部署方式:Redis Master上不做持久化保證讀寫性能,Slave上同時開啟RDB(快照)和AOF,保證數據的安全性。當 Redis啟動時,程序會優(yōu)先使用 AOF 文件來恢復數據集,因為AOF文件所保存的數據通常是最完整的。
在服務器運行時對 RDB 文件進行備份。RDB文件一旦被創(chuàng)建,就不會進行任何修改,當服務器要創(chuàng)建一個新的RDB文件時,它先將文件的內容保存在一個臨時文件里,當臨時文件寫入完畢才會替換原來的RDB文件,因此備份RDB文件都是相對安全的。
本站僅提供存儲服務,所有內容均由用戶發(fā)布,如發(fā)現有害或侵權內容,請
點擊舉報。