
课程咨询: 400-996-5531 / 投诉建议: 400-111-8989
认真做教育 专心促就业
随着互联网的不断发展,越来越多的人都在学习计算机编程开发相关的技术知识,而本文我们就通过案例分析来简单了解一下,分布式锁的概念与应用分析。
分布式锁,是一种跨进程的跨机器节点的互斥锁,它可以用来保证多机器节点对于共享资源访问的排他性。
我觉得分布式锁和线程锁本质上是一样的,线程锁的生命周期是单进程多线程,分布式锁的声明周期是多进程多机器节点。
在本质上,他们都需要满足锁的几个重要特性:
排他性,也就是说,同一时刻只能有一个节点去访问共享资源。
可重入性,允许一个已经获得锁的进程,在没有释放锁之前再次重新获得锁。
锁的获取、释放的方法
锁的失效机制,避免死锁的问题
所以,我认为,只要能够满足这些特性的技术组件都能够实现分布式锁。
关系型数据库,可以使用约束来实现锁的排他性,
如果要针对某个方法加锁,就可以创建一个表包含方法名称字段,
并且把方法名设置成的约束。
那抢占锁的逻辑就是:往表里面插入一条数据,如果已经有其他的线程获得了某个方法的锁,那这个时候插入数据会失败,从而保证了互斥性。
这种方式虽然简单啊,但是要实现比较完整的分布式锁,还需要考虑重入性、锁失效机制、没抢占到锁的线程要实现阻塞等,就会比较麻烦。
Redis,它里面提供了SETNX命令可以实现锁的排他性,当key不存在就返回1,存在就返回0。然后还可以用expire命令设置锁的失效时间,从而避免死锁问题。
当然有可能存在锁过期了,但是业务逻辑还没执行完的情况。所以这种情况,可以写一个定时任务对指定的key进行续期。
Redisson这个开源组件,就提供了分布式锁的封装实现,并且也内置了一个WatchDog机制来对key做续期。
我认为Redis里面这种分布式锁设计已经能够解决99%的问题了,当然如果在Redis搭建了高可用集群的情况下出现主从切换导致key失效,这个问题也有可能造成
多个线程抢占到同一个锁资源的情况,所以Redis官方也提供了一个RedLock的解决办法,但是实现会相对复杂一些。
在我看来,分布式锁应该是一个CP模型,而Redis是一个AP模型,所以在集群架构下由于数据的一致性问题导致极端情况下出现多个线程抢占到锁的情况很难避免。
那么基于CP模型又能实现分布式锁特性的组件,我认为可以选择Zookeeper或者etcd,
在数据一致性方面,zookeeper用到了zab协议来保证数据的一致性,etcd用到了raft算法来保证数据一致性。
在锁的互斥方面,zookeeper可以基于有序节点再结合Watch机制实现互斥和唤醒,etcd可以基于Prefix机制和Watch实现互斥和唤醒。
【免责声明】本文系本网编辑部分转载,转载目的在于传递更多信息,并不代表本网赞同其观点和对其真实性负责。如涉及作品内容、版权和其它问题,请在30日内与管理员联系,我们会予以更改或删除相关文章,以保证您的权益!更多内容请加danei0707学习了解。欢迎关注“达内在线”参与分销,赚更多好礼。