// Path: vertx-infinispan/src/test/java/io/vertx/Lifecycle.java
// public class Lifecycle {
// 
//   private static final Logger log = LoggerFactory.getLogger(Lifecycle.class);
// 
//   public static void closeClustered(List<Vertx> clustered) throws Exception {
//     for (Vertx vertx : clustered) {
//       VertxInternal vertxInternal = (VertxInternal) vertx;
// 
//       InfinispanClusterManager clusterManager = getInfinispanClusterManager(vertxInternal.getClusterManager());
// 
//       ComponentStatus status = null;
//       if (clusterManager != null) {
//         EmbeddedCacheManager cacheManager = (EmbeddedCacheManager) clusterManager.getCacheContainer();
//         status = cacheManager.getStatus();
// 
//         Health health = cacheManager.getHealth();
// 
//         SECONDS.sleep(2); // Make sure rebalancing has been triggered
// 
//         long start = System.currentTimeMillis();
//         try {
//           while (health.getClusterHealth().getHealthStatus() != HealthStatus.HEALTHY
//             && System.currentTimeMillis() - start < MILLISECONDS.convert(2, MINUTES)) {
//             MILLISECONDS.sleep(100);
//           }
//         } catch (Exception ignore) {
//         }
//       }
// 
//       if (status == null || status.compareTo(STOPPING) >= 0) {
//         vertxInternal.close();
//       } else {
//         CountDownLatch latch = new CountDownLatch(1);
//         vertxInternal.close(ar -> {
//           if (ar.failed()) {
//             log.error("Failed to shutdown vert.x", ar.cause());
//           }
//           latch.countDown();
//         });
//         latch.await(2, TimeUnit.MINUTES);
//       }
//     }
//   }
// 
//   private static InfinispanClusterManager getInfinispanClusterManager(ClusterManager cm) {
//     if (cm == null) {
//       return null;
//     }
//     if (cm instanceof WrappedClusterManager) {
//       return getInfinispanClusterManager(((WrappedClusterManager) cm).getDelegate());
//     }
//     if (cm instanceof InfinispanClusterManager) {
//       return (InfinispanClusterManager) cm;
//     }
//     throw new ClassCastException("Unexpected cluster manager implementation: " + cm.getClass());
//   }
// 
//   private Lifecycle() {
//     // Utility
//   }
// }


import static org.hamcrest.CoreMatchers.is;
import static org.infinispan.health.HealthStatus.HEALTHY;
import static org.infinispan.health.HealthStatus.HEALTHY_REBALANCING;
import io.vertx.Lifecycle;
import io.vertx.core.*;
import io.vertx.core.json.JsonObject;
import io.vertx.core.spi.cluster.ClusterManager;
import io.vertx.test.core.VertxTestBase;
import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.TemporaryFolder;
import java.util.List;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;
import static org.hamcrest.CoreMatchers.anyOf;
    super.setUp();
  }

  @Override
  protected void clusteredVertx(VertxOptions options, Handler<AsyncResult<Vertx>> ar) {
    CountDownLatch latch = new CountDownLatch(1);
    Promise<Vertx> promise = Promise.promise();
    promise.future().onComplete(ar);
    super.clusteredVertx(options, asyncResult -> {
      if (asyncResult.succeeded()) {
        promise.complete(asyncResult.result());
      } else {
        promise.fail(asyncResult.cause());
      }
      latch.countDown();
    });
    try {
      assertTrue(latch.await(2, TimeUnit.MINUTES));
    } catch (InterruptedException e) {
      fail(e.getMessage());
    }
  }

  @Override
  protected ClusterManager getClusterManager() {
    return new InfinispanClusterManager();
  }

  @Override
  protected void closeClustered(List<Vertx> clustered) throws Exception {
// Path: vertx-infinispan/src/test/java/io/vertx/Lifecycle.java
// public class Lifecycle {
// 
//   private static final Logger log = LoggerFactory.getLogger(Lifecycle.class);
// 
//   public static void closeClustered(List<Vertx> clustered) throws Exception {
//     for (Vertx vertx : clustered) {
//       VertxInternal vertxInternal = (VertxInternal) vertx;
// 
//       InfinispanClusterManager clusterManager = getInfinispanClusterManager(vertxInternal.getClusterManager());
// 
//       ComponentStatus status = null;
//       if (clusterManager != null) {
//         EmbeddedCacheManager cacheManager = (EmbeddedCacheManager) clusterManager.getCacheContainer();
//         status = cacheManager.getStatus();
// 
//         Health health = cacheManager.getHealth();
// 
//         SECONDS.sleep(2); // Make sure rebalancing has been triggered
// 
//         long start = System.currentTimeMillis();
//         try {
//           while (health.getClusterHealth().getHealthStatus() != HealthStatus.HEALTHY
//             && System.currentTimeMillis() - start < MILLISECONDS.convert(2, MINUTES)) {
//             MILLISECONDS.sleep(100);
//           }
//         } catch (Exception ignore) {
//         }
//       }
// 
//       if (status == null || status.compareTo(STOPPING) >= 0) {
//         vertxInternal.close();
//       } else {
//         CountDownLatch latch = new CountDownLatch(1);
//         vertxInternal.close(ar -> {
//           if (ar.failed()) {
//             log.error("Failed to shutdown vert.x", ar.cause());
//           }
//           latch.countDown();
//         });
//         latch.await(2, TimeUnit.MINUTES);
//       }
//     }
//   }
// 
//   private static InfinispanClusterManager getInfinispanClusterManager(ClusterManager cm) {
//     if (cm == null) {
//       return null;
//     }
//     if (cm instanceof WrappedClusterManager) {
//       return getInfinispanClusterManager(((WrappedClusterManager) cm).getDelegate());
//     }
//     if (cm instanceof InfinispanClusterManager) {
//       return (InfinispanClusterManager) cm;
//     }
//     throw new ClassCastException("Unexpected cluster manager implementation: " + cm.getClass());
//   }
// 
//   private Lifecycle() {
//     // Utility
//   }
// }


// Path: vertx-infinispan/src/test/java/io/vertx/ext/cluster/infinispan/ClusterHealthCheckTest.java
import static org.hamcrest.CoreMatchers.is;
import static org.infinispan.health.HealthStatus.HEALTHY;
import static org.infinispan.health.HealthStatus.HEALTHY_REBALANCING;
import io.vertx.Lifecycle;
import io.vertx.core.*;
import io.vertx.core.json.JsonObject;
import io.vertx.core.spi.cluster.ClusterManager;
import io.vertx.test.core.VertxTestBase;
import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.TemporaryFolder;
import java.util.List;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;
import static org.hamcrest.CoreMatchers.anyOf;

    super.setUp();
  }

  @Override
  protected void clusteredVertx(VertxOptions options, Handler<AsyncResult<Vertx>> ar) {
    CountDownLatch latch = new CountDownLatch(1);
    Promise<Vertx> promise = Promise.promise();
    promise.future().onComplete(ar);
    super.clusteredVertx(options, asyncResult -> {
      if (asyncResult.succeeded()) {
        promise.complete(asyncResult.result());
      } else {
        promise.fail(asyncResult.cause());
      }
      latch.countDown();
    });
    try {
      assertTrue(latch.await(2, TimeUnit.MINUTES));
    } catch (InterruptedException e) {
      fail(e.getMessage());
    }
  }

  @Override
  protected ClusterManager getClusterManager() {
    return new InfinispanClusterManager();
  }

  @Override
  protected void closeClustered(List<Vertx> clustered) throws Exception {
    Lifecycle.closeClustered(clustered);