CN110287206A - 构建用于Redis数据库的分布式锁的方法 - Google Patents
构建用于Redis数据库的分布式锁的方法 Download PDFInfo
- Publication number
- CN110287206A CN110287206A CN201910583604.6A CN201910583604A CN110287206A CN 110287206 A CN110287206 A CN 110287206A CN 201910583604 A CN201910583604 A CN 201910583604A CN 110287206 A CN110287206 A CN 110287206A
- Authority
- CN
- China
- Prior art keywords
- lock
- queue
- dead letter
- distributed
- distributed lock
- Prior art date
- Legal status (The legal status is an assumption and is not a legal conclusion. Google has not performed a legal analysis and makes no representation as to the accuracy of the status listed.)
- Granted
Links
Classifications
-
- G—PHYSICS
- G06—COMPUTING; CALCULATING OR COUNTING
- G06F—ELECTRIC DIGITAL DATA PROCESSING
- G06F16/00—Information retrieval; Database structures therefor; File system structures therefor
- G06F16/20—Information retrieval; Database structures therefor; File system structures therefor of structured data, e.g. relational data
- G06F16/23—Updating
- G06F16/2308—Concurrency control
- G06F16/2336—Pessimistic concurrency control approaches, e.g. locking or multiple versions without time stamps
- G06F16/2343—Locking methods, e.g. distributed locking or locking implementation details
Landscapes
- Engineering & Computer Science (AREA)
- Theoretical Computer Science (AREA)
- Data Mining & Analysis (AREA)
- Databases & Information Systems (AREA)
- Physics & Mathematics (AREA)
- General Engineering & Computer Science (AREA)
- General Physics & Mathematics (AREA)
- Information Retrieval, Db Structures And Fs Structures Therefor (AREA)
Abstract
本发明涉及构建用于Redis数据库的分布式锁的方法,包括:A.在RabbitMQ中创建死信交换机和直连交换机,以及创建死信队列和分布式锁队列,将死信队列和死信交换机绑定,分布式锁队列分别与死信交换机分别和直连交换机绑定;B.定义基于Redssion的用于获取分布式锁和释放分布式锁的工具类;C.定义死信队列的消费者类;D.调用工具类中的加锁方法,得到加锁是否成功的结果;E.加锁成功,则执行业务代码;加锁失败,退出执行业务代码;F.锁释放。本发明能够满足高并发场景中的性能诉求,并且解决了基于Redis数据库的锁失效时间机制,以及失效时间设置过长或过短导致锁提前释放等问题,实现了实现高可用性。
Description
技术领域
本发明涉及分布式系统中分布式锁的构建方法,具体讲是构建用于Redis数据库的分布式锁的方法。
背景技术
在分布式应用的场景下,有时需要保证一个资源在同一时间内只能被同一个操作方修改,因此就引入了分布式锁的概念和技术。为了实现分布式锁,目前比较常用的几种方式为:
1.基于数据库实现分布式锁:
步骤:
1)在数据库中创建一张锁表,用于记录每个线程对应持有的锁;
2)获取锁的时候,向锁表中增加一条记录;
3)释放锁的时候,删除这条记录;
缺点:
1)性能不能满足高并发场景的诉求;
2)为了提高可用性,解决单点问题,需要两台数据库,并互为主备,运维难度高;
3)为了实现阻塞锁,需要不断尝试直到成功,这种方式验证浪费服务资源;
4)为了实现可重入锁,需要记录机器信息、线程信息,操作繁琐复杂;
5)为了解决死锁,需要记录锁失效时间,做一个定时任务,每隔一定时间把数据库超时的数据清理掉,增量了工作量而且也不能做到即时释放锁资源;
2.基于zookeeper(一种分布式的、开放源码的分布式应用程序协调服务)实现分布式锁:
步骤:
1)在zookeeper对于指定节点的目录下,生成一个唯一的瞬时有序节点;
2)获取锁的时候,只需要判断有序节点中序号最小的一个;
3)释放锁的时候,将这个瞬时节点删除即可;
缺点:
1)性能较低,不能满足高并发场景的诉求;
3.基于Redis(一种开源的数据库)实现分布式锁:
步骤:
1)调用RedissonClient的tryLock方法来实现获取锁;
2)调用RedissonClient的unlock方法实现释放锁;
缺点:
1)基于Redis的失效时间(Time To Live)机制,在服务宕机的情况下,可以自动释放锁。但是失效时间设置多长不好确定,如果设置的时间太短,方法没执行完,锁就自动释放了,那么就会导致并发问题。如果设置的时间太长,其他需要获取锁的线程有可能需要多等一段时间。
发明内容
本发明提供了一种构建用于Redis数据库的分布式锁的方法,以降低死锁风险、解决锁提前释放等问题、提高并发性能、实现高可用性(High Availability)。
本发明构建用于Redis数据库的分布式锁的方法,包括:
A.在RabbitMQ中创建死信交换机和直连交换机,以及创建死信队列和分布式锁队列,将死信队列和死信交换机绑定,分布式锁队列分别与死信交换机分别和直连交换机绑定;
B.定义基于Redssion的用于获取分布式锁和释放分布式锁的工具类;Redisson是一个在Redis的基础上实现的Java驻内存数据网格,还提供了许多分布式服务;
C.定义死信队列的消费者类,该类用于获取死信队列中的消息,并决定是否重置锁失效时间;
D.在需要获取分布式锁的业务里调用工具类中的加锁方法,得到加锁是否成功的结果;
E.如果步骤D加锁成功,则执行业务代码,得到业务结果;如果加锁失败,退出执行业务代码;
F.得到业务结果后,调用工具类中的解锁方法用于释放锁,得到锁释放,整个业务流程完成。
RabbitMQ是一种实现了高级消息队列协议(AMQP)的开源消息代理软件,亦称面向消息的中间件。由于RabbitMQ中不存在延时队列,但是可以通过设置消息的过期时间和死信队列来实现延迟队列,由消费者监听死信交换机绑定的队列,而不需要监听消息发送的队列。
在RabbitMQ中可以对队列和消息分别设置TTL(消息存活时间),第一种方式是通过队列进行设置,该队列中所有的消息都存在相同的过期时间;第二种方式是通过对消息本身进行设置,使每条消息的过期时间都不一样。如果同时使用了这两种方式,则以过期时间小的那个数值为准。当消息达到过期时间还没有被消费,那么那个消息就成为了一个死信消息。
死信交换机(Dead Letter Exchange)与同普通的交换机基本相同,只是在某一个设置有死信交换机的队列中有消息过期了,会自动触发消息的转发,将消息发送到死信交换机中去。
因此,为了实现基于RabbitMQ的延迟队列,本发明建立了死信队列和分布式锁队列的两个队列,一个用于发送消息,一个用于消息过期后自动转发到目标队列,原理如图1所示。
进一步的,步骤A包括:
A1.在RabbitMQ中创建类型为direct的死信交换机;
A2.创建用于存放死信消息的死信队列,所述的死信交换机与死信队列通过对应的路由键进行绑定;
A3.创建类型为direct的直连交换机;
A4.创建用于存储分布式锁信息的分布式锁队列,并与死信队列通过对应的路由键进行绑定,所述的死信交换机会根据该路由键找到死信消息存放的死信队列;设置消息的存活时间。
进一步的,在步骤B所述的工具类中包含有四个方法,分别为:
tryLock方法:用于尝试获取分布式锁并发送分布式锁名称到分布式锁队列;
unlock方法:用于释放分布式锁;
isExists方法:用于判断分布式锁是否存在;
expire方法:用于重置锁失效时间。
具体的,在tryLock方法中包含四个参数:分布式锁名称、等待锁时间(等待获取锁的时间,如果超过指定的等待时间则认为获取锁失败)、锁失效时间(表示持有这把锁的最长时间,超过该时间后Redis会自动释放锁)和时间单位,调用该方法后如果返回结果为true表示加锁成功,返回结果为false表示加锁失败;
在unlock方法中包含分布式锁名称的参数;
在isExists方法中包含分布式锁名称的参数,该方法返回结果如果为true表示锁存在,如果为false表示锁不存在;
在expire方法有三个参数:分布式锁名称、锁失效时间和锁失效时间单位。
进一步的,步骤C所述的消费者类先获取死信队列中的消息,通过调用工具类中的方法判断锁是否释放,如没有被释放,向日志文件打印告警日志,然后再通过工具类进行重置锁失效时间,并将所述死信队列中的消息投递回分布锁队列,当该消息过期后会重新投递回死信队列进入步骤C,直到锁释放;如锁已释放不做任何处理。由此便解决了基于Redis数据库的锁失效时间机制,以及失效时间设置过长导致假象死锁问题和失效时间设置过短导致锁提前释放等问题。
本发明构建用于Redis数据库的分布式锁的方法能够满足高并发场景中的性能诉求,并且解决了基于Redis数据库的锁失效时间机制,以及失效时间设置过长导致假象死锁问题或失效时间设置过短导致锁提前释放等问题,同时还提供了锁释放超时告警机制,实现了实现高可用性。
以下结合实施例的具体实施方式,对本发明的上述内容再作进一步的详细说明。但不应将此理解为本发明上述主题的范围仅限于以下的实例。在不脱离本发明上述技术思想情况下,根据本领域普通技术知识和惯用手段做出的各种替换或变更,均应包括在本发明的范围内。
附图说明
图1为本发明中RabbitMQ延迟队列消息流转过程示意图。
图2为本发明构建用于Redis数据库的分布式锁的方法的流程图。
具体实施方式
如图2所示本发明构建用于Redis数据库的分布式锁的方法,包括:
A.创建延迟队列:
A1.在RabbitMQ中创建类型为direct的死信交换机;
A2.创建用于存放死信消息的死信队列,所述的死信交换机与死信队列通过对应的路由键进行绑定;
A3.创建类型为direct的直连交换机;
A4.创建用于存储分布式锁信息的分布式锁队列,并与死信队列通过对应的路由键进行绑定,所述的死信交换机会根据该路由键找到死信消息存放的死信队列;设置消息的存活时间为30秒。
B.定义基于Redssion的用于获取分布式锁和释放分布式锁的工具类。在所述的工具类中包含有四个方法,分别为:
tryLock方法:用于尝试获取分布式锁并发送分布式锁名称到分布式锁队列。该方法有四个参数,第一个参数是分布式锁名称,第二个参数是等待锁时间(等待获取锁时间,如果超过指定的等待时间认为获取锁失败),第三个参数是锁失效时间(表示持有这把锁的最长时间,超过该时间后Redis数据库会自动释放锁),第四个参数是时间单位,调用该方法如果返回结果为true表示加锁成功,如果返回结果为false表示加锁失败。
unlock方法:用于释放分布式锁。该方法只有一个参数,是分布式锁名称。
isExists方法:用于判断分布式锁是否存在。该方法只有一个参数,是分布式锁名称,该方法如果返回结果为true表示锁存在,返回结果为false表示锁不存在。
expire方法:用于重置锁失效时间。该方法有三个参数,第一个参数是分布式锁名称,第二个参数是锁失效时间,第三个参数是锁失效时间单位。
C.定义死信队列的消费者类,该类用于获取死信队列中的消息,并决定是否重置锁失效时间。消费者类中只有一个方法,该方法只有一个参数,就是分布式锁名称。该方法首先获取死信队列中的消息,通过调用步骤C所述工具类的isExists方法判断锁是否释放,如没有被释放,打印告警日志到日志文件,用于锁释放超时告警。然后调用工具类的expire方法重置锁失效时间,并将死信队列中的消息投递回分布锁队列,当该消息过期后会重新投递回死信队列进入步骤C,直到锁释放;如锁已释放则不做任何处理。由此就解决了基于Redis的锁失效时间机制,以及失效时间设置过长导致假象死锁问题和失效时间设置过短导致锁提前释放等问题。
D.在需要获取分布式锁的业务里调用工具类中的tryLock方法,得到加锁是否成功的结果,返回结果为true表示加锁成功,结果为false表示加锁失败。
E.如果步骤D加锁成功,则执行业务代码,得到业务结果;如果加锁失败,退出执行业务代码;
F.得到业务结果后,调用工具类中的unlock方法释放锁,得到锁释放,整个业务流程完成。
Claims (5)
1.构建用于Redis数据库的分布式锁的方法,其特征包括:
A.在RabbitMQ中创建死信交换机和直连交换机,以及创建死信队列和分布式锁队列,将死信队列和死信交换机绑定,分布式锁队列分别与死信交换机分别和直连交换机绑定;
B.定义基于Redssion的用于获取分布式锁和释放分布式锁的工具类;
C.定义死信队列的消费者类,该类用于获取死信队列中的消息,并决定是否重置锁失效时间;
D.在需要获取分布式锁的业务里调用工具类中的加锁方法,得到加锁是否成功的结果;
E.如果步骤D加锁成功,则执行业务代码,得到业务结果;如果加锁失败,退出执行业务代码;
F.得到业务结果后,调用工具类中的解锁方法用于释放锁,得到锁释放,整个业务流程完成。
2.如权利要求1所述的构建用于Redis数据库的分布式锁的方法,其特征为:步骤A包括:
A1.在RabbitMQ中创建类型为direct的死信交换机;
A2.创建用于存放死信消息的死信队列,所述的死信交换机与死信队列通过对应的路由键进行绑定;
A3.创建类型为direct的直连交换机;
A4.创建用于存储分布式锁信息的分布式锁队列,并与死信队列通过对应的路由键进行绑定;设置消息的存活时间。
3.如权利要求1所述的构建用于Redis数据库的分布式锁的方法,其特征为:在步骤B所述的工具类中包含有四个方法,分别为:
tryLock方法:用于尝试获取分布式锁并发送分布式锁名称到分布式锁队列;
unlock方法:用于释放分布式锁;
isExists方法:用于判断分布式锁是否存在;
expire方法:用于重置锁失效时间。
4.如权利要求3所述的构建用于Redis数据库的分布式锁的方法,其特征为:在tryLock方法中包含四个参数:分布式锁名称、等待锁时间、锁失效时间和时间单位,调用该方法后如果返回结果为true表示加锁成功,返回结果为false表示加锁失败;
在unlock方法中包含分布式锁名称的参数;
在isExists方法中包含分布式锁名称的参数,该方法返回结果如果为true表示锁存在,如果为false表示锁不存在;
在expire方法有三个参数:分布式锁名称、锁失效时间和锁失效时间单位。
5.如权利要求1所述的构建用于Redis数据库的分布式锁的方法,其特征为:步骤C所述的消费者类先获取死信队列中的消息,通过调用工具类中的方法判断锁是否释放,如没有被释放,向日志文件打印告警日志,然后再通过工具类进行重置锁失效时间,并将所述死信队列中的消息投递回分布锁队列,当该消息过期后会重新投递回死信队列进入步骤C,直到锁释放;如锁已释放不做任何处理。
Priority Applications (1)
Application Number | Priority Date | Filing Date | Title |
---|---|---|---|
CN201910583604.6A CN110287206B (zh) | 2019-07-01 | 2019-07-01 | 构建用于Redis数据库的分布式锁的方法 |
Applications Claiming Priority (1)
Application Number | Priority Date | Filing Date | Title |
---|---|---|---|
CN201910583604.6A CN110287206B (zh) | 2019-07-01 | 2019-07-01 | 构建用于Redis数据库的分布式锁的方法 |
Publications (2)
Publication Number | Publication Date |
---|---|
CN110287206A true CN110287206A (zh) | 2019-09-27 |
CN110287206B CN110287206B (zh) | 2021-04-27 |
Family
ID=68020333
Family Applications (1)
Application Number | Title | Priority Date | Filing Date |
---|---|---|---|
CN201910583604.6A Active CN110287206B (zh) | 2019-07-01 | 2019-07-01 | 构建用于Redis数据库的分布式锁的方法 |
Country Status (1)
Country | Link |
---|---|
CN (1) | CN110287206B (zh) |
Cited By (5)
Publication number | Priority date | Publication date | Assignee | Title |
---|---|---|---|---|
CN110856004A (zh) * | 2019-11-05 | 2020-02-28 | 北京字节跳动网络技术有限公司 | 消息处理方法、装置、可读存储介质及电子设备 |
CN110925935A (zh) * | 2019-10-24 | 2020-03-27 | 珠海格力电器股份有限公司 | 定时控制方法、装置、存储介质、计算机设备 |
CN111049730A (zh) * | 2019-12-05 | 2020-04-21 | 紫光云(南京)数字技术有限公司 | RabbitMQ消息重传及消费方幂等性解决方法 |
CN113542113A (zh) * | 2021-07-13 | 2021-10-22 | 浪潮云信息技术股份公司 | 一种基于RabbitMQ处理延迟任务的方法及工具 |
CN115866039A (zh) * | 2022-11-29 | 2023-03-28 | 北京达佳互联信息技术有限公司 | 消息处理方法、装置、电子设备及存储介质 |
Citations (6)
Publication number | Priority date | Publication date | Assignee | Title |
---|---|---|---|---|
CN102880475B (zh) * | 2012-10-23 | 2015-08-12 | 普元信息技术股份有限公司 | 计算机软件系统中基于云计算的实时事件处理系统及方法 |
CN106126673A (zh) * | 2016-06-29 | 2016-11-16 | 上海浦东发展银行股份有限公司信用卡中心 | 一种基于Redis和HBase的分锁方法 |
CN106354565A (zh) * | 2016-09-21 | 2017-01-25 | 努比亚技术有限公司 | 一种分布式锁客户端及控制方法 |
US20170185678A1 (en) * | 2015-12-28 | 2017-06-29 | Le Holdings (Beijing) Co., Ltd. | Crawler system and method |
CN107180040A (zh) * | 2016-03-09 | 2017-09-19 | 广州市动景计算机科技有限公司 | 一种业务数据的管理方法及装置 |
CN109558218A (zh) * | 2018-12-04 | 2019-04-02 | 山东浪潮通软信息科技有限公司 | 一种基于Redis的分布式业务数据锁实现方法 |
-
2019
- 2019-07-01 CN CN201910583604.6A patent/CN110287206B/zh active Active
Patent Citations (6)
Publication number | Priority date | Publication date | Assignee | Title |
---|---|---|---|---|
CN102880475B (zh) * | 2012-10-23 | 2015-08-12 | 普元信息技术股份有限公司 | 计算机软件系统中基于云计算的实时事件处理系统及方法 |
US20170185678A1 (en) * | 2015-12-28 | 2017-06-29 | Le Holdings (Beijing) Co., Ltd. | Crawler system and method |
CN107180040A (zh) * | 2016-03-09 | 2017-09-19 | 广州市动景计算机科技有限公司 | 一种业务数据的管理方法及装置 |
CN106126673A (zh) * | 2016-06-29 | 2016-11-16 | 上海浦东发展银行股份有限公司信用卡中心 | 一种基于Redis和HBase的分锁方法 |
CN106354565A (zh) * | 2016-09-21 | 2017-01-25 | 努比亚技术有限公司 | 一种分布式锁客户端及控制方法 |
CN109558218A (zh) * | 2018-12-04 | 2019-04-02 | 山东浪潮通软信息科技有限公司 | 一种基于Redis的分布式业务数据锁实现方法 |
Non-Patent Citations (1)
Title |
---|
无: ""https://www.cnblogs.com/leigepython/p/11022479.html"", 《博客园》 * |
Cited By (6)
Publication number | Priority date | Publication date | Assignee | Title |
---|---|---|---|---|
CN110925935A (zh) * | 2019-10-24 | 2020-03-27 | 珠海格力电器股份有限公司 | 定时控制方法、装置、存储介质、计算机设备 |
CN110856004A (zh) * | 2019-11-05 | 2020-02-28 | 北京字节跳动网络技术有限公司 | 消息处理方法、装置、可读存储介质及电子设备 |
CN110856004B (zh) * | 2019-11-05 | 2022-02-01 | 北京字节跳动网络技术有限公司 | 消息处理方法、装置、可读存储介质及电子设备 |
CN111049730A (zh) * | 2019-12-05 | 2020-04-21 | 紫光云(南京)数字技术有限公司 | RabbitMQ消息重传及消费方幂等性解决方法 |
CN113542113A (zh) * | 2021-07-13 | 2021-10-22 | 浪潮云信息技术股份公司 | 一种基于RabbitMQ处理延迟任务的方法及工具 |
CN115866039A (zh) * | 2022-11-29 | 2023-03-28 | 北京达佳互联信息技术有限公司 | 消息处理方法、装置、电子设备及存储介质 |
Also Published As
Publication number | Publication date |
---|---|
CN110287206B (zh) | 2021-04-27 |
Similar Documents
Publication | Publication Date | Title |
---|---|---|
CN110287206A (zh) | 构建用于Redis数据库的分布式锁的方法 | |
CN111782360B (zh) | 分布式任务调度方法及装置 | |
EP2254286B1 (en) | Network real time monitoring and control method, system and computer program product | |
US8191071B2 (en) | Method for supervising task-based data processing | |
CN102088363B (zh) | 告警处理方法和系统 | |
CN103229535B (zh) | 电信网络中用于单元恢复的方法和系统 | |
CA2701240C (en) | Control management of voice-over-ip parameters | |
CN106850740A (zh) | 一种高吞吐数据流处理方法 | |
CN109445944A (zh) | 一种基于dpdk的网络数据采集处理系统及其方法 | |
CN106161076A (zh) | 虚拟网络功能扩展方法和装置 | |
LU503247B1 (en) | Distributed task scheduling gateway scheduling method based on rate limiting | |
CN111092778A (zh) | 基于有限时序数据队列实现api实时预警的系统及方法 | |
CN100525211C (zh) | 一种在网元管理系统中实现集中调度的系统 | |
JPH03503832A (ja) | バスシステムとして構成された局域通信用のチャネルアクセス方法 | |
CN116760655B (zh) | Sd-wan应用中提供cpe最优接入的pop点方法 | |
CN112667409A (zh) | 一种可重入的分布式排它锁实现方法 | |
CN108255515B (zh) | 一种实现定时器服务的方法和装置 | |
CN111352746A (zh) | 消息限流方法、存储介质 | |
KR100599929B1 (ko) | 지능형통합보안관리시스템의 에이전트계층 데이터처리방법 | |
US20030172195A1 (en) | Method and system for guaranteeing sequential consistency in distributed computations | |
CA2331899C (en) | Method and communications system for processing state information in a management network having a number of management levels | |
JP3145992B2 (ja) | 交換制御サービス論理の競合制御方式及び競合制御方法 | |
WO1997000479A1 (en) | A method for determining the contents of a restoration log | |
CN108846633A (zh) | 一种智能高效的卡任务处理方法 | |
CN113660178A (zh) | 一种cdn内容管理系统 |
Legal Events
Date | Code | Title | Description |
---|---|---|---|
PB01 | Publication | ||
PB01 | Publication | ||
SE01 | Entry into force of request for substantive examination | ||
SE01 | Entry into force of request for substantive examination | ||
GR01 | Patent grant | ||
GR01 | Patent grant |