redis分布式鎖死鎖處理方案 Redis分布式鎖的原理是什么?如何續(xù)期?
Redis分布式鎖的原理是什么?如何續(xù)期?分布式鎖的需求伴隨著應(yīng)用的分布式部署。在單個應(yīng)用程序只部署一臺服務(wù)器的情況下,可以通過Java同步鎖來實(shí)現(xiàn)。同步鎖是一種原子操作。當(dāng)應(yīng)用程序以分布式方式部署并
Redis分布式鎖的原理是什么?如何續(xù)期?
分布式鎖的需求伴隨著應(yīng)用的分布式部署。在單個應(yīng)用程序只部署一臺服務(wù)器的情況下,可以通過Java同步鎖來實(shí)現(xiàn)。同步鎖是一種原子操作。
當(dāng)應(yīng)用程序以分布式方式部署并且具有多個服務(wù)時,應(yīng)用服務(wù)器將無法提供原子操作。Redis具有高性能,而且是單線程的,因此它可以為原子操作提供一個場所。有了它,就可以實(shí)現(xiàn)分布式鎖。
有些“上古”程序員一直堅持反對使用redis怎么辦?
分享大人物的答案似乎合情合理。
不要告訴我們是否使用redis。你必須告訴我們你為什么要使用redis。沒有redis的業(yè)務(wù)怎么了?世界上沒有免費(fèi)的午餐。如果不直接使用頭部緩存/NoSQL,可能會帶來越來越嚴(yán)重的問題。
單個數(shù)據(jù)庫的最大優(yōu)點(diǎn)是易于實(shí)現(xiàn)事務(wù),并由數(shù)據(jù)庫本身保證。舉個簡單的例子,要下訂單,需要扣除庫存并插入訂單條目。如果inventory和order都是數(shù)據(jù)庫表條目,那么這個事務(wù)是無可挑剔的。如果庫存在redis中,訂單條目是mysql,通常需要先寫redis,成功后再寫數(shù)據(jù)庫。如果您寫數(shù)據(jù)庫失敗,需要回滾redis,如果由于網(wǎng)絡(luò)或其他原因回滾失敗,將再扣減一個存貨。不要認(rèn)為這些事情很容易解決。事務(wù)處理的復(fù)雜性遠(yuǎn)遠(yuǎn)超出您的想象。例如,當(dāng)您編寫mysql時,您在提交時就失去了連接。你無法判斷提交是成功還是失敗。你的redis是不是在倒退?
因此,當(dāng)您引入一個新層時,您必須弄清楚您必須使用cache/NoSQL的目的以及您可以接受的一致性模型。否則,你就要出丑了。
怎么實(shí)現(xiàn)redis的讀鎖?
避免落入setnx(set if not exists)陷阱的最好方法是永遠(yuǎn)不要使用它:
setnx lock“l(fā)ock”
expire lock 100
del lock
場景:查詢數(shù)據(jù)庫的接口有大量調(diào)用,因此添加了緩存,問題是當(dāng)并發(fā)量大的時候,如果沒有鎖機(jī)制,大量的并發(fā)請求會在緩存過期的時候穿透緩存,直接查詢數(shù)據(jù)庫,造成雪崩效應(yīng),如果有鎖機(jī)制,只能處理一個請求控制以更新緩存。其他請求根據(jù)情況等待或使用過期的緩存。
$key=“cache update Lock”//Lock
$random=MD5(uniqid(getmypid())?!啊?mturand().“”,true))//隨機(jī)值
$TTL=10//NX不存在,ex為過期時間,TTL為生存時間,單位為秒
if($redis->set($key,$random,[“NX”,“ex”=>$TTL]){
$cache->update()//鎖定后執(zhí)行業(yè)務(wù)邏輯,這里是update cache
//添加隨機(jī)值判斷避免刪除其他操作的鎖
如果($redis->get($key)==$random){
$redis->del($key)}