[infinispan-commits] Infinispan SVN: r320 - in trunk/core/src: main/java/org/infinispan/commands/tx and 2 other directories.
infinispan-commits at lists.jboss.org
infinispan-commits at lists.jboss.org
Mon May 18 17:12:47 EDT 2009
Author: vblagojevic at jboss.com
Date: 2009-05-18 17:12:47 -0400 (Mon, 18 May 2009)
New Revision: 320
Modified:
trunk/core/src/main/java/org/infinispan/commands/LockControlCommand.java
trunk/core/src/main/java/org/infinispan/commands/tx/PrepareCommand.java
trunk/core/src/main/java/org/infinispan/transaction/xa/RemoteTransaction.java
trunk/core/src/test/java/org/infinispan/replication/SyncReplLockingTest.java
Log:
[ISPN-48] - Introduce lock() and unlock() API methods
coordinating LockControlCommand and PrepareCommand around remote tx creation
Modified: trunk/core/src/main/java/org/infinispan/commands/LockControlCommand.java
===================================================================
--- trunk/core/src/main/java/org/infinispan/commands/LockControlCommand.java 2009-05-18 09:47:25 UTC (rev 319)
+++ trunk/core/src/main/java/org/infinispan/commands/LockControlCommand.java 2009-05-18 21:12:47 UTC (rev 320)
@@ -24,7 +24,9 @@
import org.infinispan.commands.tx.AbstractTransactionBoundaryCommand;
import org.infinispan.commands.write.WriteCommand;
import org.infinispan.context.InvocationContext;
+import org.infinispan.context.impl.RemoteTxInvocationContext;
import org.infinispan.transaction.xa.GlobalTransaction;
+import org.infinispan.transaction.xa.RemoteTransaction;
import java.util.Collection;
@@ -68,13 +70,17 @@
public Object perform(InvocationContext ignored) throws Throwable {
if (ignored != null)
throw new IllegalStateException("Expected null context!");
+
+ RemoteTxInvocationContext ctxt = icc.createRemoteTxInvocationContext();
boolean remoteTxinitiated = txTable.getRemoteTransaction(globalTx) != null ? true : false;
+ RemoteTransaction transaction =null;
if (!remoteTxinitiated) {
//create bogus modifications (we do not know modifications ahead of time)
- txTable.createRemoteTransaction(globalTx, new WriteCommand[]{});
+ transaction = txTable.createRemoteTransaction(globalTx, new WriteCommand[]{});
+ ctxt.setRemoteTransaction(transaction);
}
- return super.perform(ignored);
+ return invoker.invoke(ctxt, this);
}
public Object acceptVisitor(InvocationContext ctx, Visitor visitor) throws Throwable {
Modified: trunk/core/src/main/java/org/infinispan/commands/tx/PrepareCommand.java
===================================================================
--- trunk/core/src/main/java/org/infinispan/commands/tx/PrepareCommand.java 2009-05-18 09:47:25 UTC (rev 319)
+++ trunk/core/src/main/java/org/infinispan/commands/tx/PrepareCommand.java 2009-05-18 21:12:47 UTC (rev 320)
@@ -74,16 +74,31 @@
}
public final Object perform(InvocationContext ignored) throws Throwable {
- if (ignored != null) throw new IllegalStateException("Expected null context!");
+ if (ignored != null)
+ throw new IllegalStateException("Expected null context!");
- //1. first create a remote transaction
- RemoteTransaction remoteTransaction = txTable.createRemoteTransaction(globalTx, modifications);
+ // 1. first create a remote transaction
+ RemoteTransaction remoteTransaction = txTable.getRemoteTransaction(globalTx);
+ boolean remoteTxinitiated = remoteTransaction != null ? true : false;
+ if (!remoteTxinitiated) {
+ remoteTransaction = txTable.createRemoteTransaction(globalTx, modifications);
+ } else {
+ /*
+ * remote tx was already created by Cache#lock() API call
+ * set the proper modifications since lock has none
+ *
+ * @see LockControlCommand.java
+ * https://jira.jboss.org/jira/browse/ISPN-48
+ */
+ remoteTransaction.setModifications(modifications);
+ }
- //2. then set it on the invocation context
+ // 2. then set it on the invocation context
RemoteTxInvocationContext ctx = icc.createRemoteTxInvocationContext();
ctx.setRemoteTransaction(remoteTransaction);
- if (trace) log.trace("Invoking remotly orginated prepare: " + this);
+ if (trace)
+ log.trace("Invoking remotly orginated prepare: " + this);
notifier.notifyTransactionRegistered(ctx.getGlobalTransaction(), ctx);
return invoker.invoke(ctx, this);
}
Modified: trunk/core/src/main/java/org/infinispan/transaction/xa/RemoteTransaction.java
===================================================================
--- trunk/core/src/main/java/org/infinispan/transaction/xa/RemoteTransaction.java 2009-05-18 09:47:25 UTC (rev 319)
+++ trunk/core/src/main/java/org/infinispan/transaction/xa/RemoteTransaction.java 2009-05-18 21:12:47 UTC (rev 320)
@@ -38,6 +38,10 @@
public List<WriteCommand> getModifications() {
return modifications;
}
+
+ public void setModifications(WriteCommand[] modifications){
+ this.modifications = Arrays.asList(modifications);
+ }
public CacheEntry lookupEntry(Object key) {
return lookedUpEntries.get(key);
Modified: trunk/core/src/test/java/org/infinispan/replication/SyncReplLockingTest.java
===================================================================
--- trunk/core/src/test/java/org/infinispan/replication/SyncReplLockingTest.java 2009-05-18 09:47:25 UTC (rev 319)
+++ trunk/core/src/test/java/org/infinispan/replication/SyncReplLockingTest.java 2009-05-18 21:12:47 UTC (rev 320)
@@ -34,6 +34,7 @@
import org.infinispan.test.MultipleCacheManagersTest;
import org.infinispan.test.TestingUtil;
import org.infinispan.transaction.lookup.DummyTransactionManagerLookup;
+import org.infinispan.util.concurrent.locks.LockManager;
import org.testng.annotations.Test;
/**
@@ -83,6 +84,31 @@
concurrentLockingHelper(true, true);
}
+
+ public void testLocksReleasedWithNoMods() throws Exception {
+ assertClusterSize("Should only be 2 caches in the cluster!!!", 2);
+
+ assertNull("Should be null", cache1.get(k));
+ assertNull("Should be null", cache2.get(k));
+
+ TransactionManager mgr = TestingUtil.getTransactionManager(cache1);
+ mgr.begin();
+
+ cache1.getAdvancedCache().lock(k);
+
+ //do a dummy read
+ cache1.get(k);
+
+ cache1.getAdvancedCache().unlock(k);
+ mgr.commit();
+
+ assertNoLocks(cache1);
+ assertNoLocks(cache2);
+
+ //TODO fails since assert cache1.isEmpty() is false because lock() creates an entry in data container
+ //cleanup();
+ }
+
private void lockingWithExplicitUnlockHelper(boolean lockPriorToPut) throws Exception {
assertClusterSize("Should only be 2 caches in the cluster!!!", 2);
@@ -108,8 +134,7 @@
assertEquals("Should have replicated", name, cache2.get(k));
cache2.remove(k);
- assert cache1.isEmpty();
- assert cache2.isEmpty();
+ cleanup();
}
private void concurrentLockingHelper(final boolean sameNode, final boolean useTx)
@@ -164,8 +189,7 @@
t.join();
cache2.remove(k);
- assert cache1.isEmpty();
- assert cache2.isEmpty();
+ cleanup();
}
private void locksReleasedWithoutExplicitUnlockHelper(boolean lockPriorToPut, boolean useCommit)
@@ -198,7 +222,21 @@
}
cache2.remove(k);
+ cleanup();
+ }
+
+ protected void assertNoLocks(Cache cache) {
+ /*
+ * cache.keySet() is not implemented yet
+ * LockManager lm = TestingUtil.extractLockManager(cache);
+ * for (Object key : cache.keySet()) assert !lm.isLocked(key);
+ */
+ }
+
+ protected void cleanup(){
assert cache1.isEmpty();
assert cache2.isEmpty();
+ cache1.clear();
+ cache2.clear();
}
}
More information about the infinispan-commits
mailing list