I think in current implementation of the alpha server, the compensate
invoking is sync and does not pass the transaction context. The other
question is the omega variable should be associated to a thread, I am not
very sure that your proposal could be fine in the multi threads environment.

Daniel Qian <chanjars...@gmail.com> 于2019年7月22日周一 下午10:34写道:

> Thanks for the suggestion, Feng.
>
> Did you mean Alpha check if the compensation method finished by
> periodically query @Status method?
>
> If I'm not misunderstanding the code, Alpha doesn't wait for the
> TxCompensatedEvent after
> CompensateCommand sent. That means, the
> CompensateCommand-TxCompensatedEvent
> communication is already async in nature.
>
> So we can take advantage of this async nature and no need to add more event
> types and statuses.
> I think we can add an attribute to indicate compensation method is async on
> @Compensable like this:
>
> @Compensale(compensationMethod="rollbackBar", compensationAsync=true)
> public void bar(arg1, arg2, arg3) {
>    // ...
> }
>
> public void rollbackBar(arg1, arg2, arg3, TransactionContextWithParent
> localTx) {
>   rollbackAsync()
>     .onsuccess(() -> {
>        omega.txCompensated(localTx);
>   })
> }
>
> Zheng Feng <zh.f...@gmail.com> 于2019年7月22日周一 下午5:14写道:
>
> > In term of the compensation method, I think I had discussed with Willem
> > before that it could introduce the @Status annotation for the alpha
> server
> > to query the compensation status. When the compensation method is async
> > which means it can not response immediately, it would return the
> > COMPENSATING result and the alpha server could query the @Status method
> to
> > check the compensation status, if this method returns COMPENSATE_OK, the
> > alpha server will mark the local transaction is compensated otherwise
> will
> > mark it with compensate_failed.
> >
> > Daniel Qian <chanjars...@gmail.com> 于2019年7月21日周日 下午8:37写道:
> >
> > > I rethink the idea I proposed, yes, provide low level apis is a bad
> idea,
> > > and I also don't suggest that let user code use omega-xxx-transport
> api.
> > >
> > > I think the essential issues are three:
> > >
> > >    1. How to pass tx context info across threads
> > >    2. How to asynchronously tell Alpha that Saga is ended or aborted,
> > which
> > >    means not triggered on @SagaStart method returns.
> > >    3. How to asynchronously tell Alpha that LocalTx is ended or
> aborted,
> > >    which means not triggered on @Compensable method returns.
> > >
> > > I think we can keep using @SagaStart @Compensable for the
> > XXXStartedEvent,
> > > and provide a helper to manually end/abort Saga/LocalTx. Thanks for PR
> > #506
> > > (SCB-1385) we can use TransactionContext to achieve that. Below is a
> code
> > > sample:
> > >
> > >
> > > @SagaStart(async=true)
> > > public void foo() {
> > >    TransactionContext txContext = OmegaContext.getTransactionContext();
> > >    someAsyncCall()
> > >      .onSuccess(Callback() {
> > >         omega.endSaga(txContext);
> > >      })
> > >      .onException(Callback() {
> > >         omega.abortSaga(txContext);
> > >      })
> > > }
> > >
> > > @Compensable(async=true, compensationMethod="rollbackBar")
> > > public void bar() {
> > >    TransactionContext txContext = OmegaContext.getTransactionContext();
> > >    someAsyncCall()
> > >      .onSuccess(Callback() {
> > >         omega.endTx(txContext);
> > >      })
> > >      .onException(Callback() {
> > >         omega.abortTx(txContext);
> > >      })
> > > }
> > >
> > > The async attribute on @SagaStart and @Compensable prevents
> Saga/LocalTx
> > > ended when method returns.
> > > TransactionContext object can be passed around safely because it's
> > > immutable.
> > > What I have not considered clearly is that how to deal with
> compensation
> > > method if it's also async.
> > >
> > >
> > > Willem Jiang <willem.ji...@gmail.com> 于2019年7月20日周六 下午10:30写道:
> > > >
> > > > Yeah, I agree we need provide some low level API for the user to
> pass.
> > > > In the recent change of SCB-1386, I introduce the TransactionContext
> > > > object which holds the reference of GID and LID, we may add some
> other
> > > > transaction context information there too.
> > > > If the sub transaction is happened in other JVM, we need to pass the
> > > > TxContext across the JVM with help of omega-xxx-transport.
> > > >
> > > > We already have some internal API to send the message from Omega to
> > > > Alpha, I prefer to use annotation instead of expose low level API to
> > > > the user.
> > > >
> > > > Willem Jiang
> > > >
> > > > Twitter: willemjiang
> > > > Weibo: 姜宁willem
> > > >
> > > > On Sat, Jul 20, 2019 at 9:50 PM Daniel Qian <chanjars...@gmail.com>
> > > wrote:
> > > > >
> > > > > After look into SCB-163, SCB-1385 and SCB-1386 I have some thoughts
> > on
> > > Saga
> > > > > involved in async invocation.
> > > > > Current implementation is basically based on sync invocation, there
> > are
> > > > > some assumption:
> > > > >
> > > > >    1. When @SagaStart method returns,  the Saga finished.
> > > > >    2. When @Compensable method returns/throws exception, the Local
> Tx
> > > > >    succeeds/failed.
> > > > >    3. When compensationMethod returns, the Local Tx is compensated.
> > > > >
> > > > > Even if considering what SCB-100 provided:
> > > > >
> > > > >    1. Add @OmegaContextAware annotation enabling
> > > > >    java.util.concurrent.Executor inject OmegaConext into threads it
> > > > >    manages/spawns
> > > > >    2. Make OmegaContext use InheritableThreadLocal field let child
> > > thread
> > > > >    inherit parent thread's Local Tx info
> > > > >
> > > > > There are still some limitations:
> > > > >
> > > > >    1. @OmegaContextAware is only viable if you use spring framework
> > > > >    2. @OmegaContextAware and OmegaContext's InheritableThreadLocal
> > > field
> > > > >    assuming that the calling thread or initator thread has Local Tx
> > >  info.
> > > > >
> > > > >
> > > > > What if user code use producer-consumer pattern in which
> > > > > InheritableThreadLocal can't work?
> > > > > What if user code use a thread scheduling library which we cannot
> use
> > > > > @OmegaContextAware,RxJava and Reactor, for example?
> > > > > I think we could provide some low-level APIs that user code can
> > manualy
> > > > > starts/ends Saga and Local Tx, something like below:
> > > > >
> > > > > TxContext context = omega.startSaga();
> > > > > TxContext subTxContext = omega.startTx(TxContext parentTxContext);
> > > > > omega.endTx(TxContext);
> > > > > omega.abortTx(TxContext);
> > > > > omega.abortSaga(TxContext);
> > > > > omega.endSaga(TxContext);
> > > > >
> > > > > TxContext is just a immutable dto like this:
> > > > >
> > > > > public class TxContext {
> > > > >   private final String globalTxId;
> > > > >   private final String localTxId;
> > > > > }
> > > > >
> > > > > Above is a just a rough idea. So any thoughts?
> > > > > --
> > > > > Daniel Qian
> > > > >
> > > > > 博客:https://segmentfault.com/u/chanjarster
> > > > > github:https://github.com/chanjarster
> > >
> > >
> > >
> > > --
> > > Daniel Qian
> > >
> > > 博客:https://segmentfault.com/u/chanjarster
> > > github:https://github.com/chanjarster
> > >
> >
>
>
> --
> Daniel Qian
>
> 博客:https://segmentfault.com/u/chanjarster
> github:https://github.com/chanjarster
>

Reply via email to