zookeeper搭分布式搭成了单节点

zookeeper搭分布式搭成了单节点,有没有清楚是哪里搭错了的。

不知道你这个问题是否已经解决, 如果还没有解决的话:
  • 这个问题的回答你可以参考下: https://ask.csdn.net/questions/7463109
  • 这篇博客也不错, 你可以看下分布式架构下实现分布式锁使用数据库方案、 Zookeeper分布式锁、Redis分布式锁
  • 除此之外, 这篇博客: Zookeeper分布式锁,小小节点真奇妙中的 4.2 zookeeper是如何基于节点去实现各种分布式锁的? 部分也许能够解决你的问题, 你可以仔细阅读以下内容或者直接跳转源博客中阅读:

    总问题:zookeeper是如何基于节点去实现各种分布式锁的?
    问题1:节点,zookeeper如何实现分布式锁?
    回答1:和lock一样的,在子节点逻辑之前创建节点,在finally块中释放节点,两行代码实现分布式锁
    解释1:
    (1)在zookeeper中,节点名为唯一的,给定节点名创建一个后就不能再创建一个,会报错,创建指定节点名的节点,类似于获得到了锁;
    (2)与lock不同的是,lock是一个进程内,对所有线程可见,而节点名是对 分布式部署 中所有的节点可见;
    (3)正常情况下,会执行finally的语句,即表示节点执行完逻辑后,正常释放节点。

    问题1.1 :zookeeper如何实现分布式锁的互斥?
    回答1.1 :zk节点有个唯一的特性,就是我们创建过这个节点了,你再创建zk是会报错的,那我们就利用一下他的唯一性去实现一下。我们全部去创建,创建成功的第一个返回true他就可以继续下面的扣减库存操作,后续的节点访问就会全部报错,扣减失败,我们把它们丢一个队列去排队。
    问题1.2 :zookeeper实现的分布式锁,客户端如何释放锁?
    回答1.2 :删除节点,Lock在finally里面unLock,现在我们在finally删除节点,删了再通知其他的客户端来争夺锁。
    问题1.3 :怎么通知其他的客户端来争夺锁?
    回答1.3 :监听节点的删除事件,知道指定节点名的节点被删除了,然后监听函数中就开始争夺 创建指定节点名节点。

    问题2:临时节点,接上面,上面说的是成功创建指定节点名的节点,在正常执行完逻辑后,正常执行完逻辑后,在finally中释放节点,但是,如果占有锁的节点宕机之后,造成的死锁的问题,如何处理?
    回答2:临时节点,zookeeper有四种节点,永久节点在java客户端程序断开连接后会保留,临时节点在java客户端程序断开连接后会销毁,创建临时节点,这样,一旦java后端创建节点的SOA服务,这个客户端获取到锁之后突然挂掉(Session连接断开),这个临时节点会被销毁,其他客户端自动获取锁。

    问题3:临时顺序节点,客户端的监听机制(监听指定节点名的节点的 操作和删除)是所有服务都去监听一个节点的,节点的释放也会通知所有的服务器,如果是900个服务器呢?这对服务器是很大的一个挑战,一个释放的消息,就好像一个牧羊犬进入了羊群,大家都四散而开,随时可能干掉机器,会占用服务资源,网络带宽等等。造成羊群效应,如何处理羊群效应?
    回答3:临时顺序节点,可以顺利解决这个问题。其他所有节点都去监听一个节点问题很大,但是监听自己的前一个节点,因为是顺序的,很容易找到自己的前后。因为每个节点只监听了自己的前一个节点,释放当然也是一个个释放下去,就不会出现羊群效应了。

    问题4:阻塞效果,加锁创建节点,但是你得实现一个阻塞的效果呀,那咋搞?
    回答4:死循环,递归不断去尝试,直到成功,一个伪装的阻塞效果。zk通过节点排队监听的机制,实现了阻塞的原理,其实就是个递归在那无限等待最小节点释放的过程。

    问题5:可重入锁,zookeeper使用指定节点名的唯一性,如何实现分布式锁的可重入?
    回答5:基于zookeeper的分布式锁实现可重入锁,可以带上线程信息,或者机器信息这样的唯一标识(只要是可以唯一表时间客户端连接的就好),获取的时候判断一下,如果是以获取锁的客户端,就不用再获取了,如果不是以获取锁的客户端,还需要重新获取。

    问题6:高可用,zookeeper集群实现的分布式锁,是否高可用?
    回答6:zookeeper是一个分布式集群架构的,是高可用的,对于写操作,follower ACK只要半数以上,就成功了。

    问题7:用zookeeper来实现分布式锁的缺点?
    回答7:
    缺点1:zookeeper性能上可能并没有缓存服务redis那么高(创建和删除节点,比较重)。

    解释:因为每次在创建锁和释放锁的过程中,都要动态创建、销毁瞬时节点来实现锁功能。这是非常重量的,ZK中创建和删除节点只能通过Leader服务器来执行,然后将数据同步到所有的Follower机器上。
    缺点2:使用Zookeeper实现分布式锁,可能带来并发问题,只是并不常见而已。
    解释:由于网络抖动,客户端可zookeeper集群的session连接断了,那么zk以为客户端挂了,就会删除临时节点,这时候其他客户端就可以获取到分布式锁了。就可能产生并发问题了,这个问题不常见是因为zk有重试机制,一旦zk集群检测不到客户端的心跳,就会重试,Curator客户端支持多种重试策略。多次重试之后还不行的话才会删除临时节点。所以,选择一个合适的重试策略也比较重要,要在锁的粒度和并发之间找一个平衡。

  • 以下回答来自chatgpt:

    可能是以下几个原因导致你只能搭建单节点:

    1. 配置文件没有正确设置,未能正确指定集群的配置信息;
    2. 网络连接出现问题,节点无法相互连接;
    3. 未正确启动节点,或者启动的节点没有注册到Zookeeper集群中。

    首先,检查你的配置文件是否正确设置。在Zookeeper的配置文件通常是zoo.cfg,确保其中指定了集群的配置信息,例如以下内容:

    tickTime=2000
    initLimit=10
    syncLimit=5
    dataDir=/var/lib/zookeeper/data
    clientPort=2181
    server.1=192.168.0.1:2888:3888
    server.2=192.168.0.2:2888:3888
    server.3=192.168.0.3:2888:3888
    

    其中,上述的server.1、server.2、server.3表示三个Zookeeper节点的配置信息。

    其次,检查节点之间的网络连接是否正常。可以通过ping命令或其他网络测试工具来检查各个节点是否能够互相通信。

    最后,确保已正确启动每个节点,并且每个节点都已经注册到Zookeeper集群中。在每个节点的启动脚本中,应该指定了配置文件的正确路径,并且节点已经按照配置文件中的信息进行了启动。可以通过以下命令来检查各个节点是否已经注册到Zookeeper集群中:

    echo stat | nc 192.168.0.1 2181
    echo stat | nc 192.168.0.2 2181
    echo stat | nc 192.168.0.3 2181
    

    如果节点已经正常注册,并且集群中至少存在两个节点,那么就已经成功搭建了分布式Zookeeper。

    如果问题仍然存在,那么可以考虑检查Zookeeper节点之间的日志信息,以确定问题的具体原因。


如果你已经解决了该问题, 非常希望你能够分享一下解决方案, 写成博客, 将相关链接放在评论区, 以帮助更多的人 ^-^