Skip to content

Commit

Permalink
[JBPM-10088] Subprocess rollbacked transaction makes getTimerMappingI…
Browse files Browse the repository at this point in the history
…nfo query fail
  • Loading branch information
elguardian committed Jun 27, 2022
1 parent 692b6fc commit c7baf50
Show file tree
Hide file tree
Showing 2 changed files with 43 additions and 1 deletion.
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
import java.time.ZonedDateTime;
import java.time.temporal.ChronoUnit;
import java.util.Date;
import java.util.List;
import java.util.concurrent.Callable;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
Expand All @@ -45,13 +46,18 @@
import javax.ejb.TimerHandle;
import javax.ejb.TransactionManagement;
import javax.ejb.TransactionManagementType;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.transaction.RollbackException;
import javax.transaction.UserTransaction;

import org.drools.core.time.JobHandle;
import org.drools.core.time.impl.TimerJobInstance;
import org.jbpm.persistence.timer.GlobalJpaTimerJobInstance;
import org.jbpm.process.core.timer.TimerServiceRegistry;
import org.jbpm.runtime.manager.impl.jpa.EntityManagerFactoryManager;
import org.jbpm.runtime.manager.impl.jpa.TimerMappingInfo;
import org.kie.internal.runtime.manager.InternalRuntimeManager;
import org.kie.internal.runtime.manager.SessionNotFoundException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
Expand Down Expand Up @@ -389,6 +395,36 @@ public TimerJobInstance getTimerByName(String jobName) {
return found;
}

public Timer getEjbTimer(InternalRuntimeManager manager, String uuid) {
try {
TimerMappingInfo timerMappingInfo = getTimerMappinInfo(manager, uuid);
if(timerMappingInfo == null || timerMappingInfo.getInfo() == null) {
return null;
}
byte[] data = timerMappingInfo.getInfo();
return ((TimerHandle) new ObjectInputStream(new ByteArrayInputStream(data)).readObject()).getTimer();
} catch (Exception e) {
logger.warn("wast not able to deserialize info field from timer info for uuid: {}", uuid);
return null;
}
}

private TimerMappingInfo getTimerMappinInfo(InternalRuntimeManager manager, String uuid) {
String pu = ((InternalRuntimeManager) manager).getDeploymentDescriptor().getPersistenceUnit();
EntityManagerFactory emf = EntityManagerFactoryManager.get().getOrCreate(pu);
EntityManager em = emf.createEntityManager();
try {
List<TimerMappingInfo> info = em.createQuery("SELECT o FROM TimerMappingInfo o WHERE o.uuid = :uuid", TimerMappingInfo.class).setParameter("uuid", uuid).getResultList();
if (!info.isEmpty()) {
return info.get(0);
} else {
return null;
}
} finally {
em.close();
}
}

public void evictCache(JobHandle jobHandle) {
String jobName = ((EjbGlobalJobHandle) jobHandle).getUuid();
logger.debug("Invalidate job {} with job name {} in cache", jobName, localCache.remove(jobName));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -101,12 +101,17 @@ public JobHandle scheduleJob(Job job, JobContext ctx, Trigger trigger) {
@Override
public boolean removeJob(JobHandle jobHandle) {
String uuid = ((EjbGlobalJobHandle) jobHandle).getUuid();
final Timer ejbTimer = getEjbTimer(getTimerMappinInfo(uuid));
InternalRuntimeManager manager = ((GlobalTimerService) globalTimerService).getRuntimeManager();
final Timer ejbTimer = scheduler.getEjbTimer(manager, uuid);
if (TRANSACTIONAL && ejbTimer == null) {
// this situation needs to be avoided as it should not happen
logger.debug("ejbTimer not found for {} and tx. This should not be possible.", jobHandle);
return false;
}

JtaTransactionManager tm = (JtaTransactionManager) TransactionManagerFactory.get().newTransactionManager();
logger.debug("Found ejbTimer in TimerMappingInfo {}, removing it. tx status is {}", ejbTimer, tm.getStatus());

try {
tm.registerTransactionSynchronization(new TransactionSynchronization() {
@Override
Expand Down Expand Up @@ -197,6 +202,7 @@ private TimerJobInstance unwrapTimerJobInstance(Timer timer) {
}
}


@Override
public void invalidate(JobHandle jobHandle) {
scheduler.evictCache(jobHandle);
Expand Down

0 comments on commit c7baf50

Please sign in to comment.