/**
  * Simply check if there is an ongoing tx.
  *
  * <ul>
  *   <li>If there is one, this is a no-op and just passes the call up the chain.
  *   <li>If there isn't one and there is a batch in progress, resume the batch's tx, pass up, and
  *       finally suspend the batch's tx.
  *   <li>If there is no batch in progress, just pass the call up the chain.
  * </ul>
  */
 @Override
 protected Object handleDefault(InvocationContext ctx, VisitableCommand command) throws Throwable {
   Transaction tx;
   if (!ctx.isOriginLocal()) return invokeNextInterceptor(ctx, command);
   // if in a batch, attach tx
   if (transactionManager.getTransaction() == null
       && (tx = batchContainer.getBatchTransaction()) != null) {
     try {
       transactionManager.resume(tx);
       // If there's no ongoing tx then BatchingInterceptor creates one and then invokes next
       // interceptor,
       // so that all interceptors in the stack will be executed in a transactional context.
       // This is where a new context (TxInvocationContext) is created, as the existing context is
       // not transactional: NonTxInvocationContext.
       InvocationContext txContext = icc.createInvocationContext(true, -1);
       txContext.setFlags(ctx.getFlags());
       return invokeNextInterceptor(txContext, command);
     } finally {
       if (transactionManager.getTransaction() != null
           && batchContainer.isSuspendTxAfterInvocation()) transactionManager.suspend();
     }
   } else {
     return invokeNextInterceptor(ctx, command);
   }
 }
Example #2
0
  private InvocationContext setInvocationContextFlagsAndClassLoader(
      InvocationContext ctx, EnumSet<Flag> explicitFlags, ClassLoader explicitClassLoader) {
    if (explicitFlags != null) ctx.setFlags(explicitFlags);
    if (explicitClassLoader != null) ctx.setClassLoader(explicitClassLoader);

    return ctx;
  }
 public void applyRemoteTxLog(List<WriteCommand> commands) {
   for (WriteCommand cmd : commands) {
     try {
       // this is a remotely originating tx
       cf.initializeReplicableCommand(cmd, true);
       InvocationContext ctx = icc.createInvocationContext();
       ctx.setFlags(SKIP_REMOTE_LOOKUP, CACHE_MODE_LOCAL, SKIP_SHARED_CACHE_STORE, SKIP_LOCKING);
       interceptorChain.invoke(ctx, cmd);
     } catch (Exception e) {
       log.exceptionWhenReplaying(cmd, e);
     }
   }
 }
  private Map<Object, InternalCacheValue> applyStateMap(
      Map<Object, InternalCacheValue> state, boolean withRetry) {
    Map<Object, InternalCacheValue> retry =
        withRetry ? new HashMap<Object, InternalCacheValue>() : null;

    for (Map.Entry<Object, InternalCacheValue> e : state.entrySet()) {
      InternalCacheValue v = e.getValue();
      InvocationContext ctx = icc.createInvocationContext();
      // locking not necessary in the case of a join since the node isn't doing anything else
      // TODO what if the node is already running?
      ctx.setFlags(
          CACHE_MODE_LOCAL,
          SKIP_CACHE_LOAD,
          SKIP_REMOTE_LOOKUP,
          SKIP_SHARED_CACHE_STORE,
          SKIP_LOCKING,
          SKIP_OWNERSHIP_CHECK);
      try {
        PutKeyValueCommand put =
            cf.buildPutKeyValueCommand(
                e.getKey(), v.getValue(), v.getLifespan(), v.getMaxIdle(), ctx.getFlags());
        interceptorChain.invoke(ctx, put);
      } catch (Exception ee) {
        if (withRetry) {
          if (trace)
            log.tracef(
                "Problem %s encountered when applying state for key %s. Adding entry to retry queue.",
                ee.getMessage(), e.getKey());
          retry.put(e.getKey(), e.getValue());
        } else {
          log.problemApplyingStateForKey(ee.getMessage(), e.getKey());
        }
      }
    }
    return retry;
  }