Search in sources :

Example 1 with TransactionEvent

use of org.apache.geode.cache.TransactionEvent in project geode by apache.

the class CallbackArgDUnitTest method doCommitOtherVm.

private void doCommitOtherVm() {
    VM vm = getOtherVm();
    vm.invoke(new CacheSerializableRunnable("create root") {

        public void run2() throws CacheException {
            AttributesFactory af = new AttributesFactory();
            CacheListener cl1 = new CacheListenerAdapter() {

                public void afterCreate(EntryEvent e) {
                    assertEquals(callbackArg, e.getCallbackArgument());
                }
            };
            af.addCacheListener(cl1);
            af.setScope(Scope.DISTRIBUTED_ACK);
            Region r1 = createRootRegion("r1", af.create());
            Region r2 = r1.createSubregion("r2", af.create());
            Region r3 = r2.createSubregion("r3", af.create());
            CacheTransactionManager ctm = getCache().getCacheTransactionManager();
            TransactionListener tl1 = new TransactionListenerAdapter() {

                public void afterCommit(TransactionEvent e) {
                    assertEquals(6, e.getEvents().size());
                    Iterator it = e.getEvents().iterator();
                    while (it.hasNext()) {
                        EntryEvent ee = (EntryEvent) it.next();
                        assertEquals(callbackArg, ee.getCallbackArgument());
                        assertEquals(true, ee.isCallbackArgumentAvailable());
                    }
                }
            };
            ctm.addListener(tl1);
            ctm.begin();
            r2.put("b", "value1", callbackArg);
            r3.put("c", "value2", callbackArg);
            r1.put("a", "value3", callbackArg);
            r1.put("a2", "value4", callbackArg);
            r3.put("c2", "value5", callbackArg);
            r2.put("b2", "value6", callbackArg);
            ctm.commit();
        }
    });
}
Also used : TransactionListener(org.apache.geode.cache.TransactionListener) TransactionListenerAdapter(org.apache.geode.cache.util.TransactionListenerAdapter) CacheException(org.apache.geode.cache.CacheException) CacheListener(org.apache.geode.cache.CacheListener) CacheTransactionManager(org.apache.geode.cache.CacheTransactionManager) TransactionEvent(org.apache.geode.cache.TransactionEvent) AttributesFactory(org.apache.geode.cache.AttributesFactory) CacheListenerAdapter(org.apache.geode.cache.util.CacheListenerAdapter) VM(org.apache.geode.test.dunit.VM) EntryEvent(org.apache.geode.cache.EntryEvent) Iterator(java.util.Iterator) Region(org.apache.geode.cache.Region)

Example 2 with TransactionEvent

use of org.apache.geode.cache.TransactionEvent in project geode by apache.

the class RemoteTransactionDUnitTest method testRemoteExceptionThrown.

@Test
public void testRemoteExceptionThrown() {
    Host host = Host.getHost(0);
    VM acc = host.getVM(0);
    VM datastore = host.getVM(1);
    initAccessorAndDataStore(acc, datastore, 0);
    VM accessor = getVMForTransactions(acc, datastore);
    datastore.invoke(new SerializableCallable() {

        public Object call() throws Exception {
            getGemfireCache().getTxManager().setWriter(new TransactionWriter() {

                public void close() {
                }

                public void beforeCommit(TransactionEvent event) throws TransactionWriterException {
                    throw new TransactionWriterException("AssertionError");
                }
            });
            return null;
        }
    });
    accessor.invoke(new SerializableCallable() {

        public Object call() throws Exception {
            getGemfireCache().getTxManager().begin();
            Region r = getCache().getRegion(CUSTOMER);
            r.put(new CustId(8), new Customer("name8", "address8"));
            try {
                getGemfireCache().getTxManager().commit();
                fail("Expected exception not thrown");
            } catch (Exception e) {
                assertEquals("AssertionError", e.getCause().getMessage());
            }
            return null;
        }
    });
}
Also used : TransactionEvent(org.apache.geode.cache.TransactionEvent) TransactionWriter(org.apache.geode.cache.TransactionWriter) CustId(org.apache.geode.internal.cache.execute.data.CustId) Customer(org.apache.geode.internal.cache.execute.data.Customer) VM(org.apache.geode.test.dunit.VM) SerializableCallable(org.apache.geode.test.dunit.SerializableCallable) TransactionWriterException(org.apache.geode.cache.TransactionWriterException) Region(org.apache.geode.cache.Region) Host(org.apache.geode.test.dunit.Host) NamingException(javax.naming.NamingException) EntryNotFoundException(org.apache.geode.cache.EntryNotFoundException) TransactionWriterException(org.apache.geode.cache.TransactionWriterException) CacheWriterException(org.apache.geode.cache.CacheWriterException) IgnoredException(org.apache.geode.test.dunit.IgnoredException) TransactionDataRebalancedException(org.apache.geode.cache.TransactionDataRebalancedException) TransactionException(org.apache.geode.cache.TransactionException) CacheLoaderException(org.apache.geode.cache.CacheLoaderException) UnsupportedOperationInTransactionException(org.apache.geode.cache.UnsupportedOperationInTransactionException) RollbackException(javax.transaction.RollbackException) TransactionDataNotColocatedException(org.apache.geode.cache.TransactionDataNotColocatedException) CommitConflictException(org.apache.geode.cache.CommitConflictException) DistributedTest(org.apache.geode.test.junit.categories.DistributedTest) TXExpiryJUnitTest(org.apache.geode.TXExpiryJUnitTest) Test(org.junit.Test)

Example 3 with TransactionEvent

use of org.apache.geode.cache.TransactionEvent in project geode by apache.

the class TXJUnitTest method testJTASynchronization.

@Test
public void testJTASynchronization() throws CacheException, javax.transaction.NotSupportedException, javax.transaction.RollbackException, javax.transaction.SystemException, javax.transaction.HeuristicMixedException, javax.transaction.HeuristicRollbackException {
    javax.transaction.TransactionManager jtaTxMgr = this.cache.getJTATransactionManager();
    TransactionListener tl = new TransactionListener() {

        @Override
        public void afterCommit(TransactionEvent event) {
            ++listenerAfterCommit;
            te = event;
        }

        @Override
        public void afterFailedCommit(TransactionEvent event) {
            ++listenerAfterFailedCommit;
            te = event;
        }

        @Override
        public void afterRollback(TransactionEvent event) {
            ++listenerAfterRollback;
            te = event;
        }

        @Override
        public void close() {
            ++listenerClose;
        }
    };
    this.txMgr.addListener(tl);
    Synchronization gfTXSync;
    // Test successful JTA commit
    jtaTxMgr.begin();
    this.txMgr.begin();
    {
        TXManagerImpl gfTxMgrImpl = (TXManagerImpl) this.txMgr;
        gfTXSync = gfTxMgrImpl.getTXState();
    }
    jtaTxMgr.getTransaction().registerSynchronization(gfTXSync);
    assertEquals(0, this.listenerAfterCommit);
    this.cache.getLogger().info("SWAP:doingCreate");
    this.region.create("syncKey1", "syncVal1");
    jtaTxMgr.commit();
    assertEquals(1, this.listenerAfterCommit);
    assertEquals("syncVal1", this.region.getEntry("syncKey1").getValue());
    try {
        this.txMgr.commit();
        fail("JTA Cache Manager should have called commit!");
    } catch (VirtualMachineError e) {
        SystemFailure.initiateFailure(e);
        throw e;
    } catch (Throwable expected) {
    }
    // Test JTA rollback
    jtaTxMgr.begin();
    this.txMgr.begin();
    {
        TXManagerImpl gfTxMgrImpl = (TXManagerImpl) this.txMgr;
        gfTXSync = gfTxMgrImpl.getTXState();
    }
    jtaTxMgr.getTransaction().registerSynchronization(gfTXSync);
    assertEquals(0, this.listenerAfterRollback);
    this.region.put("syncKey2", "syncVal2");
    jtaTxMgr.rollback();
    assertEquals(1, this.listenerAfterRollback);
    assertTrue(!this.region.containsKey("syncKey2"));
    // Test failed JTA commit with suspend
    jtaTxMgr.begin();
    this.txMgr.begin();
    {
        TXManagerImpl gfTxMgrImpl = (TXManagerImpl) this.txMgr;
        gfTXSync = gfTxMgrImpl.getTXState();
        jtaTxMgr.getTransaction().registerSynchronization(gfTXSync);
        assertEquals(0, this.listenerAfterFailedCommit);
        this.region.put("syncKey3", "syncVal3");
        assertEquals("syncVal3", this.region.getEntry("syncKey3").getValue());
        TXStateProxy gfTx = gfTxMgrImpl.internalSuspend();
        javax.transaction.Transaction jtaTx = jtaTxMgr.suspend();
        assertNull(jtaTxMgr.getTransaction());
        this.region.put("syncKey3", "syncVal4");
        assertEquals("syncVal4", this.region.getEntry("syncKey3").getValue());
        gfTxMgrImpl.internalResume(gfTx);
        try {
            jtaTxMgr.resume(jtaTx);
        } catch (Exception failure) {
            fail("JTA resume failed");
        }
        assertNotNull(jtaTxMgr.getTransaction());
    }
    assertEquals("syncVal3", this.region.getEntry("syncKey3").getValue());
    try {
        jtaTxMgr.commit();
        fail("Expected JTA manager conflict exception!");
    } catch (VirtualMachineError e) {
        SystemFailure.initiateFailure(e);
        throw e;
    } catch (Throwable expected) {
    }
    assertEquals(1, this.listenerAfterFailedCommit);
    assertEquals("syncVal4", this.region.getEntry("syncKey3").getValue());
    // Test failed JTA commit with a new thread
    jtaTxMgr.begin();
    this.txMgr.begin();
    {
        TXManagerImpl gfTxMgrImpl = (TXManagerImpl) this.txMgr;
        gfTXSync = gfTxMgrImpl.getTXState();
        jtaTxMgr.getTransaction().registerSynchronization(gfTXSync);
        assertEquals(1, this.listenerAfterFailedCommit);
        this.region.put("syncKey4", "syncVal3");
        assertEquals("syncVal3", this.region.getEntry("syncKey4").getValue());
        // Create a new thread and have it update the same key, causing
        // a conflict
        final int[] signal = { 0 };
        Thread t = new Thread("non-TX conflict generator") {

            @Override
            public void run() {
                try {
                    region.put("syncKey4", "syncVal4");
                    while (true) synchronized (signal) {
                        signal[0] = 1;
                        signal.notify();
                        signal.wait();
                        if (signal[0] == 0) {
                            break;
                        }
                    }
                } catch (Exception error) {
                    fail("Non-tx thread failure due to: " + error);
                }
            }
        };
        t.start();
        try {
            while (true) synchronized (signal) {
                if (signal[0] == 1) {
                    signal[0] = 0;
                    signal.notify();
                    break;
                } else {
                    signal.wait();
                }
            }
        } catch (InterruptedException dangit) {
            fail("Tx thread waiting for non-tx thread failed due to : " + dangit);
        }
        assertEquals("syncVal3", this.region.getEntry("syncKey4").getValue());
    }
    try {
        jtaTxMgr.commit();
        fail("Expected JTA manager conflict exception!");
    } catch (javax.transaction.HeuristicRollbackException expected) {
    } catch (javax.transaction.RollbackException alsoExpected) {
    } catch (VirtualMachineError e) {
        SystemFailure.initiateFailure(e);
        throw e;
    } catch (Throwable yuk) {
        fail("Did not expect this throwable from JTA commit: " + yuk);
    }
    assertEquals(2, this.listenerAfterFailedCommit);
    assertEquals("syncVal4", this.region.getEntry("syncKey4").getValue());
    this.txMgr.removeListener(tl);
}
Also used : TransactionListener(org.apache.geode.cache.TransactionListener) TXManagerImpl(org.apache.geode.internal.cache.TXManagerImpl) Synchronization(javax.transaction.Synchronization) TimeoutException(org.apache.geode.cache.TimeoutException) EntryExistsException(org.apache.geode.cache.EntryExistsException) EntryNotFoundException(org.apache.geode.cache.EntryNotFoundException) CacheWriterException(org.apache.geode.cache.CacheWriterException) TransactionException(org.apache.geode.cache.TransactionException) CacheLoaderException(org.apache.geode.cache.CacheLoaderException) UnsupportedOperationInTransactionException(org.apache.geode.cache.UnsupportedOperationInTransactionException) FailedSynchronizationException(org.apache.geode.cache.FailedSynchronizationException) NoSuchElementException(java.util.NoSuchElementException) CacheException(org.apache.geode.cache.CacheException) CommitConflictException(org.apache.geode.cache.CommitConflictException) QueryException(org.apache.geode.cache.query.QueryException) TransactionEvent(org.apache.geode.cache.TransactionEvent) TXStateProxy(org.apache.geode.internal.cache.TXStateProxy) Test(org.junit.Test) IntegrationTest(org.apache.geode.test.junit.categories.IntegrationTest)

Example 4 with TransactionEvent

use of org.apache.geode.cache.TransactionEvent in project geode by apache.

the class TXJUnitTest method testNoopInvalidates.

@Test
public void testNoopInvalidates() throws CacheException {
    final CachePerfStats stats = this.cache.getCachePerfStats();
    TransactionListener tl = new TransactionListenerAdapter() {

        @Override
        public void afterRollback(TransactionEvent event) {
            te = event;
        }
    };
    this.txMgr.addListener(tl);
    // Make sure invalidates done on invalid entries are noops
    {
        // distributed invalidate
        // first make sure invalidate is counted as a change
        int txRollbackChanges = stats.getTxRollbackChanges();
        this.region.create("key1", "value1");
        this.txMgr.begin();
        this.region.invalidate("key1");
        this.txMgr.rollback();
        assertEquals(txRollbackChanges + 1, stats.getTxRollbackChanges());
        assertEquals(1, te.getEvents().size());
        this.region.destroy("key1");
        this.region.create("key1", "value1");
        this.txMgr.begin();
        this.region.invalidate("key1");
        this.txMgr.commit();
        assertEquals(1, te.getEvents().size());
        this.region.destroy("key1");
        // now make sure a committed entry that is invalid is not counted as a change
        txRollbackChanges = stats.getTxRollbackChanges();
        this.region.create("key1", "value1");
        this.region.invalidate("key1");
        this.txMgr.begin();
        this.region.invalidate("key1");
        this.txMgr.rollback();
        assertEquals(txRollbackChanges, stats.getTxRollbackChanges());
        assertEquals(0, te.getEvents().size());
        this.region.destroy("key1");
        this.region.create("key1", "value1");
        this.region.invalidate("key1");
        this.txMgr.begin();
        this.region.invalidate("key1");
        this.txMgr.commit();
        assertEquals(0, te.getEvents().size());
        this.region.destroy("key1");
        // now make sure that multiple invalidates of same entry are a single change
        txRollbackChanges = stats.getTxRollbackChanges();
        this.region.create("key1", "value1");
        this.txMgr.begin();
        this.region.invalidate("key1");
        this.region.invalidate("key1");
        this.region.invalidate("key1");
        this.txMgr.rollback();
        assertEquals(txRollbackChanges + 1, stats.getTxRollbackChanges());
        assertEquals(1, te.getEvents().size());
        this.region.destroy("key1");
        this.region.create("key1", "value1");
        this.txMgr.begin();
        this.region.invalidate("key1");
        this.region.invalidate("key1");
        this.region.invalidate("key1");
        this.txMgr.commit();
        assertEquals(1, te.getEvents().size());
        this.region.destroy("key1");
    }
    {
        // local invalidate
        // first make sure invalidate is counted as a change
        int txRollbackChanges = stats.getTxRollbackChanges();
        this.region.create("key1", "value1");
        this.txMgr.begin();
        this.region.localInvalidate("key1");
        this.txMgr.rollback();
        assertEquals(txRollbackChanges + 1, stats.getTxRollbackChanges());
        this.region.destroy("key1");
        // now make sure a committed entry that is invalid is not counted as a change
        txRollbackChanges = stats.getTxRollbackChanges();
        this.region.create("key1", "value1");
        this.region.localInvalidate("key1");
        this.txMgr.begin();
        this.region.localInvalidate("key1");
        this.txMgr.rollback();
        assertEquals(txRollbackChanges, stats.getTxRollbackChanges());
        this.region.destroy("key1");
        // now make sure that multiple localInvalidates of same entry are a single change
        txRollbackChanges = stats.getTxRollbackChanges();
        this.region.create("key1", "value1");
        this.txMgr.begin();
        this.region.localInvalidate("key1");
        this.region.localInvalidate("key1");
        this.region.localInvalidate("key1");
        this.txMgr.rollback();
        assertEquals(txRollbackChanges + 1, stats.getTxRollbackChanges());
        this.region.destroy("key1");
    }
}
Also used : TransactionListener(org.apache.geode.cache.TransactionListener) TransactionListenerAdapter(org.apache.geode.cache.util.TransactionListenerAdapter) TransactionEvent(org.apache.geode.cache.TransactionEvent) CachePerfStats(org.apache.geode.internal.cache.CachePerfStats) Test(org.junit.Test) IntegrationTest(org.apache.geode.test.junit.categories.IntegrationTest)

Example 5 with TransactionEvent

use of org.apache.geode.cache.TransactionEvent in project geode by apache.

the class TXJUnitTest method testTxAlgebra.

@Test
public void testTxAlgebra() throws CacheException {
    TransactionId myTxId;
    Region<String, String> reg1 = this.region;
    this.txMgr.setListener(new TransactionListener() {

        @Override
        public void afterCommit(TransactionEvent event) {
            listenerAfterCommit = 1;
            te = event;
        }

        @Override
        public void afterFailedCommit(TransactionEvent event) {
            listenerAfterFailedCommit = 1;
            te = event;
        }

        @Override
        public void afterRollback(TransactionEvent event) {
            listenerAfterRollback = 1;
            te = event;
        }

        @Override
        public void close() {
            listenerClose = 1;
        }
    });
    AttributesMutator<String, String> mutator = this.region.getAttributesMutator();
    CountingCacheListener cntListener = new CountingCacheListener() {

        volatile int aCreateCalls, aUpdateCalls, aInvalidateCalls, aDestroyCalls, aLocalDestroyCalls;

        @Override
        public void close() {
        }

        @Override
        public void reset() {
            this.aCreateCalls = this.aUpdateCalls = this.aInvalidateCalls = this.aDestroyCalls = this.aLocalDestroyCalls = 0;
        }

        @Override
        public void afterCreate(EntryEvent e) {
            ++this.aCreateCalls;
        }

        @Override
        public void afterUpdate(EntryEvent e) {
            ++this.aUpdateCalls;
        }

        @Override
        public void afterInvalidate(EntryEvent e) {
            ++this.aInvalidateCalls;
        }

        @Override
        public void afterDestroy(EntryEvent e) {
            if (e.getOperation().isDistributed()) {
                ++this.aDestroyCalls;
            } else {
                ++this.aLocalDestroyCalls;
            }
        }

        @Override
        public void afterRegionInvalidate(RegionEvent e) {
            fail("Unexpected afterRegionInvalidate in testTxAlgebra");
        }

        @Override
        public void afterRegionDestroy(RegionEvent e) {
            if (!e.getOperation().isClose()) {
                fail("Unexpected afterRegionDestroy in testTxAlgebra");
            }
        }

        @Override
        public void afterRegionClear(RegionEvent event) {
        }

        @Override
        public void afterRegionCreate(RegionEvent event) {
        }

        @Override
        public void afterRegionLive(RegionEvent event) {
        }

        @Override
        public int getAfterCreateCalls() {
            return this.aCreateCalls;
        }

        @Override
        public int getAfterUpdateCalls() {
            return this.aUpdateCalls;
        }

        @Override
        public int getAfterInvalidateCalls() {
            return this.aInvalidateCalls;
        }

        @Override
        public int getAfterDestroyCalls(boolean fetchLocal) {
            return fetchLocal ? this.aLocalDestroyCalls : this.aDestroyCalls;
        }
    };
    mutator.setCacheListener(cntListener);
    CountingCacheWriter cntWriter = new CountingCacheWriter() {

        int bCreateCalls, bUpdateCalls, bDestroyCalls, bLocalDestroyCalls;

        @Override
        public void close() {
        }

        @Override
        public void reset() {
            this.bCreateCalls = this.bUpdateCalls = this.bDestroyCalls = this.bLocalDestroyCalls = 0;
        }

        @Override
        public void beforeCreate(EntryEvent e) {
            ++this.bCreateCalls;
        }

        @Override
        public void beforeUpdate(EntryEvent e) {
            ++this.bUpdateCalls;
        }

        @Override
        public void beforeDestroy(EntryEvent e) {
            ++this.bDestroyCalls;
        }

        @Override
        public void beforeRegionDestroy(RegionEvent e) {
            fail("Unexpected beforeRegionDestroy in testTxAlgebra");
        }

        @Override
        public void beforeRegionClear(RegionEvent e) {
            fail("Unexpected beforeRegionClear in testTxAlgebra");
        }

        @Override
        public int getBeforeCreateCalls() {
            return this.bCreateCalls;
        }

        @Override
        public int getBeforeUpdateCalls() {
            return this.bUpdateCalls;
        }

        @Override
        public int getBeforeDestroyCalls(boolean fetchLocal) {
            return fetchLocal ? this.bLocalDestroyCalls : this.bDestroyCalls;
        }
    };
    mutator.setCacheWriter(cntWriter);
    CountingCallBackValidator callbackVal = new CountingCallBackValidator(cntListener, cntWriter);
    // make sure each op sequence has the correct affect transaction event
    // check C + C -> EX
    // check C + P -> C
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.create("key1", "value1");
    callbackVal.assertCreateWriterCnt(1);
    try {
        reg1.create("key1", "value2");
        fail("expected EntryExistsException");
    } catch (EntryExistsException ok) {
    }
    callbackVal.assertCreateWriterCnt(1, /* remember */
    false);
    reg1.put("key1", "value2");
    callbackVal.assertUpdateWriterCnt(1);
    assertEquals("value2", reg1.getEntry("key1").getValue());
    // Make sure listener callbacks were not triggered before commit
    callbackVal.assertCreateListenerCnt(0, false);
    callbackVal.assertUpdateListenerCnt(0);
    this.txMgr.commit();
    callbackVal.assertCreateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value2", reg1.getEntry("key1").getValue());
    assertEquals(1, this.te.getEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value2", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // Check C + DI -> C
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.create("key1", "value1");
    callbackVal.assertCreateWriterCnt(1);
    reg1.invalidate("key1");
    callbackVal.assertInvalidateCnt(0, false);
    assertTrue(reg1.containsKey("key1"));
    assertTrue(!reg1.containsValueForKey("key1"));
    callbackVal.assertCreateListenerCnt(0, false);
    this.txMgr.commit();
    callbackVal.assertCreateListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(reg1.containsKey("key1"));
    assertTrue(!reg1.containsValueForKey("key1"));
    assertEquals(1, this.te.getEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // TODO: mitch implement the following
    // check LI + DI -> NOOP
    // check DI + LI -> NOOP
    // check DI + DI -> NOOP
    // check LI + LI -> NOOP
    // check C + DD -> NOOP
    callbackVal.reset();
    this.txMgr.begin();
    reg1.create("key1", "value0");
    callbackVal.assertCreateWriterCnt(1);
    reg1.destroy("key1");
    callbackVal.assertDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    callbackVal.assertDestroyListenerCnt(0);
    this.txMgr.commit();
    callbackVal.assertDestroyListenerCnt(0);
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getEvents().size());
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    // Check C + LI -> C
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.create("key1", "value1");
    callbackVal.assertCreateWriterCnt(1);
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0);
    assertTrue(reg1.containsKey("key1"));
    assertTrue(!reg1.containsValueForKey("key1"));
    this.txMgr.commit();
    callbackVal.assertCreateListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(reg1.containsKey("key1"));
    assertTrue(!reg1.containsValueForKey("key1"));
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // Check C + LI + C -> EX
    // Check C + LI + P -> C
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.create("key1", "value1");
    callbackVal.assertCreateWriterCnt(1);
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0);
    try {
        reg1.create("key1", "ex");
        fail("expected EntryExistsException");
    } catch (EntryExistsException ok) {
    }
    callbackVal.assertCreateWriterCnt(1, /* remember */
    false);
    reg1.put("key1", "value2");
    callbackVal.assertUpdateWriterCnt(1);
    assertTrue(reg1.containsKey("key1"));
    assertEquals("value2", reg1.getEntry("key1").getValue());
    callbackVal.assertUpdateListenerCnt(0);
    callbackVal.assertCreateListenerCnt(0, false);
    this.txMgr.commit();
    callbackVal.assertCreateListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(reg1.containsKey("key1"));
    assertEquals("value2", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value2", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // Check C + LI + LD -> NOOP
    callbackVal.reset();
    this.txMgr.begin();
    reg1.create("key1", "value1");
    callbackVal.assertCreateWriterCnt(1);
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    this.txMgr.commit();
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.assertDestroyListenerCnt(0);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(0, this.te.getEvents().size());
    // Check C + LI + DD -> NOOP
    callbackVal.reset();
    this.txMgr.begin();
    reg1.create("key1", "value1");
    callbackVal.assertCreateWriterCnt(1);
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0);
    reg1.destroy("key1");
    callbackVal.assertDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    this.txMgr.commit();
    callbackVal.assertDestroyListenerCnt(0);
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(0, this.te.getEvents().size());
    // check C + LD -> NOOP
    callbackVal.reset();
    this.txMgr.begin();
    reg1.create("key1", "value0");
    callbackVal.assertCreateWriterCnt(1);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    this.txMgr.commit();
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.assertLocalDestroyListenerCnt(0);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(0, this.te.getEvents().size());
    // check C + LD + D -> EX
    // check C + LD + I -> EX
    // check C + LD + C -> C
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.create("key1", "value0");
    callbackVal.assertCreateWriterCnt(1, /* remember */
    false);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    try {
        reg1.localDestroy("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertLocalDestroyWriterCnt(1, /* remember */
    false);
    try {
        reg1.destroy("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertDestroyWriterCnt(0);
    try {
        reg1.localInvalidate("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertInvalidateCnt(0);
    try {
        reg1.invalidate("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertInvalidateCnt(0, /* remember */
    false);
    reg1.create("key1", "value3");
    callbackVal.assertCreateWriterCnt(2);
    assertEquals("value3", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertCreateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value3", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value3", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check C + LD + P -> C
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.create("key1", "value0");
    callbackVal.assertCreateWriterCnt(1, /* remember */
    false);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    reg1.put("key1", "value3");
    callbackVal.assertCreateWriterCnt(2);
    assertEquals("value3", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertCreateListenerCnt(1);
    callbackVal.assertUpdateListenerCnt(0);
    callbackVal.reAssert();
    assertEquals("value3", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value3", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check put of existing entry
    // check P + C -> EX
    // check P + P -> P
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1, /* remember */
    false);
    try {
        reg1.create("key1", "value2");
        fail("expected EntryExistsException");
    } catch (EntryExistsException ok) {
    }
    callbackVal.assertUpdateWriterCnt(1, /* remember */
    false);
    callbackVal.assertCreateWriterCnt(0);
    reg1.put("key1", "value3");
    callbackVal.assertUpdateWriterCnt(2);
    assertEquals("value3", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value3", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getPutEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value3", ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check P + DI -> DI
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1);
    reg1.invalidate("key1");
    callbackVal.assertInvalidateCnt(0, false);
    assertTrue(reg1.containsKey("key1"));
    assertTrue(!reg1.containsValueForKey("key1"));
    this.txMgr.commit();
    callbackVal.assertInvalidateCnt(1);
    callbackVal.assertUpdateListenerCnt(0);
    callbackVal.reAssert();
    assertTrue(reg1.containsKey("key1"));
    assertTrue(!reg1.containsValueForKey("key1"));
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getInvalidateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check P + DD -> D
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1);
    reg1.destroy("key1");
    callbackVal.assertDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    this.txMgr.commit();
    callbackVal.assertUpdateListenerCnt(0);
    callbackVal.assertLocalDestroyListenerCnt(0);
    callbackVal.assertDestroyListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getDestroyEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    // check P + LI -> LI
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1);
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0);
    assertTrue(reg1.containsKey("key1"));
    assertTrue(!reg1.containsValueForKey("key1"));
    this.txMgr.commit();
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(reg1.containsKey("key1"));
    assertEquals(null, reg1.getEntry("key1").getValue());
    assertTrue(!reg1.containsValueForKey("key1"));
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getInvalidateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(!ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // Check P + LI + C -> EX
    // Check P + LI + P -> P
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1, /* remember */
    false);
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0);
    try {
        reg1.create("key1", "ex");
        fail("expected EntryExistsException");
    } catch (EntryExistsException ok) {
    }
    callbackVal.assertCreateWriterCnt(0);
    callbackVal.assertUpdateWriterCnt(1, /* remember */
    false);
    reg1.put("key1", "value2");
    callbackVal.assertUpdateWriterCnt(2);
    assertTrue(reg1.containsKey("key1"));
    assertEquals("value2", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(reg1.containsKey("key1"));
    assertEquals("value2", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getPutEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value2", ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // Check P + LI + LD -> LD
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1);
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    this.txMgr.commit();
    callbackVal.assertUpdateListenerCnt(0);
    callbackVal.assertDestroyListenerCnt(0);
    callbackVal.assertLocalDestroyListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getDestroyEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(!ev.getOperation().isDistributed());
        }
    }
    // Check P + LI + DD -> DD
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1);
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0);
    reg1.destroy("key1");
    callbackVal.assertDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    this.txMgr.commit();
    callbackVal.assertUpdateListenerCnt(0);
    callbackVal.assertDestroyListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getDestroyEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    // check P + LD -> LD
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    this.txMgr.commit();
    callbackVal.assertUpdateListenerCnt(0);
    callbackVal.assertDestroyListenerCnt(0);
    callbackVal.assertLocalDestroyListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getDestroyEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(!ev.getOperation().isDistributed());
        }
    }
    // check P + LD + D -> EX
    // check P + LD + I -> EX
    // check P + LD + C -> C
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    try {
        reg1.localDestroy("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertLocalDestroyWriterCnt(1, /* remember */
    false);
    try {
        reg1.destroy("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertDestroyWriterCnt(0);
    try {
        reg1.localInvalidate("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertInvalidateCnt(0, /* remember */
    false);
    try {
        reg1.invalidate("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertInvalidateCnt(0);
    reg1.create("key1", "value3");
    callbackVal.assertCreateWriterCnt(1);
    assertEquals("value3", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertLocalDestroyListenerCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value3", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value3", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check P + LD + P -> C
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1, /* remember */
    false);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    reg1.put("key1", "value3");
    callbackVal.assertCreateWriterCnt(1);
    assertEquals("value3", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertLocalDestroyListenerCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value3", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value3", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check DI + C -> EX
    // check DI + P -> P
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.invalidate("key1");
    callbackVal.assertInvalidateCnt(0);
    try {
        reg1.create("key1", "value1");
        fail("expected EntryExistsException");
    } catch (EntryExistsException ok) {
    }
    callbackVal.assertCreateWriterCnt(0);
    reg1.put("key1", "value2");
    callbackVal.assertUpdateWriterCnt(1);
    assertEquals("value2", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value2", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getPutEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value2", ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check DI + DD -> D
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.invalidate("key1");
    callbackVal.assertInvalidateCnt(0);
    reg1.destroy("key1");
    callbackVal.assertDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    this.txMgr.commit();
    callbackVal.assertDestroyListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getDestroyEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    // check DI + LD -> LD
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.invalidate("key1");
    callbackVal.assertInvalidateCnt(0);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    this.txMgr.commit();
    callbackVal.assertDestroyListenerCnt(0);
    callbackVal.assertLocalDestroyListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getDestroyEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(!ev.getOperation().isDistributed());
        }
    }
    // check DI + LD + D -> EX
    // check DI + LD + I -> EX
    // check DI + LD + C -> C
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.invalidate("key1");
    callbackVal.assertInvalidateCnt(0, false);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    try {
        reg1.localDestroy("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertLocalDestroyWriterCnt(1, /* remember */
    false);
    try {
        reg1.destroy("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertDestroyWriterCnt(0);
    try {
        reg1.localInvalidate("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertInvalidateCnt(0, /* remember */
    false);
    try {
        reg1.invalidate("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertInvalidateCnt(0, /* remember */
    false);
    reg1.create("key1", "value3");
    callbackVal.assertCreateWriterCnt(1);
    assertEquals("value3", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertInvalidateCnt(0);
    callbackVal.assertDestroyListenerCnt(0);
    callbackVal.assertLocalDestroyListenerCnt(0);
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value3", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value3", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check DI + LD + P -> C
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.invalidate("key1", "value1");
    callbackVal.assertInvalidateCnt(0, false);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    reg1.put("key1", "value3");
    callbackVal.assertCreateWriterCnt(1);
    assertEquals("value3", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertInvalidateCnt(0);
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.assertLocalDestroyListenerCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value3", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value3", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check LI + C -> EX
    // check LI + P -> P
    reg1.create("key1", "value0");
    this.txMgr.begin();
    callbackVal.reset();
    myTxId = this.txMgr.getTransactionId();
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0, false);
    try {
        reg1.create("key1", "value1");
        fail("expected EntryExistsException");
    } catch (EntryExistsException ok) {
    }
    callbackVal.assertCreateWriterCnt(0);
    reg1.put("key1", "value2");
    callbackVal.assertUpdateWriterCnt(1);
    assertEquals("value2", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.assertInvalidateCnt(0);
    callbackVal.reAssert();
    assertEquals("value2", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getPutEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value2", ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check LI + DD -> DD
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0, false);
    reg1.destroy("key1");
    callbackVal.assertDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    this.txMgr.commit();
    callbackVal.assertInvalidateCnt(0);
    callbackVal.assertDestroyListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getDestroyEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    // check LI + LD -> LD
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0, false);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    this.txMgr.commit();
    callbackVal.assertInvalidateCnt(0);
    callbackVal.assertLocalDestroyListenerCnt(1);
    callbackVal.reAssert();
    assertTrue(!reg1.containsKey("key1"));
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getDestroyEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals(null, ev.getNewValue());
            assertEquals("value0", ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(!ev.getOperation().isDistributed());
        }
    }
    // check LI + LD + D -> EX
    // check LI + LD + I -> EX
    // check LI + LD + C -> C
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0, false);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    assertTrue(!reg1.containsKey("key1"));
    try {
        reg1.localDestroy("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertLocalDestroyWriterCnt(1, /* remember */
    false);
    try {
        reg1.destroy("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertDestroyWriterCnt(0);
    try {
        reg1.localInvalidate("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertInvalidateCnt(0, /* remember */
    false);
    try {
        reg1.invalidate("key1");
        fail("expected EntryNotFoundException");
    } catch (EntryNotFoundException ok) {
    }
    callbackVal.assertInvalidateCnt(0, /* remember */
    false);
    reg1.create("key1", "value3");
    callbackVal.assertCreateWriterCnt(1);
    assertEquals("value3", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertInvalidateCnt(0);
    callbackVal.assertDestroyListenerCnt(0);
    callbackVal.assertLocalDestroyListenerCnt(0);
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value3", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value3", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check LI + LD + P -> C
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.localInvalidate("key1", "value1");
    callbackVal.assertInvalidateCnt(0, false);
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    reg1.put("key1", "value3");
    callbackVal.assertCreateWriterCnt(1);
    assertEquals("value3", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertLocalDestroyListenerCnt(0);
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.assertInvalidateCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value3", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value3", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check init state LI + P + I -> I token (bug 33073)
    reg1.create("key1", "value0");
    reg1.localInvalidate("key1");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1);
    assertEquals("value1", reg1.getEntry("key1").getValue());
    reg1.invalidate("key1");
    callbackVal.assertInvalidateCnt(0, false);
    this.txMgr.commit();
    callbackVal.assertUpdateListenerCnt(0);
    callbackVal.assertInvalidateCnt(1);
    callbackVal.reAssert();
    assertNull(reg1.getEntry("key1").getValue());
    {
        // Special check to assert Invaldate token
        LocalRegion.NonTXEntry nonTXe = (LocalRegion.NonTXEntry) reg1.getEntry("key1");
        assertTrue(nonTXe.getRegionEntry().isInvalid());
    }
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getInvalidateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertNull(ev.getNewValue());
            assertNull(ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    // check init state I + P + LI -> LI token (bug 33073)
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.put("key1", "value1");
    callbackVal.assertUpdateWriterCnt(1);
    assertEquals("value1", reg1.getEntry("key1").getValue());
    reg1.localInvalidate("key1");
    callbackVal.assertInvalidateCnt(0, false);
    this.txMgr.commit();
    callbackVal.assertInvalidateCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.reAssert();
    assertNull(reg1.getEntry("key1").getValue());
    {
        // Special check to assert Local Invaldate token
        LocalRegion.NonTXEntry nonTXe = (LocalRegion.NonTXEntry) reg1.getEntry("key1");
        assertTrue(nonTXe.getRegionEntry().isInvalid());
    }
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(0, this.te.getCreateEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getInvalidateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertNull(ev.getNewValue());
            assertNull(ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(!ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check DD + C -> C
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.destroy("key1");
    callbackVal.assertDestroyWriterCnt(1);
    reg1.create("key1", "value1");
    callbackVal.assertCreateWriterCnt(1);
    assertEquals("value1", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertDestroyListenerCnt(0);
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value1", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value1", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check DD + P -> C
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.destroy("key1");
    callbackVal.assertDestroyWriterCnt(1);
    reg1.put("key1", "value1");
    callbackVal.assertCreateWriterCnt(1);
    assertEquals("value1", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertDestroyListenerCnt(0);
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value1", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value1", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check LD + C -> C
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    reg1.create("key1", "value1");
    callbackVal.assertCreateWriterCnt(1);
    assertEquals("value1", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertLocalDestroyListenerCnt(0);
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value1", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value1", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
    // check LD + P -> C
    reg1.create("key1", "value0");
    callbackVal.reset();
    this.txMgr.begin();
    myTxId = this.txMgr.getTransactionId();
    reg1.localDestroy("key1");
    callbackVal.assertLocalDestroyWriterCnt(1);
    reg1.put("key1", "value1");
    callbackVal.assertCreateWriterCnt(1);
    assertEquals("value1", reg1.getEntry("key1").getValue());
    this.txMgr.commit();
    callbackVal.assertLocalDestroyListenerCnt(0);
    callbackVal.assertCreateListenerCnt(0);
    callbackVal.assertUpdateListenerCnt(1);
    callbackVal.reAssert();
    assertEquals("value1", reg1.getEntry("key1").getValue());
    assertEquals(0, this.te.getPutEvents().size());
    assertEquals(0, this.te.getInvalidateEvents().size());
    assertEquals(0, this.te.getDestroyEvents().size());
    assertEquals(1, this.te.getEvents().size());
    {
        List<EntryEvent<?, ?>> events = this.te.getCreateEvents();
        assertEquals(myTxId, this.te.getTransactionId());
        assertEquals(1, events.size());
        for (EntryEvent ev : events) {
            assertEquals(myTxId, ev.getTransactionId());
            assertTrue(ev.getRegion() == reg1);
            assertEquals("key1", ev.getKey());
            assertEquals("value1", ev.getNewValue());
            assertEquals(null, ev.getOldValue());
            verifyEventProps(ev);
            assertEquals(null, ev.getCallbackArgument());
            assertEquals(true, ev.isCallbackArgumentAvailable());
            assertTrue(!ev.isOriginRemote());
            assertTrue(!ev.getOperation().isExpiration());
            assertTrue(ev.getOperation().isDistributed());
        }
    }
    reg1.localDestroy("key1");
}
Also used : TransactionListener(org.apache.geode.cache.TransactionListener) EntryExistsException(org.apache.geode.cache.EntryExistsException) LocalRegion(org.apache.geode.internal.cache.LocalRegion) RegionEvent(org.apache.geode.cache.RegionEvent) TransactionId(org.apache.geode.cache.TransactionId) TransactionEvent(org.apache.geode.cache.TransactionEvent) EntryEvent(org.apache.geode.cache.EntryEvent) EntryNotFoundException(org.apache.geode.cache.EntryNotFoundException) List(java.util.List) ArrayList(java.util.ArrayList) Test(org.junit.Test) IntegrationTest(org.apache.geode.test.junit.categories.IntegrationTest)

Aggregations

TransactionEvent (org.apache.geode.cache.TransactionEvent)16 Test (org.junit.Test)14 IntegrationTest (org.apache.geode.test.junit.categories.IntegrationTest)12 TransactionListener (org.apache.geode.cache.TransactionListener)10 CacheTransactionManager (org.apache.geode.cache.CacheTransactionManager)9 CommitConflictException (org.apache.geode.cache.CommitConflictException)7 EntryEvent (org.apache.geode.cache.EntryEvent)6 TransactionWriter (org.apache.geode.cache.TransactionWriter)6 TransactionWriterException (org.apache.geode.cache.TransactionWriterException)6 ArrayList (java.util.ArrayList)5 AttributesFactory (org.apache.geode.cache.AttributesFactory)4 EntryNotFoundException (org.apache.geode.cache.EntryNotFoundException)4 Region (org.apache.geode.cache.Region)4 SynchronizationCommitConflictException (org.apache.geode.cache.SynchronizationCommitConflictException)4 TransactionId (org.apache.geode.cache.TransactionId)4 TransactionListenerAdapter (org.apache.geode.cache.util.TransactionListenerAdapter)4 Iterator (java.util.Iterator)3 List (java.util.List)3 CacheException (org.apache.geode.cache.CacheException)3 CacheListener (org.apache.geode.cache.CacheListener)3