1.引入jar包
<dependency>
<groupId>org.apache.curator</groupId>
<artifactId>curator-recipes</artifactId>
<version>${curator.version}</version>
</dependency>
1.1:jar包对应的版本
<curator.version>2.5.0</curator.version>
2.新建一个工具类:zkClient
类名上需要加@Component注解
@Component
public class ZkClient
2.声明一个连接工厂
@Bean
public CuratorFramework getZkClient(){
CuratorFrameworkFactory.Builder builder= CuratorFrameworkFactory.builder()
.connectString(parameters.getZkHost())//从配置文件中取得配置 也就是zookeeper的地址
.connectionTimeoutMs(3000)//3000毫秒超时时间
.retryPolicy(new RetryNTimes(5, 10));//超时后重试五次,每10毫秒一次
CuratorFramework framework = builder.build();
framework.start();
return framework;
}
3.使用
1.注入刚才工具类声明的bean
@Autowired
private CuratorFramework curatorFramework;
2.获取lock
InterProcessLock lock = null;
lock = new
InterProcessMutex(curatorFramework,Constants.USER_REGISTER_DISTRIBUTE_LOCK_PATH);
这里的Constants.***是自定义好的一串字符串,作为锁的名称。
3.设置锁的超时时间,单位是毫秒,并获取锁
lock.acquire(3000,TimeUnit.MILLISECONDS);
这里会有一个返回值,true是获取到了锁,false则是失败
4.关闭锁,必须关闭锁 ,否则一旦出现bug,该锁用到的功能将彻底锁死
lock.release();
千万要放到finally中!!!
4.示例:放个示例吧,毕竟没有demo很难理解。
@Autowired
private CuratorFramework zkClient;
//这个是Constants工具类里面的常量
public static final String USER_REGISTER_DISTRIBUTE_LOCK_PATH = "/user_reg";
public void lock() throws Exception {
InterProcessLock lock = null;
try {
//设置锁
lock = new InterProcessMutex(curatorFramework,Constants.USER_REGISTER_DISTRIBUTE_LOCK_PATH);
int rest = 0;
boolean retry = true;
do{
//设置锁超时时间 3000 单位毫秒
if(lock.acquire(3000,TimeUnit.MILLISECONDS)){
/** 这里写具体业务代码 注册 之类的
*/
retry = false;
}
rest++;
}while (rest > 3 || retry);
//这个循环的意思是获取不到锁的情况下重试三次,获取到直接走下一步
}catch (Exception e){
log.error("异常",e);
throw e;
}finally {
try {
lock.release();
log.info(Thread.currentThread().getName()+":释放锁");
} catch (Exception e) {
e.printStackTrace();
}
}
}
5.闲谈
zookeeper通常用做Dubbo的注册中心
但它的功能远远不止于此,当然作为分布式锁性能比不上redis实现
但redis也有自己的缺点,多知道一点技术,总比少知道好