众所周知,多个服务间的调用,产生多个JVM问题,当我们使用传统的锁的时候就会出现问题,因为跨JVM中无法可见到同一把锁,这个时候分布式锁就应运而生,例如就出现了Redis分布式锁,基于setnx的方式去实现,当然我们也可以通过zookeeper去实现分布式锁,通过创建子节点从而实现分布式锁。
一、代码实现如下:
package top.chenxiky.module.zookeeper;
import lombok.extern.slf4j.Slf4j;
import org.apache.curator.framework.CuratorFramework;
import org.apache.curator.framework.CuratorFrameworkFactory;
import org.apache.curator.framework.recipes.locks.InterProcessMutex;
import org.apache.curator.retry.RetryNTimes;
import org.springframework.stereotype.Service;
import java.util.concurrent.TimeUnit;
/**
* <p>zookeeper分布式锁</p>
*
* @author chenxiky
* @version 1.0.0
* @since 2023/04/13/23:12
*/
@Slf4j
@Service
public class ZookeeperLock implements Runnable{
/** zookeeper的地址 */
private static final String ZK_ADDRESS = "xxx.xxx.xxx.xxx:2181";
/**zkLock目录下创建临时节点 */
private static final String ZK_LOCK_PATH = "/zkLock";
static CuratorFramework client = null;
/**静态代码块实例化链接*/
static {
client = CuratorFrameworkFactory.newClient(ZK_ADDRESS,
new RetryNTimes(10, 10000));
client.start();
}
/**
* 分布式锁
*/
private static void zookeeperLock() {
InterProcessMutex lock = new InterProcessMutex(client,ZK_LOCK_PATH);
try {
if (lock.acquire(5*1000, TimeUnit.SECONDS)) {
// TODO 执行业务逻辑
Thread.sleep(5000);
log.info("当前线程名称={}",Thread.currentThread().getName());
}
} catch (Exception e) {
log.error("业务处理出现异常",e);
} finally {
try {
lock.release();
} catch (Exception e) {
log.error("锁释放出现异常",e);
}
}
}
/**
* 函数启动入口
*/
public static void main(String[] args) {
// 创建二个线程模拟分布式锁
new Thread(new ZookeeperLock()).start();
new Thread(new ZookeeperLock()).start();
}
@Override
public void run() {
zookeeperLock();
}
/**
* 依赖坐标
* <dependency>
* <groupId>org.apache.curator</groupId>
* <artifactId>curator-recipes</artifactId>
* <version>2.12.0</version>
* </dependency>
*/
}