当前位置:网站首页>How to ensure data consistency between MySQL and redis?
How to ensure data consistency between MySQL and redis?
2022-07-06 13:02:00 【Java misty rain】
Let me just throw the conclusion first : Under the condition of real-time , There is no plan to keep the two completely consistent , Only the final consistency scheme . According to many online solutions , Sum up 6 Kind of , Look directly at the catalog :
Bad plan
1. First write MySQL, To write Redis
Illustration :
This is a sequence diagram , Base note describing the sequence of requests ;
The orange line is a request A, The black line is a request B;
Orange text , yes MySQL and Redis Final inconsistent data ;
Data is from 10 Updated to 11;
All the pictures in the back , That's what it means , I won't repeat .
request A、B They all write first MySQL, And then write Redis, In high concurrency , If you ask for A Writing Redis I was stuck for a while , request B The data update has been completed in turn , There will be problems in the figure .
The picture has been drawn very clearly , I don't have to be wordy anymore , But here's a premise , Is for read requests , Read first Redis, without , Read it again DB, But the read request will not be written back Redis. In plain English , That is, the read request will not be updated Redis.
2. First write Redis, To write MySQL
Same as “ First write MySQL, To write Redis”, Look at the picture and you can understand .
3. Delete first Redis, To write MySQL
This picture is somewhat different from the above , The previous request A and B All update requests , Here's the request A It's an update request , But request B It's a read request , And ask B Your read request will be written back Redis.
request A So let's delete the cache , Maybe because of Caton , The data has not been updated to MySQL, The two data are inconsistent .
The probability of this situation is relatively high , Because request A to update MySQL It may take a long time , The request B The first two steps are both query , It will be very fast .
Good plan
4. Delete first Redis, To write MySQL, And then delete Redis
about “ Delete first Redis, To write MySQL”, If the final inconsistency is to be solved , In fact, no more Redis Just delete it again , This is also what people often say “ Cache double deletion ”.
In order to make it easy for everyone to see the picture , For blue text ,“ Delete cache 10” Must be in “ Write back cache 10” Back , How can we guarantee that it must be in the back ? The first scheme given online is , Make a request A Last deletion of , wait for 500ms.
For this scenario , Just look at it , I can't use it anyway , too Low 了 , The risk is not controllable .
Is there a better plan , I recommend asynchronous serialization deletion , That is, delete the request into the queue
Asynchronous deletion has no effect on online business , Serialization ensures correct deletion in concurrent situations .
What if double deletion fails , Online Redis Add a scheme of cache expiration time , I can't agree with this . I suggest the whole retry mechanism , The retry mechanism of message queue can be used , You can also the whole table by yourself , Record the number of retries , There are many ways .
A brief summary :
“ Cache double deletion ” Don't use mindless sleep 500 ms;
Asynchrony through message queuing & Serial , Achieve the last cache deletion ;
Cache delete failed , Add retry mechanism .
5. First write MySQL, And then delete Redis
For the above situation , For the first query , request B The data queried is 10, however MySQL The data of 11, There is only one inconsistency , For businesses that do not require strong consistency , Can tolerate .( Under what circumstances can it not be tolerated , For example, second kill business 、 Inventory service, etc .)
When requested B When making the second query , Because I missed Redis, Will check again DB, Then write back Reids.
Under what circumstances will there be inconsistencies ? Brother Su is writing 《 How to ensure the consistency of double write between database and cache ?》 It was explained .
Here we need to meet 2 Conditions :
The cache just expires automatically ;
request B From the database 10, Write back cache time consuming , Than request A Write database , And the time to delete the cache is still long .
For the second condition , We all know that updates DB It must take longer than query , So the probability of this happening is very small , It is less likely that the above conditions are met at the same time .
6. First write MySQL, adopt Binlog, Asynchronous update Redis
This program , Mainly monitoring MySQL Of Binlog, And then asynchronously , Update data to Redis, This scheme has a premise , Request for inquiry , Will not write back Redis.
This scheme , To ensure that MySQL and Redis The ultimate consistency of , But if you ask halfway B Need to query data , If there is no data in the cache , Just check it directly DB; If there is data in the cache , The data queried will also be inconsistent .
So this program , Is the ultimate solution to achieve ultimate consistency , But there is no guarantee of real-time .
Several schemes are compared
Let's compare the above discussion 6 Kind of plan :
First write Redis, To write MySQL
This program , I'm sure I won't use , In case DB Hang up , You write data to the cache ,DB No data , This is catastrophic ;
I've seen my classmates use it like this before , If write DB Failure , Yes Redis Reverse operation , What if the reverse operation fails , Do you want to try again ?
First write MySQL, To write Redis
For concurrency 、 Projects with low consistency requirements , That's how many people use it , I used to do this a lot , But it's not recommended ;
When Redis Instant unavailability , Need to call the police , Then deal with it offline .
Delete first Redis, To write MySQL
This way, , I haven't used it yet , Just ignore .
Delete first Redis, To write MySQL, And then delete Redis
It's possible , however It's complicated , We also need to build a message queue to delete asynchronously Redis.
First write MySQL, And then delete Redis
It's recommended , Delete Redis If you fail , You can try again a few more times , Or call the police ;
This scheme , It is the best solution in real-time , In some high concurrency scenarios , Recommend this .
First write MySQL, adopt Binlog, Asynchronous update Redis
For remote disaster recovery 、 Data aggregation, etc , It is suggested that this way , such as binlog + kafka, The consistency of data can also reach the second level ;
Pure high concurrency scenario , This scheme is not recommended , For example, rush to buy 、 Second kill, etc .
Personal conclusion :
Real time consistency scheme : use “ First write MySQL, And then delete Redis” The strategy of , Although there will be inconsistencies between the two , But the conditions to be met are a little harsh , So it is under the condition of real-time , The optimal solution that can satisfy the consistency as much as possible .
The final consistency plan : use “ First write MySQL, adopt Binlog, Asynchronous update Redis”, Can pass Binlog, Asynchronous update with message queue Redis, Is the optimal solution of the final consistency .
It is better to believe in books than to have no books , Because of limited personal ability , There are inevitably omissions and mistakes , If found bug Or better advice , Welcome criticism and correction , Thank you very much .
If this article helps you , Don't forget to give me a 3 even , give the thumbs-up , forward , Comment on ,
I'll see you next time ! How to get answers : Liked Commented Closed ~
Learn more knowledge and skills , Follow up with private bloggers (03)
边栏推荐
- KF UD分解之伪代码实现进阶篇【2】
- 抗差估计在rtklib的pntpos函数(标准单点定位spp)中的c代码实现
- 2022 National Games RE1 baby_ tree
- 错误: 找不到符号
- 基于rtklib源码进行片上移植的思路分享
- Comparative analysis of the execution efficiency of MySQL 5.7 statistical table records
- Record: the solution of MySQL denial of access when CMD starts for the first time
- 阿里云一面:并发场景下的底层细节 - 伪共享问题
- 3月15号 Go 1.18 正式版发布 了解最新特色以及使用方法
- Fairygui loop list
猜你喜欢
Unity3D基础入门之粒子系统(属性介绍+火焰粒子系统案例制作)
The earth revolves around the sun
121道分布式面试题和答案
[algorithme] swordfinger offer2 golang question d'entrevue 2: addition binaire
Combination of fairygui check box and progress bar
[algorithm] sword finger offer2 golang interview question 4: numbers that appear only once
The port is occupied because the service is not shut down normally
MySQL 三万字精华总结 + 面试100 问,吊打面试官绰绰有余(收藏系列
Fairygui joystick
[算法] 剑指offer2 golang 面试题2:二进制加法
随机推荐
What are the functions and features of helm or terrain
Sharing ideas of on-chip transplantation based on rtklib source code
[算法] 剑指offer2 golang 面试题10:和为k的子数组
错误: 找不到符号
微信小程序开发心得
MySQL performance tuning - dirty page refresh
【GNSS】抗差估计(稳健估计)原理及程序实现
使用rtknavi进行RT-PPP测试
The service robots that have been hyped by capital and the Winter Olympics are not just a flash in the pan
[算法] 剑指offer2 golang 面试题12:左右两边子数组的和相等
isEmpty 和 isBlank 的用法区别
Record: the solution of MySQL denial of access when CMD starts for the first time
【干货】提升RTK模糊度固定率的建议之周跳探测
记录:newInstance()过时的代替方法
雇佣收银员【差分约束】
Matlab读取GNSS 观测值o文件代码示例
rtklib单点定位spp使用抗差估计遇到的问题及解决
Pride-pppar source code analysis
染色法判定二分图
[untitled]