public static void createClientCache(String host, int port1, int port2, int port3, int port4,
      int redundancy, int socketReadTimeout, int retryInterval)
      throws Exception {
    if (!FailOverDetectionByCCU) {
      oldBo = ClientServerObserverHolder.setInstance(new ClientServerObserverAdapter() {
        @Override
        public void beforeFailoverByCacheClientUpdater(ServerLocation epFailed) {
          try {
            Thread.sleep(300000);
          } catch (InterruptedException ie) {
            // expected - test will shut down the cache which will interrupt
            // the CacheClientUpdater thread that invoked this method
            Thread.currentThread().interrupt();
          }
        }
      });
    }

    Properties props = new Properties();
    props.setProperty(MCAST_PORT, "0");
    props.setProperty(LOCATORS, "");
    new RedundancyLevelTestBase().createCache(props);

    PoolImpl p = (PoolImpl) PoolManager.createFactory().addServer(host, PORT1)
        .addServer(host, PORT2).addServer(host, PORT3).addServer(host, PORT4)
        .setSubscriptionEnabled(true).setReadTimeout(socketReadTimeout).setSocketBufferSize(32768)
        .setMinConnections(8).setSubscriptionRedundancy(redundancy).setRetryAttempts(5)
        .setPingInterval(retryInterval).create("DurableClientReconnectDUnitTestPool");

    AttributesFactory<String, String> factory = new AttributesFactory<>();
    factory.setScope(Scope.DISTRIBUTED_ACK);
    factory.setPoolName(p.getName());
    RegionAttributes<String, String> attrs = factory.createRegionAttributes();
    cache.createRegion(REGION_NAME, attrs);
    pool = p;
    createEntriesK1andK2();
    registerK1AndK2();
  }
@param connectedServers is the expected number of connected servers (1 or more)
@param redundantServers is the expected number of redundant servers (0 or more)
geode-core/src/distributedTest/java/org/apache/geode/internal/cache/tier/sockets/RedundancyLevelTestBase.java