blob: 6452d96e9342a4b5ad2445f2adfbd8a6eb37c0fd [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one or more contributor license
* agreements. See the NOTICE file distributed with this work for additional information regarding
* copyright ownership. The ASF licenses this file to You under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the License. You may obtain a
* copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software distributed under the License
* is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
* or implied. See the License for the specific language governing permissions and limitations under
* the License.
*/
package org.apache.geode.internal.cache.tier.sockets;
import static org.apache.geode.cache.Region.SEPARATOR;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
import java.util.ArrayList;
import java.util.List;
import java.util.Properties;
import org.junit.Test;
import org.junit.experimental.categories.Category;
import org.apache.geode.cache.AttributesFactory;
import org.apache.geode.cache.Cache;
import org.apache.geode.cache.CacheFactory;
import org.apache.geode.cache.DataPolicy;
import org.apache.geode.cache.InterestResultPolicy;
import org.apache.geode.cache.Region;
import org.apache.geode.cache.RegionAttributes;
import org.apache.geode.cache.Scope;
import org.apache.geode.distributed.DistributedSystem;
import org.apache.geode.test.dunit.Host;
import org.apache.geode.test.dunit.VM;
import org.apache.geode.test.dunit.Wait;
import org.apache.geode.test.dunit.internal.JUnit4DistributedTestCase;
import org.apache.geode.test.junit.categories.ClientServerTest;
/**
* This tests that basic entry operations work properly when regions are configured with newly added
* RegionAttributes in a P2P environment.
*/
@Category({ClientServerTest.class})
public class NewRegionAttributesDUnitTest extends JUnit4DistributedTestCase {
/** test VM */
VM vm0, vm1 = null;
/** the cache instance for the test */
private static Cache cache = null;
/** total number of puts for the test */
private static final int TOTAL_PUTS = 10;
private static final String REGION_NAME = "NewRegionAttributesDUnitTest_region";
/**
* Creates the server cache on test-VMs
*
* @throws Exception thrown if any problem occurs in set-up
*/
@Override
public final void postSetUp() throws Exception {
disconnectAllFromDS();
Wait.pause(5000);
final Host host = Host.getHost(0);
vm0 = host.getVM(0);
vm1 = host.getVM(1);
Object[] objArr = new Object[4];
// enable WAN
objArr[0] = new Boolean(true);
// enable Publisher
objArr[1] = new Boolean(true);
// enableConflation
objArr[2] = new Boolean(true);
// enableAsyncConflation
objArr[3] = new Boolean(true);
// create cache on test VMs
vm0.invoke(NewRegionAttributesDUnitTest.class, "createServerCache", objArr);
vm1.invoke(NewRegionAttributesDUnitTest.class, "createServerCache", objArr);
}
/**
* Closes the cache on test VMs
*
* @throws Exception thrown if any problem occurs while closing the cache
*/
@Override
public final void preTearDown() throws Exception {
vm0.invoke(() -> NewRegionAttributesDUnitTest.closeCache());
vm1.invoke(() -> NewRegionAttributesDUnitTest.closeCache());
}
/**
* Creates the cache and the region on the test VM with given parameters
*
* @param enableWan boolean to make test-region wan-enabled
* @param setPublisher boolean to make test-region as publisher
* @param enableConflation boolean to enable conflation for test-region
* @param enableAsyncConflation boolean to enable async conflation on test-region
* @throws Exception thrown if any problem occurs while creating cache or test-region
*
* @see AttributesFactory#setPublisher(boolean)
* @see AttributesFactory#setEnableConflation(boolean)
* @see AttributesFactory#setEnableAsyncConflation(boolean)
*/
public static void createServerCache(Boolean enableWan, Boolean setPublisher,
Boolean enableConflation, Boolean enableAsyncConflation) throws Exception {
NewRegionAttributesDUnitTest test = new NewRegionAttributesDUnitTest();
cache = test.createCache(new Properties());
AttributesFactory factory = new AttributesFactory();
factory.setScope(Scope.DISTRIBUTED_ACK);
factory.setDataPolicy(DataPolicy.REPLICATE);
// factory.setPublisher(setPublisher.booleanValue());
factory.setEnableConflation(enableConflation.booleanValue());
factory.setEnableAsyncConflation(enableAsyncConflation.booleanValue());
RegionAttributes attrs = factory.create();
cache.createRegion(REGION_NAME, attrs);
}
/**
* Creates cache instance
*
* @param props - properties of the distributed system
* @throws Exception - thrown if any problem occurs while connecting to distributed system or
* creating cache
*/
private Cache createCache(Properties props) throws Exception {
DistributedSystem ds = getSystem(props);
Cache cache = null;
cache = CacheFactory.create(ds);
if (cache == null) {
throw new Exception("CacheFactory.create() returned null ");
}
return cache;
}
/**
* Closes the cache instance created and disconnects from the distributed system.
*/
public static void closeCache() {
if (cache != null && !cache.isClosed()) {
cache.close();
cache.getDistributedSystem().disconnect();
}
}
/**
* This test configures a region on test VMs with newly added attributes enabled and verifies that
* basic entry operations are properly working. The test does the followings : <br>
* 1)Verify on both the VMs that both the attributes are set properly<br>
* 2)Perform PUTs from one VM and verify that all of them reach the other VM<br>
* 3)Perform PUTs,INVALIDATEs and DESTROYs from one VM and verify at the end that all are
* destroyed in the other VM also<br>
*
* @see AttributesFactory#setPublisher(boolean)
* @see AttributesFactory#setEnableConflation(boolean)
* @see AttributesFactory#setEnableAsyncConflation(boolean)
*/
@Test
public void testEntryOperationsWithNewAttributesEnabled() {
vm0.invoke(() -> NewRegionAttributesDUnitTest.checkAttributes());
vm1.invoke(() -> NewRegionAttributesDUnitTest.checkAttributes());
vm0.invoke(() -> NewRegionAttributesDUnitTest.doPuts());
Integer cnt1 = (Integer) vm1.invoke(() -> NewRegionAttributesDUnitTest.getEntryCount());
assertEquals(TOTAL_PUTS, cnt1.intValue());
vm0.invoke(() -> NewRegionAttributesDUnitTest.doPuts());
vm0.invoke(() -> NewRegionAttributesDUnitTest.doInvalidates());
vm0.invoke(() -> NewRegionAttributesDUnitTest.doDestroy());
Integer cnt2 = (Integer) vm1.invoke(() -> NewRegionAttributesDUnitTest.getEntryCount());
assertEquals(0, cnt2.intValue());
}
/**
* This test tries to call register/unregister interest related API's on the test-region (which
* does not have any bridge-client or bridge-server) and verifies that
* <code>UnsupportedOperationException</code> occurs as expected
*/
@Test
public void testRegisterInterestUseCases() {
vm1.invoke(() -> NewRegionAttributesDUnitTest.registerInterest());
vm1.invoke(() -> NewRegionAttributesDUnitTest.unregisterInterest());
vm1.invoke(() -> NewRegionAttributesDUnitTest.getInterestForRegion());
}
/**
* This methods verifies on both test VMs that enableWan, setPublisher, enableConflation and
* enableAysncConflation are set properly to true for the test-region
*/
public static void checkAttributes() {
Region region1 = cache.getRegion(SEPARATOR + REGION_NAME);
// assertTrue(region1.getAttributes().getPublisher());
assertTrue(region1.getAttributes().getEnableConflation());
assertTrue(region1.getAttributes().getEnableAsyncConflation());
}
/**
* Performs PUT operations on the test-region and fails if any Exception occurs during the PUTs
*/
public static void doPuts() {
Region region1 = cache.getRegion(SEPARATOR + REGION_NAME);
for (int i = 0; i < TOTAL_PUTS; i++) {
try {
region1.put("key-" + i, "val-" + i);
} catch (Exception e) {
fail("Test failed due to unexpected exception during PUTs : " + e);
}
}
}
/**
* Performs INVALIDATES operations on the test-region and fails if any Exception occurs during the
* INVALIDATESs
*/
public static void doInvalidates() {
Region region1 = cache.getRegion(SEPARATOR + REGION_NAME);
for (int i = 0; i < TOTAL_PUTS; i++) {
try {
region1.invalidate("key-" + i);
} catch (Exception e) {
fail("Test failed due to unexpected exception during INVALIDATESs : " + e);
}
}
}
/**
* Performs DESTROY operations on the test-region and fails if any Exception occurs during the
* DESTROYs
*/
public static void doDestroy() {
Region region1 = cache.getRegion(SEPARATOR + REGION_NAME);
for (int i = 0; i < TOTAL_PUTS; i++) {
try {
region1.destroy("key-" + i);
} catch (Exception e) {
fail("Test failed due to unexpected exception during DESTROYs : " + e);
}
}
}
/**
* Gets the total number of entries in the test region
*
* @return total entries
*/
public static Object getEntryCount() {
Region region1 = cache.getRegion(SEPARATOR + REGION_NAME);
int keysSize = region1.entrySet(false).size();
return new Integer(keysSize);
}
/**
* This method invokes all the registerInterest related API's for the test-region and verifies
* that <code>UnsupportedOperationException</code> is thrown in all the cases since test-region
* does not have bridge-server or bridge-client.
*
* @see Region#registerInterest(Object)
* @see Region#registerInterest(Object, InterestResultPolicy)
* @see Region#registerInterestRegex(String)
* @see Region#registerInterestRegex(String, InterestResultPolicy)
*/
public static void registerInterest() {
InterestResultPolicy policy = InterestResultPolicy.KEYS_VALUES;
int totalKeys = 5;
Region region1 = cache.getRegion(SEPARATOR + REGION_NAME);
List keylist = new ArrayList();
for (int i = 0; i < totalKeys; i++) {
keylist.add("key-" + i);
}
boolean exceptionOccurred = false;
// test registerInterest(key)
try {
region1.registerInterest("DummyKey1");
} catch (UnsupportedOperationException expected) {
exceptionOccurred = true;
} finally {
if (!exceptionOccurred)
fail("UnsupportedOperationException was not thrown as expected for registerInterest(key)");
}
// test registerInterest(key,policy)
exceptionOccurred = false;
try {
region1.registerInterest("DummyKey2", policy);
} catch (UnsupportedOperationException expected) {
exceptionOccurred = true;
} finally {
if (!exceptionOccurred)
fail(
"UnsupportedOperationException was not thrown as expected for registerInterest(key,policy)");
}
// test registerInterest(keylist)
exceptionOccurred = false;
try {
region1.registerInterest(keylist);
} catch (UnsupportedOperationException expected) {
exceptionOccurred = true;
} finally {
if (!exceptionOccurred)
fail(
"UnsupportedOperationException was not thrown as expected for registerInterest(keylist)");
}
// test registerInterest(keylist,policy)
exceptionOccurred = false;
try {
region1.registerInterest(keylist, policy);
} catch (UnsupportedOperationException expected) {
exceptionOccurred = true;
} finally {
if (!exceptionOccurred)
fail(
"UnsupportedOperationException was not thrown as expected for registerInterest(keylist,policy)");
}
// test registerInterestRegex(expr)
exceptionOccurred = false;
try {
region1.registerInterestRegex("ke?");
} catch (UnsupportedOperationException expected) {
exceptionOccurred = true;
} finally {
if (!exceptionOccurred)
fail(
"UnsupportedOperationException was not thrown as expected for registerInterestRegex(expr)");
}
// test registerInterestRegex(expr,policy)
exceptionOccurred = false;
try {
region1.registerInterestRegex("ke?", InterestResultPolicy.KEYS_VALUES);
} catch (UnsupportedOperationException expected) {
exceptionOccurred = true;
} finally {
if (!exceptionOccurred)
fail(
"UnsupportedOperationException was not thrown as expected for registerInterestRegex(expr,policy)");
}
}
/**
* This method invokes all the unregisterInterest related API's for the test-region and verifies
* that <code>UnsupportedOperationException</code> is thrown in all the cases since test-region
* does not have bridge-server or bridge-client.
*
* @see Region#unregisterInterest(Object)
* @see Region#unregisterInterestRegex(String)
*/
public static void unregisterInterest() {
int totalKeys = 5;
Region region1 = cache.getRegion(SEPARATOR + REGION_NAME);
List keylist = new ArrayList();
for (int i = 0; i < totalKeys; i++) {
keylist.add("key-" + i);
}
// test unregisterInterest(key)
boolean exceptionOccurred = false;
try {
region1.unregisterInterest("DummyKey1");
} catch (UnsupportedOperationException expected) {
exceptionOccurred = true;
} finally {
if (!exceptionOccurred)
fail(
"UnsupportedOperationException was not thrown as expected for unregisterInterest(key)");
}
// test unregisterInterest(keylist)
exceptionOccurred = false;
try {
region1.unregisterInterest(keylist);
} catch (UnsupportedOperationException expected) {
exceptionOccurred = true;
} finally {
if (!exceptionOccurred)
fail(
"UnsupportedOperationException was not thrown as expected for unregisterInterest(keylist)");
}
// test unregisterInterestRegex(expr)
exceptionOccurred = false;
try {
region1.unregisterInterestRegex("kp?");
} catch (UnsupportedOperationException expected) {
exceptionOccurred = true;
} finally {
if (!exceptionOccurred)
fail(
"UnsupportedOperationException was not thrown as expected for unregisterInterestRegex(expr)");
}
}
/**
* This method invokes all the getter API's for interest-list on the test-region and verifies that
* <code>UnsupportedOperationException</code> is thrown in all the cases since test-region does
* not have bridge-server or bridge-client.
*
* @see Region#getInterestList()
* @see Region#getInterestListRegex()
*/
public static void getInterestForRegion() {
Region region1 = cache.getRegion(SEPARATOR + REGION_NAME);
boolean exceptionOccurred = false;
// test getInterestList()
try {
region1.getInterestList();
} catch (UnsupportedOperationException e) {
exceptionOccurred = true;
} finally {
if (!exceptionOccurred)
fail("UnsupportedOperationException was not thrown as expected for getInterestList()");
}
// test getInterestListRegex()
exceptionOccurred = false;
try {
region1.getInterestListRegex();
} catch (UnsupportedOperationException e) {
exceptionOccurred = true;
} finally {
if (!exceptionOccurred)
fail("UnsupportedOperationException was not thrown as expected for getInterestListRegex()");
}
}
}