This is an automated email from the ASF dual-hosted git repository.

ningjiang pushed a commit to branch SCB-1385
in repository https://gitbox.apache.org/repos/asf/servicecomb-pack.git

commit 5beee85a70117a1dec6ef9563e62e966f9b47c60
Author: Willem Jiang <[email protected]>
AuthorDate: Fri Jul 19 19:37:22 2019 +0800

    SCB-1385 provide a common way to pass the GID and LID
---
 .../pack/omega/context/OmegaContext.java           |  4 ++
 .../pack/omega/context/TransactionContext.java     | 46 +++++++++++++++++++
 .../omega/context/TransactionContextWrapper.java   | 25 +++++++++++
 .../pack/omega/transaction/TransactionAspect.java  | 22 +++++++++
 .../omega/transaction/TransactionAspectTest.java   | 52 ++++++++++++++++++++++
 5 files changed, 149 insertions(+)

diff --git 
a/omega/omega-context/src/main/java/org/apache/servicecomb/pack/omega/context/OmegaContext.java
 
b/omega/omega-context/src/main/java/org/apache/servicecomb/pack/omega/context/OmegaContext.java
index 96e54bd..660b923 100644
--- 
a/omega/omega-context/src/main/java/org/apache/servicecomb/pack/omega/context/OmegaContext.java
+++ 
b/omega/omega-context/src/main/java/org/apache/servicecomb/pack/omega/context/OmegaContext.java
@@ -71,6 +71,10 @@ public class OmegaContext {
     return alphaFeatureAkkaEnabled;
   }
 
+  public TransactionContext getTransactionContext() {
+    return new TransactionContext(globalTxId(), localTxId());
+  }
+
   public void clear() {
     globalTxId.remove();
     localTxId.remove();
diff --git 
a/omega/omega-context/src/main/java/org/apache/servicecomb/pack/omega/context/TransactionContext.java
 
b/omega/omega-context/src/main/java/org/apache/servicecomb/pack/omega/context/TransactionContext.java
new file mode 100644
index 0000000..48bd370
--- /dev/null
+++ 
b/omega/omega-context/src/main/java/org/apache/servicecomb/pack/omega/context/TransactionContext.java
@@ -0,0 +1,46 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.servicecomb.pack.omega.context;
+
+/**
+ *  This class is holding the Transaction related context which could be use 
in customer code
+ */
+public class TransactionContext {
+  private String globalTxId;
+  private String localTxId;
+
+  public TransactionContext(String globalTxId, String localTxId) {
+    this.globalTxId = globalTxId;
+    this.localTxId = localTxId;
+  }
+
+  public String globalTxId() {
+    return globalTxId;
+  }
+
+  public void setGlobalTxId(String globalTxId) {
+    this.globalTxId = globalTxId;
+  }
+
+  public String localTxId() {
+    return localTxId;
+  }
+
+  public void setLocalTxId(String localTxId) {
+    this.localTxId = localTxId;
+  }
+}
diff --git 
a/omega/omega-context/src/main/java/org/apache/servicecomb/pack/omega/context/TransactionContextWrapper.java
 
b/omega/omega-context/src/main/java/org/apache/servicecomb/pack/omega/context/TransactionContextWrapper.java
new file mode 100644
index 0000000..ccfe099
--- /dev/null
+++ 
b/omega/omega-context/src/main/java/org/apache/servicecomb/pack/omega/context/TransactionContextWrapper.java
@@ -0,0 +1,25 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.servicecomb.pack.omega.context;
+
+/**
+ * Once the user business class implement this TransactionContextWrapper, 
Omega could extract the TransactionContext instance
+ * out of the business class, and set up the OmegaContext before calling sub 
transaction method.
+ */
+public interface TransactionContextWrapper {
+  TransactionContext getTransactionContext();
+}
diff --git 
a/omega/omega-transaction/src/main/java/org/apache/servicecomb/pack/omega/transaction/TransactionAspect.java
 
b/omega/omega-transaction/src/main/java/org/apache/servicecomb/pack/omega/transaction/TransactionAspect.java
index 5e57ee7..fa7bbf4 100644
--- 
a/omega/omega-transaction/src/main/java/org/apache/servicecomb/pack/omega/transaction/TransactionAspect.java
+++ 
b/omega/omega-transaction/src/main/java/org/apache/servicecomb/pack/omega/transaction/TransactionAspect.java
@@ -21,6 +21,8 @@ import java.lang.invoke.MethodHandles;
 import java.lang.reflect.Method;
 
 import org.apache.servicecomb.pack.omega.context.OmegaContext;
+import org.apache.servicecomb.pack.omega.context.TransactionContext;
+import org.apache.servicecomb.pack.omega.context.TransactionContextWrapper;
 import org.apache.servicecomb.pack.omega.transaction.annotations.Compensable;
 import org.aspectj.lang.ProceedingJoinPoint;
 import org.aspectj.lang.annotation.Around;
@@ -46,6 +48,15 @@ public class TransactionAspect {
   
@Around("execution(@org.apache.servicecomb.pack.omega.transaction.annotations.Compensable
 * *(..)) && @annotation(compensable)")
   Object advise(ProceedingJoinPoint joinPoint, Compensable compensable) throws 
Throwable {
     Method method = ((MethodSignature) joinPoint.getSignature()).getMethod();
+    // just check if we need to setup the transaction context information first
+    TransactionContext transactionContext = 
getTransactionContextFromArgs(joinPoint.getArgs());
+    if (transactionContext != null) {
+      LOG.debug("Updated context {} for globalTxId:{} and localTxId:{}", 
context,
+          transactionContext.globalTxId(), transactionContext.localTxId());
+      context.setGlobalTxId(transactionContext.globalTxId());
+      context.setLocalTxId(transactionContext.localTxId());
+    }
+
     String localTxId = context.localTxId();
     context.newLocalTxId();
     LOG.debug("Updated context {} for compensable method {} ", context, 
method.toString());
@@ -59,4 +70,15 @@ public class TransactionAspect {
       LOG.debug("Restored context back to {}", context);
     }
   }
+
+  TransactionContext getTransactionContextFromArgs(Object[] args) {
+    if (args != null) {
+      for (Object arg : args) {
+        if (arg instanceof TransactionContextWrapper) {
+          return ((TransactionContextWrapper) arg).getTransactionContext();
+        }
+      }
+    }
+    return null;
+  }
 }
diff --git 
a/omega/omega-transaction/src/test/java/org/apache/servicecomb/pack/omega/transaction/TransactionAspectTest.java
 
b/omega/omega-transaction/src/test/java/org/apache/servicecomb/pack/omega/transaction/TransactionAspectTest.java
index eb82080..17a5aa3 100644
--- 
a/omega/omega-transaction/src/test/java/org/apache/servicecomb/pack/omega/transaction/TransactionAspectTest.java
+++ 
b/omega/omega-transaction/src/test/java/org/apache/servicecomb/pack/omega/transaction/TransactionAspectTest.java
@@ -21,7 +21,9 @@ import static 
com.seanyinx.github.unit.scaffolding.AssertUtils.expectFailing;
 import static org.hamcrest.core.AnyOf.anyOf;
 import static org.hamcrest.core.Is.is;
 import static org.hamcrest.core.IsInstanceOf.instanceOf;
+import static org.junit.Assert.assertNull;
 import static org.junit.Assert.assertThat;
+import static org.mockito.ArgumentMatchers.isNull;
 import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.when;
 
@@ -37,6 +39,8 @@ import java.util.UUID;
 import org.apache.servicecomb.pack.common.EventType;
 import org.apache.servicecomb.pack.omega.context.IdGenerator;
 import org.apache.servicecomb.pack.omega.context.OmegaContext;
+import org.apache.servicecomb.pack.omega.context.TransactionContext;
+import org.apache.servicecomb.pack.omega.context.TransactionContextWrapper;
 import org.apache.servicecomb.pack.omega.transaction.annotations.Compensable;
 import org.aspectj.lang.ProceedingJoinPoint;
 import org.aspectj.lang.reflect.MethodSignature;
@@ -52,6 +56,9 @@ public class TransactionAspectTest {
   private final String localTxId = UUID.randomUUID().toString();
   private final String newLocalTxId = UUID.randomUUID().toString();
 
+  private final String transactionGloablTxId = UUID.randomUUID().toString();
+  private final String transactionLocalTxId = UUID.randomUUID().toString();
+
   private final SagaMessageSender sender = new SagaMessageSender() {
     @Override
     public void onConnected() {
@@ -86,6 +93,9 @@ public class TransactionAspectTest {
   private final OmegaContext omegaContext = new OmegaContext(idGenerator);
   private final TransactionAspect aspect = new TransactionAspect(sender, 
omegaContext);
 
+  private final TransactionContext tx = mock(TransactionContext.class);
+  private final TransactionContextWrapper wrapper = 
mock(TransactionContextWrapper.class);
+
   @Before
   public void setUp() throws Exception {
     when(idGenerator.nextId()).thenReturn(newLocalTxId);
@@ -98,6 +108,48 @@ public class TransactionAspectTest {
 
     omegaContext.setGlobalTxId(globalTxId);
     omegaContext.setLocalTxId(localTxId);
+
+    when(wrapper.getTransactionContext()).thenReturn(tx);
+    when(tx.globalTxId()).thenReturn(transactionGloablTxId);
+    when(tx.localTxId()).thenReturn(transactionLocalTxId);
+  }
+
+  @Test
+  public void testGetTransactionContextFromArgs() throws Throwable {
+
+    TransactionContext result = aspect.getTransactionContextFromArgs(new 
Object[]{tx,wrapper});
+    assertThat(result, is(tx));
+
+    result = aspect.getTransactionContextFromArgs(new Object[]{});
+    assertNull(result);
+
+    result = aspect.getTransactionContextFromArgs(new Object[]{tx});
+    assertNull(result);
+  }
+
+  @Test
+  public void setNewLocalTxIdCompensableWithTransactionContext() throws 
Throwable {
+    // setup the argument class
+    when(joinPoint.getArgs()).thenReturn(new Object[]{wrapper});
+    aspect.advise(joinPoint, compensable);
+    TxEvent startedEvent = messages.get(0);
+
+    assertThat(startedEvent.globalTxId(), is(transactionGloablTxId));
+    assertThat(startedEvent.localTxId(), is(newLocalTxId));
+    assertThat(startedEvent.parentTxId(), is(transactionLocalTxId));
+    assertThat(startedEvent.type(), is(EventType.TxStartedEvent));
+    assertThat(startedEvent.retries(), is(0));
+    assertThat(startedEvent.retryMethod().isEmpty(), is(true));
+
+    TxEvent endedEvent = messages.get(1);
+
+    assertThat(endedEvent.globalTxId(), is(transactionGloablTxId));
+    assertThat(endedEvent.localTxId(), is(newLocalTxId));
+    assertThat(endedEvent.parentTxId(), is(transactionLocalTxId));
+    assertThat(endedEvent.type(), is(EventType.TxEndedEvent));
+
+    assertThat(omegaContext.globalTxId(), is(transactionGloablTxId));
+    assertThat(omegaContext.localTxId(), is(transactionLocalTxId));
   }
 
   @Test

Reply via email to