问题描述
在多次启动 Curator 服务发现时,在 ZooKeeper 服务器不可用的某些执行中, 开始,它无限期地等待和挂起,可以看到线程转储堆栈跟踪 以下。 当 ZooKeeper 服务器不可用时示例场景开始,然后 ZooKeeper 可用 - 但 Java 线程仍然挂起。 这也是用 Curator 单元测试服务器重现的:org.apache.curator.test.TestingServer。
ZooKeeper 版本为 3.6。
由于这不是一致地重现,这似乎是 Curator/ZooKeeper 客户端的竞争条件。
java.lang.Object.wait(Native Method)
java.lang.Object.wait(Object.java:502)
org.apache.zookeeper.ClientCnxn.submitRequest(ClientCnxn.java:1561)
org.apache.zookeeper.ClientCnxn.submitRequest(ClientCnxn.java:1533)
org.apache.zookeeper.ZooKeeper.create(ZooKeeper.java:1834)
org.apache.curator.framework.imps.CreateBuilderImpl$16.call(CreateBuilderImpl.java:1131)
org.apache.curator.framework.imps.CreateBuilderImpl$16.call(CreateBuilderImpl.java:1113)
org.apache.curator.RetryLoop.callWithRetry(RetryLoop.java:93)
org.apache.curator.framework.imps.CreateBuilderImpl.pathInForeground(CreateBuilderImpl.java:1110)
org.apache.curator.framework.imps.CreateBuilderImpl.protectedPathInForeground(CreateBuilderImpl.java:593)
org.apache.curator.framework.imps.CreateBuilderImpl.forPath(CreateBuilderImpl.java:583)
org.apache.curator.framework.imps.CreateBuilderImpl.forPath(CreateBuilderImpl.java:48)
org.apache.curator.x.discovery.details.ServiceDiscoveryImpl.internalRegisterService(ServiceDiscoveryImpl.java:237)
org.apache.curator.x.discovery.details.ServiceDiscoveryImpl.reRegisterServices(ServiceDiscoveryImpl.java:456)
org.apache.curator.x.discovery.details.ServiceDiscoveryImpl.start(ServiceDiscoveryImpl.java:135)
...
解决方法
作为一种变通的解决方案,初始化在池中的单独线程中执行,以便在挂起时能够通过中断将其停止。