in geode-core/src/integrationTest/java/org/apache/geode/TXJUnitTest.java [5925:6188]
public void testEviction() throws CacheException {
final int lruSize = 8;
AttributesFactory<String, Object> af = new AttributesFactory<>();
af.setEvictionAttributes(
EvictionAttributes.createLRUEntryAttributes(lruSize, EvictionAction.LOCAL_DESTROY));
af.setScope(Scope.LOCAL);
Region<String, Object> lruRegion = cache.createRegion(getUniqueName(), af.create());
// Non-TX LRU verification
assertEquals(0, lruRegion.entrySet(false).size());
int numToPut = lruSize + 2;
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("key" + i, new Integer(i));
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
clearRegion(lruRegion);
// TX LRU verification
assertEquals(0, lruRegion.entrySet(false).size());
numToPut = lruSize + 2;
txMgr.begin();
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("key" + i, new Long(i));
}
assertLRUEntries(lruRegion.entrySet(false), numToPut, "key", LRUENTRY_LONG);
txMgr.commit();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_LONG);
clearRegion(lruRegion);
// TX/non-TX no conflict verification w/ initial state
// full+2, all committed entries have TX refs
{
final TXManagerImpl txMgrImpl = (TXManagerImpl) txMgr;
TXStateProxy tx;
numToPut = lruSize + 2;
assertEquals(0, lruRegion.entrySet(false).size());
for (int i = 0; i < numToPut; ++i) {
lruRegion.create("key" + i, new Integer(i));
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
txMgr.begin();
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("key" + i, new Long(i));
}
assertLRUEntries(lruRegion.entrySet(false), numToPut, "key", LRUENTRY_LONG);
tx = txMgrImpl.pauseTransaction();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("non-tx key" + i, new Integer(i));
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
assertNull(lruRegion.get("non-tx key0"));
txMgrImpl.unpauseTransaction(tx);
txMgr.commit();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_LONG);
}
clearRegion(lruRegion);
// TX/non-TX no conflict verification w/ invalid initial state
// full+2, all committed entries have TX refs using a loader
{
AttributesMutator<String, Object> mutator = lruRegion.getAttributesMutator();
mutator.setCacheLoader(new CacheLoader() {
// int count = 0;
@Override
public Object load(LoaderHelper helper) throws CacheLoaderException {
return "value" + helper.getArgument();
}
@Override
public void close() {}
});
final TXManagerImpl txMgrImpl = (TXManagerImpl) txMgr;
TXStateProxy tx;
numToPut = lruSize + 2;
assertEquals(0, lruRegion.entrySet(false).size());
for (int i = 0; i < numToPut; ++i) {
lruRegion.create("key" + i, null);
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_NULL);
// assertIndexDetailsEquals(lruSize, lruRegion.entrySet(false).size());
txMgr.begin();
for (int i = 0; i < numToPut; ++i) {
lruRegion.get("key" + i, new Integer(i));
}
assertLRUEntries(lruRegion.entrySet(false), numToPut, "key", LRUENTRY_STRING);
tx = txMgrImpl.pauseTransaction();
assertEquals(lruSize, lruRegion.entrySet(false).size());
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_NULL);
for (int i = 0; i < numToPut; ++i) {
lruRegion.get("non-tx key" + i, new Integer(i));
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_NULL);
assertNull(lruRegion.getEntry("non-tx key0"));
txMgrImpl.unpauseTransaction(tx);
txMgr.commit();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_STRING);
for (final String s : lruRegion.keySet()) {
lruRegion.localInvalidate(s, null);
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_NULL);
mutator.setCacheLoader(null);
}
clearRegion(lruRegion);
// TX/TX/non-TX no conflict verification w/ initial state full, TX
// add lruLimit+4, existing committed have TX 2 refs, force non-TX
// eviction, force TX eviction
{
final TXManagerImpl txMgrImpl = (TXManagerImpl) txMgr;
TransactionId txId1, txId2;
numToPut = lruSize + 4;
assertEquals(0, lruRegion.entrySet(false).size());
// Create entries
for (int i = 0; i < numToPut; ++i) {
lruRegion.create("key" + i, new Integer(i));
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
txMgr.begin();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
// Add a TX reference to committed entries, add a few on top of that
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("key" + i, new Long(i));
}
assertLRUEntries(lruRegion.entrySet(false), numToPut, "key", LRUENTRY_LONG);
txId1 = txMgrImpl.suspend();
txMgr.begin();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
// Add another TX reference to committed entries, add a few on top of that
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("key" + i, new Double(i));
}
assertLRUEntries(lruRegion.entrySet(false), numToPut, "key", LRUENTRY_DOUBLE);
txId2 = txMgrImpl.suspend();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
// Force the Non-Tx "put" to remove each attempt since region is full
// and all the committed entries are currently part of a TX
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("non-tx key" + i, new Integer(i));
}
assertTrue(numToPut > lruSize);
assertNull(lruRegion.get("non-tx key0"));
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
txMgrImpl.resume(txId1);
assertLRUEntries(lruRegion.entrySet(false), numToPut, "key", LRUENTRY_LONG);
// Check to make sure no conflict was caused by non-TX put evictions
// This should remove all references for each committed entry
txMgr.commit();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_LONG);
txMgrImpl.resume(txId2);
assertLRUEntries(lruRegion.entrySet(false), numToPut, "key", LRUENTRY_DOUBLE);
txMgr.rollback();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_LONG);
// Test to make sure we can evict something that has been rolled back
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("key" + i, "value" + i);
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_STRING);
}
clearRegion(lruRegion);
// TX/non-TX no conflict verification w/ initial state full, TX
// add lruLimit+4, force non-TX eviction, then rolls back, make
// sure that non-TX eviction works properly
{
final TXManagerImpl txMgrImpl = (TXManagerImpl) txMgr;
TXStateProxy tx;
numToPut = lruSize + 4;
assertEquals(0, lruRegion.entrySet(false).size());
// Create entries
for (int i = 0; i < numToPut; ++i) {
lruRegion.create("key" + i, new Integer(i));
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
txMgr.begin();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
// Add a TX reference to committed entries, add a few on top of that
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("key" + i, new Long(i));
}
assertLRUEntries(lruRegion.entrySet(false), numToPut, "key", LRUENTRY_LONG);
tx = txMgrImpl.pauseTransaction();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
// Force the Non-Tx "put" to remove each attempt since region is full
// and all the committed entries are currently part of a TX
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("non-tx key" + i, new Integer(i));
}
assertNull(lruRegion.get("non-tx key0"));
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
txMgrImpl.unpauseTransaction(tx);
assertLRUEntries(lruRegion.entrySet(false), numToPut, "key", LRUENTRY_LONG);
// This should remove all references for each committed entry
txMgr.rollback();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
// Test to make sure we can evict something that has been rolled back
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("key" + i, "value" + i);
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_STRING);
}
clearRegion(lruRegion);
// TX/TX conflict with initial state full, TX
// add lruLimit+4, after failed commit make
// sure that non-TX eviction works properly
{
final TXManagerImpl txMgrImpl = (TXManagerImpl) txMgr;
TXStateProxy tx;
numToPut = lruSize + 4;
assertEquals(0, lruRegion.entrySet(false).size());
// Create entries
for (int i = 0; i < numToPut; ++i) {
lruRegion.create("key" + i, new Integer(i));
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
txMgr.begin();
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
// Add a TX reference to committed entries, add a few on top of that
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("key" + i, new Long(i));
}
assertLRUEntries(lruRegion.entrySet(false), numToPut, "key", LRUENTRY_LONG);
tx = txMgrImpl.pauseTransaction();
// Cause a conflict
lruRegion.put("key" + (numToPut - 1), new Integer(numToPut - 1));
txMgrImpl.unpauseTransaction(tx);
assertLRUEntries(lruRegion.entrySet(false), numToPut, "key", LRUENTRY_LONG);
// This should remove all references for each committed entry
try {
txMgr.commit();
fail("Expected CommitConflictException during commit LRU Eviction test!");
} catch (CommitConflictException ignored) {
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_INTEGER);
// Test to make sure we can evict something that has been rolled back
for (int i = 0; i < numToPut; ++i) {
lruRegion.put("key" + i, "value" + i);
}
assertLRUEntries(lruRegion.entrySet(false), lruSize, "key", LRUENTRY_STRING);
}
lruRegion.localDestroyRegion();
}