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

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

redis 哨兵 异步_redis 使用历程

發(fā)布時間:2023/12/15 编程问答 27 豆豆
生活随笔 收集整理的這篇文章主要介紹了 redis 哨兵 异步_redis 使用历程 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

redis 使用歷程

為什么使用redis緩存?

答:之前是沒有使用redis的,直接用Java代碼寫類緩存功能,有些系統(tǒng)參數(shù)方面也是采用直接查詢數(shù)據(jù)庫。此中間還出現(xiàn)過一些其他問題,后面才選擇redis。

先說下不使用緩存會造成哪些影響:

1、在項目中,為避免不斷查詢數(shù)據(jù)庫,給數(shù)據(jù)庫造成壓力,需要將生效的用戶充值地址加入到緩存中,剛開始直接使用ArrayList,但是在測試階段就發(fā)現(xiàn),在不斷將新的地址加入到ArrayList中,會出現(xiàn)添加異常情況,同時導(dǎo)致應(yīng)用假死情況,后來經(jīng)排查發(fā)現(xiàn)ArrayList非線程安全,然后采用CopyOnWriteArrayList(該list適合讀多寫少的情況),這個很好的解決了問題。雖然CopyOnWriteArrayList解決了并發(fā)問題,但是在性能上不理想,每次有新的地址添加到list中都會創(chuàng)建新的列表,并將之前的列表通過 Arrays.copyOf(elements, len + 1); 效率低下,且如果緩存的用戶地址太多(比如幾萬、十幾萬時),在每次發(fā)生新增是會造成內(nèi)存使用短期飆升的情況。

2、同時在項目中還有些系統(tǒng)配置參數(shù),在業(yè)務(wù)處理中會根據(jù)配置參數(shù)執(zhí)行對應(yīng)的邏輯(比如:是否允許提現(xiàn)、每日最大提現(xiàn)額度,定時任務(wù)是否執(zhí)行等),但是這些系統(tǒng)參數(shù)基本上不怎么變動,在不斷的查詢數(shù)據(jù)庫也是一種浪費。

3、對一些用戶訪問量大的數(shù)據(jù),直接訪問數(shù)據(jù)庫,在高并發(fā)情況下,可能會導(dǎo)致項目掛掉。

4、自己寫的本地緩存方案可能存在一些潛在的未知問題。

基于上述情況,開始加入緩存技術(shù),并就緩存方案進行選型。

緩存方案選型

目前市面上主流的緩存方案有兩種:redis、memcache。我為什么放棄memcache而選擇redis呢?

1、從支持的數(shù)據(jù)類型方面:memcache只支持簡單數(shù)據(jù)類型,需要客戶端自己處理復(fù)雜對象;而redis支持的類型,除String、List、Hash、Set、SortedSet外,還支持pub/sub(不支持持久化,如果消費者當時不在現(xiàn)場,則消息丟失,可靠的操作還是選擇消息隊列)、Transaction、HyperLogLog(非精確的去重統(tǒng)計,伯努利實驗及拋硬幣)、bloomFilter(避免擊穿)等功能。

2、從持久化方面:memcached不支持持久化,redis支持持久化(可通過aof,rdb)

3、從線程角度:redis是單線程(但單機就可支持10萬的并發(fā)量,且不需要考慮上下文切換等問題,如果并發(fā)量太大,可以考慮多機部署方案【主從復(fù)制、哨兵模式、集群模式等】),memcache多線程。

4、綜上,我選擇redis作為項目的緩存方案。

使用redis常見問題

1、緩存集中到期問題(緩存設(shè)置的時候,設(shè)置了固定的到期時長,如果同一段時間集中加入緩存,則會存在集中過期的情況,在剛好過期時嗎,如果有大量請求進來,則可能會存在短暫卡頓,或者雪崩現(xiàn)象,甚至導(dǎo)致訪問數(shù)據(jù)庫癱瘓)

解決方案:

1、在某些基本不怎么變動的緩存,設(shè)置永不過期(必要時手動更新)

2、對需要設(shè)置過期時間的, 過期時間大小加個隨機數(shù),將集中過期變的分散些,降低緩存雪崩概率。

2、緩存穿透&緩存擊穿

先說【緩存穿透】,指的是請求查詢緩存及數(shù)據(jù)庫均不存在的數(shù)據(jù)。比如查詢用戶id(一般都是正數(shù)遞增的),你查詢負數(shù)或者其他字符串肯定不會存在,且請求會不斷打到db上。避免方案是對請求數(shù)據(jù)的合法性進行校驗(權(quán)限校驗、參數(shù)校驗),還有就是采用布隆過濾器(原理是采用bitmap位圖,緩存的key會議bit的方式存入布隆過濾器上, 如果在布隆過濾器上能找到,則可能存在,否則肯定不存在),然后在進行緩存查詢、數(shù)據(jù)庫查詢。

緩存擊穿:在key失效瞬間(比如過期失效),大量請求打到數(shù)據(jù)庫上。

3、分布式鎖

說白了就是通過setnx(key不存在則設(shè)值)命令向緩存中設(shè)值。如果設(shè)值成功則獲取鎖,為避免加鎖后忘記釋放,通過expire設(shè)值鎖失效時間;若設(shè)值不成功,則加鎖失敗。但是有可能在加鎖后,還沒來得及設(shè)值過期時間,程序掛掉,需要采用setIfAbsent(K key, V value, long timeout, TimeUnit unit) 記得是這個方法。

但是:雖然解決了鎖過期無法釋放的問題,但設(shè)置的過期時間不能保證我當前獲取鎖的線程執(zhí)行完成了,假如業(yè)務(wù)線比較長,在鎖過期后還沒有正常執(zhí)行完成,又有可能引發(fā)其他問題。

4、假如在線上環(huán)境中有上億個key,如何找出以某些字符串開頭key的值,為什么不能使用keys *?

首先說下為什么不能使用keys * ,因為redis是單線程。使用keys 時會導(dǎo)致其他線程阻塞,導(dǎo)致其他請求進來時需要等待,直到key【且key沒有l(wèi)imit,會全部遍歷】 執(zhí)行完成,如果剛好在執(zhí)行key命令時,大量請求進來,那就GG了。推薦方案:采用scan方式,該命令可無阻塞的獲取指定模式的key列表。該命令的缺點是可能會存在一定的重復(fù)(為什么會存在重復(fù)呢?因為redis底層采用hashMap進行的實現(xiàn),也就是說數(shù)據(jù)結(jié)構(gòu)是數(shù)組加鏈表,如果在查詢過程中存在擴容或者鎖容時,就會出現(xiàn)重復(fù)),需要業(yè)務(wù)系統(tǒng)進行去重。

5、redis異步消息

可以采用list數(shù)據(jù)結(jié)構(gòu)進行處理。lpush 加入消息、然后rpop獲取消息,如果list為空,則阻塞。或者rpush加入消息,lpop獲取消息。這樣保證了消息的先進先出;如果lpush、lpop或rpush、rpop則是先進后出。

6、redis延時隊列

可通過sortedSet數(shù)據(jù)結(jié)構(gòu),通過zadd添加消息,每次添加時對score自增(建議方案是采用時間戳,但是別神經(jīng)病調(diào)整系統(tǒng)時間,不然就把自己找地埋了吧),消費時使用zrangebyscore(讀取數(shù)據(jù)后,業(yè)務(wù)方根據(jù)業(yè)務(wù)邏輯處理)

7、Pipeline操作

redis的管道命令,可以批量將多個請求發(fā)送給服務(wù)端,中間不需要等待請求的回復(fù),只需要最后一并讀取結(jié)果就可以了。但是在集群模式下,不能直接使用Pipeline,否則可能會報錯。

原因:集群模式下,各集群節(jié)點是分配了不同的slot槽位,而請求的key在hash及crc16計算后可能存在不同的節(jié)點上,所以直接使用會報錯。可以根據(jù)redis集群的槽位分配請求,對批量數(shù)據(jù)進行先計算分配,然后再發(fā)起請求。

8、過期策略

定期清理:定期隨機抽取過期的key進行清理

惰性清理:被訪問時,如果發(fā)現(xiàn)已過期則清理,且不返回數(shù)據(jù)給調(diào)用方。

9、redis持久化

RDB模式:

原理:是redis會單獨創(chuàng)建(fork)一個與當前進程一模一樣的子進程來進行持久化,這個子線程的所有數(shù)據(jù)(變量。環(huán)境變量,程序程序計數(shù)器等)都和原進程一模一樣,會先將數(shù)據(jù)寫入到一個臨時文件中,待持久化結(jié)束了,再用這個臨時文件替換上次持久化好的文件,整個過程中,主進程不進行任何的io操作,這就確保了極高的性能

觸發(fā)機制:shutdown時,如果沒有開啟aof,會觸發(fā)配置文件中默認的快照配置;執(zhí)行命令save或者bgsave save是只管保存,其他不管,全部阻塞 bgsave: redis會在后臺異步進行快照操作,同時可以響應(yīng)客戶端的請求。

AOF

原理:將Reids的操作日志以追加的方式寫入文件,讀操作是不記錄的(配置文件中appendonly默認不開啟)

優(yōu)勢:優(yōu)化數(shù)據(jù)丟失問題,rdb會丟失最后一次快照后的數(shù)據(jù),aof丟失不會超過2秒的數(shù)據(jù)

觸發(fā)機制:

no:表示等操作系統(tǒng)進行數(shù)據(jù)緩存同步到磁盤(快,持久化沒保證) ? always:同步持久化,每次發(fā)生數(shù)據(jù)變更時,立即記錄到磁盤(慢,安全) ? everysec:表示每秒同步一次(默認值,很快,但可能會丟失一秒以內(nèi)的數(shù)據(jù))

auto-aof-rewrite-percentage 100 當AOF文件增長到一定大小的時候Redis能夠調(diào)用 bgrewriteaof對日志文件進行重寫 。當AOF文件大小的增長率大于該配置項時自動開啟重寫(這里指超過原大小的100%)

auto-aof-rewrite-min-size 64mb:當AOF文件增長到一定大小的時候Redis能夠調(diào)用 bgrewriteaof對日志文件進行重寫 。當AOF文件大小大于該配置項時自動開啟重寫

混合持久化:4.0版本默認關(guān)閉,5.0 版本默認開啟。通過aof-use-rdb-preamble配置參數(shù)控制,yes則表示開啟,no表示禁用;注意:同時開啟aof跟rdb,aof優(yōu)先(數(shù)據(jù)更加全面)

9、同步機制

第一次同步時,主節(jié)點做一次bgsave,并同時將后續(xù)修改操作記錄到內(nèi)存buffer,待完成后將RDB文件全量同步到復(fù)制節(jié)點,復(fù)制節(jié)點接受完成后將RDB鏡像加載到內(nèi)存。加載完成后,再通知主節(jié)點將期間修改的操作記錄同步到復(fù)制節(jié)點進行重放就完成了同步過程。后續(xù)的增量數(shù)據(jù)通過AOF日志同步即可,有點類似數(shù)據(jù)庫的binlog

10、集群方案

1、主從模式

2.6版本之后,slave默認只讀(缺點:主機掛掉后不能更新數(shù)據(jù))

2、哨兵模式(高可用)

在master掛掉時,將slave提升為master。中間會有幾秒鐘的不可用狀態(tài),因為在進行選舉。

哨兵原理:

主觀下線:在心跳檢測的定時任務(wù)中,如果其他節(jié)點超過一定時間沒有回復(fù),小兵節(jié)點就會將其進行主管下線

客觀下線:哨兵節(jié)點在對主節(jié)點進行主管下線后,會聽過sentinel is-master-down-by-addr命令詢問其他哨兵節(jié)點該主節(jié)點的狀態(tài);如果判斷主節(jié)點下線的數(shù)量達到一定數(shù)值,則對該主節(jié)點進行客觀下線

哨兵定時任務(wù):

每10秒通過想主從節(jié)點發(fā)送info命令獲取最新的主從結(jié)構(gòu);發(fā)現(xiàn)slave節(jié)點,確定主從關(guān)系

每2秒通過發(fā)布訂閱功能獲取其他哨兵節(jié)點的信息

沒秒通過向其他節(jié)點發(fā)送平命令進行心跳檢測,判斷是否下線

哨兵選舉:raft算法(基本思路是先到先得,一般情況誰先完成客觀下線誰就會成為領(lǐng)導(dǎo)者)

新節(jié)點選舉:

1、過濾掉不健康的從節(jié)點

2、選擇優(yōu)先級最高的從節(jié)點(由replica-priority指定);如果優(yōu)先級無法區(qū)分 3、選擇復(fù)制偏移量最大的從節(jié)點;如果仍無法區(qū)分 4、選擇runid最小的從節(jié)點

建議:哨兵節(jié)點大于一個(應(yīng)該是奇數(shù)),一方面增加哨兵節(jié)點的冗余,冰面哨兵本身成為高可用的瓶頸,另一方面減少對下線的誤判,同時也應(yīng)該部署在不同的物理機上

3、集群模式(高擴展)

手動搭建步驟:配置文件開啟集群配置;meet個節(jié)點;設(shè)置slot槽;設(shè)置主從;

腳本執(zhí)行:

5.0之前需要安裝環(huán)境并執(zhí)行redis-trib.rb;

5.0之后可用下面命令執(zhí)行:

/usr/local/bin/redis-cli --cluster create 192.168.0.104:7000 192.168.0.104:7001 192.168.0.104:7002 192.168.0.104:7003 192.168.0.104:7004 192.168.0.104:7005 --cluster-replicas 1

原創(chuàng)不易、轉(zhuǎn)載請注明來源

集群的擴容與縮容,注意slot分配

總結(jié)

以上是生活随笔為你收集整理的redis 哨兵 异步_redis 使用历程的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。