最近最火的词是什么?那大概就是微服务(Microservice)了。最近也火的一踏糊涂的Docker、AppOps也都是围绕着微服务领域的。在微服务领域还有很多相关名词。这些名词有一个共同的特点那就是晦涩难懂。他们就像中国古代的道、气、八卦等词一样,一解释就懂,一问就不知,一讨论就打架。
单机应用架构中,秒杀案例使用ReentrantLcok或者synchronized来达到秒杀商品互斥的目的。然而在分布式系统中,会存在多台机器并行去实现同一个功能。也就是说,在多进程中,如果还使用以上JDK提供的进程锁,来并发访问数据库资源就可能会出现商品超卖的情况。因此,需要我们来实现自己的分布式锁。
实现一个分布式锁应该具备的特性:
高可用、高性能的获取锁与释放锁
在分布式系统环境下,一个方法或者变量同一时间只能被一个线程操作
具备锁失效机制,网络中断或宕机无法释放锁时,锁必须被删除,防止死锁
具备阻塞锁特性,即没有获取到锁,则继续等待获取锁
具备非阻塞锁特性,即没有获取到锁,则直接返回获取锁失败
具备可重入特性,一个线程中可以多次获取同一把锁,比如一个线程在执行一个带锁的方法,该方法中又调用了另一个需要相同锁的方法,java开发之道 则该线程可以直接执行调用的方法,而无需重新获得锁
在之前的秒杀案例中,我们曾介绍过关于分布式锁几种实现方式:
基于数据库实现分布式锁
基于 Redis 实现分布式锁
基于 Zookeeper 实现分布式锁
前两种对于分布式生产环境来说并不是特别推荐,高并发下数据库锁性能太差,Redis在锁时间限制和缓存一致性存在一定问题。这里我们重点介绍一下 Zookeeper 如何实现分布式锁。实现原理