blob: c917dbe86ff77e881de7806e247605f981b8f2c8 [file] [log] [blame]
/*=========================================================================
* Copyright (c) 2010-2014 Pivotal Software, Inc. All Rights Reserved.
* This product is protected by U.S. and international copyright
* and intellectual property laws. Pivotal products are covered by
* one or more patents listed at http://www.pivotal.io/patents.
*=========================================================================
*/
package com.gemstone.gemfire.cache30;
import com.gemstone.gemfire.SystemFailure;
import com.gemstone.gemfire.internal.cache.xmlcache.CacheCreation;
import com.gemstone.gemfire.cache.*;
import com.gemstone.gemfire.internal.OSProcess;
import dunit.*;
import java.io.*;
import java.util.*;
/**
* Test to make sure dynamic regions work
*
* @author darrel
* @since 4.3
*/
public class DynamicRegionDUnitTest extends CacheTestCase {
// Specify oplog size in MB
private static final int OPLOG_SIZE = 1;
public DynamicRegionDUnitTest(String name) {
super(name);
}
// this test has special config of its distributed system so
// the setUp and tearDown methods need to make sure we don't
// use the ds from previous test and that we don't leave ours around
// for the next test to use.
public void setUp() throws Exception {
try {
disconnectAllFromDS();
} finally {
File d = new File("DynamicRegionData" + OSProcess.getId());
d.mkdirs();
DynamicRegionFactory.get().open(new DynamicRegionFactory.Config(d, null));
super.setUp();
}
}
/**
* Tear down the test suite.
* <p> <H1>IMPORTANT NOTE:</H1>
* Never throw an exception from this method as it will mask any exception thrown
* in a test.
* </p>
*/
public void tearDown2() throws Exception {
getLogWriter().info("Running tearDown in " + this);
try {
//Asif destroy dynamic regions at the end of the test
CacheSerializableRunnable destroyDynRegn = new CacheSerializableRunnable("Destroy Dynamic regions") {
public void run2() throws CacheException
{
Region dr = getCache().getRegion("__DynamicRegions");
if(dr != null) {
dr.localDestroyRegion();
}
}
};
getOtherVm().invoke(destroyDynRegn);
Region dr = getCache().getRegion("__DynamicRegions");
if(dr != null) {
dr.localDestroyRegion();
}
super.tearDown2();
}
catch (VirtualMachineError e) {
SystemFailure.initiateFailure(e);
throw e;
}
catch (Throwable t) {
getLogWriter().severe("tearDown in " + this + " failed due to " + t);
}
finally {
try {
disconnectAllFromDS();
}
catch (VirtualMachineError e) {
SystemFailure.initiateFailure(e);
throw e;
}
catch (Throwable t) {
getLogWriter().severe("tearDown in " + this + " failed to disconnect all DS due to " + t);
}
}
if (! DynamicRegionFactory.get().isClosed()) {
getLogWriter().severe("DynamicRegionFactory not closed!", new Exception());
}
}
////////////////////// Test Methods //////////////////////
private VM getOtherVm() {
Host host = Host.getHost(0);
return host.getVM(0);
}
private void doParentCreateOtherVm(final Properties p, final boolean persist) {
VM vm = getOtherVm();
vm.invoke(new CacheSerializableRunnable("create root") {
public void run2() throws CacheException {
File d = new File("DynamicRegionData" + OSProcess.getId());
d.mkdirs();
DynamicRegionFactory.get().open(new DynamicRegionFactory.Config(d, null));
getSystem(p);
assertEquals(true, DynamicRegionFactory.get().isOpen());
createParentRegion("parent", persist);
}
});
}
private void recreateOtherVm() {
VM vm = getOtherVm();
vm.invoke(new CacheSerializableRunnable("recreate") {
public void run2() throws CacheException {
beginCacheXml();
{
File d = new File("DynamicRegionData" + OSProcess.getId());
d.mkdirs();
CacheCreation cc = (CacheCreation)getCache();
cc.setDynamicRegionFactoryConfig(new DynamicRegionFactory.Config(d, null));
}
createParentRegion("parent", true);
finishCacheXml("dynamicRegionDUnitTest");
// now make sure we recovered from disk ok
assertEquals(true, DynamicRegionFactory.get().isOpen());
}
});
}
private void checkForRegionOtherVm(final String fullPath, final boolean shouldExist) {
VM vm = getOtherVm();
vm.invoke(new CacheSerializableRunnable("checkForRegion") {
public void run2() throws CacheException {
Region r = getCache().getRegion(fullPath);
if (shouldExist) {
if (r == null) {
fail("region " + fullPath + " does not exist");
}
//assertNotSame(r.getParentRegion().getAttributes().getCapacityController(),
// r.getAttributes().getCapacityController());
assertEquals(true, r.containsKey("key1"));
assertEquals(true, r.containsValueForKey("key1"));
assertEquals("value1", r.getEntry("key1").getValue());
} else {
assertEquals(null, r);
}
}
});
}
private void checkForSubregionOtherVm(final String fullPath, final boolean shouldExist) {
VM vm = getOtherVm();
vm.invoke(new CacheSerializableRunnable("checkForRegion") {
public void run2() throws CacheException {
Region r = getCache().getRegion(fullPath);
if (shouldExist) {
if (r == null) {
fail("region " + fullPath + " does not exist");
}
} else {
assertEquals(null, r);
}
}
});
}
/**
* @param persist added this param to fix bug 37439
*/
protected Region createParentRegion(String name, boolean persist) throws CacheException {
final AttributesFactory factory = new AttributesFactory();
factory.setScope(Scope.DISTRIBUTED_ACK);
factory.setDataPolicy(DataPolicy.REPLICATE);
File d = new File("DynamicRegionData" + OSProcess.getId());
factory.setDiskStoreName(getCache().createDiskStoreFactory()
.setDiskDirs(new File[] {d})
.setMaxOplogSize(OPLOG_SIZE)
.create("DynamicRegionDUnitTest")
.getName());
if (persist) {
factory.setDataPolicy(DataPolicy.PERSISTENT_REPLICATE);
}
factory.setEvictionAttributes(EvictionAttributes.createLRUEntryAttributes(100, EvictionAction.OVERFLOW_TO_DISK));
final Region r = createRootRegion(name, factory.create());
return r;
}
/**
* Make sure dynamic regions work on peers
*/
public void testPeerRegion() {
assertEquals(true, DynamicRegionFactory.get().isOpen());
createParentRegion("parent", true);
Properties p = new Properties();
doParentCreateOtherVm(p, false);
Region dr = DynamicRegionFactory.get().createDynamicRegion("parent", "dynamicRegion1");
String drFullPath = dr.getFullPath();
dr.put("key1", "value1");
// test for bug 35528 - support for dynamic subregions of dynamic regions
for (int i=0; i<10; i++) {
DynamicRegionFactory.get().createDynamicRegion(drFullPath, "subregion" + i);
}
getLogWriter().info("testPeerRegion - check #1 make sure other region has new dynamic subregion");
checkForRegionOtherVm(drFullPath, true);
// spot check the subregions
checkForSubregionOtherVm(drFullPath + "/subregion7", true);
// now see if OTHER can recreate which should fetch meta-info from controller
recreateOtherVm();
getLogWriter().info("testPeerRegion - check #2 make sure other region has dynamic region after restarting through getInitialImage");
checkForRegionOtherVm(drFullPath, true);
// now close the controller and see if OTHER can still fetch meta-info from disk
closeCache();
recreateOtherVm();
getLogWriter().info("testPeerRegion - check #3 make sure dynamic region can be recovered from disk");
checkForRegionOtherVm(drFullPath, true);
for (int i=0; i<10; i++) {
checkForSubregionOtherVm(drFullPath + "/subregion" + i, true);
}
// now start our cache back up and see if we still have the dynamic regions
// even if we don't have disk on the controller to recover from.
// This means we will get them from the peer
{
assertEquals(true, DynamicRegionFactory.get().isClosed());
DynamicRegionFactory.get().open(new DynamicRegionFactory.Config());
beginCacheXml();
createParentRegion("parent", true);
finishCacheXml("dynamicRegionCTRDUnitTest");
assertEquals(true, DynamicRegionFactory.get().isOpen());
assertEquals(true, DynamicRegionFactory.get().isActive());
Cache c = getCache();
// verify that controller has all dynamic regions
assertEquals(true, c.getRegion(drFullPath) != null);
// now make sure we can destroy dynamic regions
for (int i=0; i<10; i++) {
String regName = drFullPath + "/subregion" + i;
assertEquals(true, c.getRegion(regName) != null);
DynamicRegionFactory.get().destroyDynamicRegion(regName);
assertEquals(null, c.getRegion(regName));
checkForSubregionOtherVm(regName, false);
}
// make sure that we can explicitly destroy a region and then still
// ask the factory to destroy it.
c.getRegion(drFullPath).localDestroyRegion();
checkForRegionOtherVm(drFullPath, true);
DynamicRegionFactory.get().destroyDynamicRegion(drFullPath);
assertEquals(null, c.getRegion(drFullPath));
checkForRegionOtherVm(drFullPath, false);
}
}
}